3

I tried such a piece of code to loop through the bytes of a u64:

let mut message: u64 = 0x1234123412341234;
let msg = &message as *mut u8;

for b in 0..8 {
    // ...some work...
}

Unfortunately, Rust doesn't allow such C-like indexing.

Shepmaster
  • 388,571
  • 95
  • 1,107
  • 1,366
hedgar2017
  • 1,425
  • 3
  • 21
  • 40
  • this code in C would be implemented behavior so it's hard to exactly understand what you want. And by the way, if we talk about strictly conforming, this code in C would be undefined behavior. – Stargateur May 27 '18 at 11:35
  • 1
    @Stargateur `char` (and [`un`]`signed char`) is an explicit exception to the strict aliasing rule, so it's easily possible to write this code in strictly conforming C. The actual behavior is implementation defined, but not undefined. – trent May 27 '18 at 18:24

2 Answers2

5

While transmute-ing is possible (see @Tim's answer), it is better to use the byteorder crate to guarantee endianness:

extern crate byteorder;

use byteorder::ByteOrder;

fn main() {
    let message = 0x1234123412341234u64;
    let mut buf = [0; 8];
    byteorder::LittleEndian::write_u64(&mut buf, message);

    for b in &buf {
         // 34, 12, 34, 12, 34, 12, 34, 12, 
         print!("{:X}, ", b);
    }

    println!("");

    byteorder::BigEndian::write_u64(&mut buf, message);

    for b in &buf {
         // 12, 34, 12, 34, 12, 34, 12, 34, 
         print!("{:X}, ", b);
    }
}

(Permalink to the playground)

Shepmaster
  • 388,571
  • 95
  • 1,107
  • 1,366
mcarton
  • 27,633
  • 5
  • 85
  • 95
3

It's safe to transmute u64 into an array [u8; 8]:

let message_arr: [u8; 8] = unsafe { mem::transmute(message) };
for b in &message_arr {
    println!("{}", b)
}

See this in action on the playground.

Shepmaster
  • 388,571
  • 95
  • 1,107
  • 1,366
Tim Diekmann
  • 7,755
  • 11
  • 41
  • 69