Need some clarification about how data is stored in memory

Hi, I tested this code:

fn main() {
    let var_1 = 7;
    let p_var_1 = &var_1;
    println!("var_1 - {} - {:p}", var_1, &var_1);
    println!("p_var_1 - {} - {:p} - {:p}\n", p_var_1, p_var_1, &p_var_1);

    let var_2 = Box::new(77);
    let p_var_2 = &var_2;
    println!("var_2 - {} - {:p} - {:p}", var_2, var_2, &var_2);
    println!("p_var_2 - {} - {:p} - {:p}", p_var_2, p_var_2, &p_var_2);
}

This is the output:

var_1 - 7 - 0x7ffe0364fc04
p_var_1 - 7 - 0x7ffe0364fc04 - 0x7ffe0364fc08

var_2 - 77 - 0x55855ce9bba0 - 0x7ffe0364fcd0
p_var_2 - 77 - 0x7ffe0364fcd0 - 0x7ffe0364fcd8

Now i need some clarification about what is stored where ? This is what i understood so far:

  1. The address 0x7ffe0364fc04 has the value 7 stored in it and its on the stack with 32 bits capacity or 4 bytes.
  2. The address 0x7ffe0364fc08 has ... i don't know.
  3. The address 0x55855ce9bba0 has ... i don't know.
  4. The address 0x7ffe0364fcd0 has the value 77 stored in it and it's on the heap cuz Box<> stores the data on the heap.
  5. The address 0x7ffe0364fcd8 has ... i don't know.

Also the &str are supposed to be stored as plain text in the executable. Is it the same for integers like i32 or doubles ?

Don't look at the exact addresses. Unless you know your system's memory layout, ASLR, etc. by heart (unlikely), addresses won't tell you anything about the particular segment your values are stored in.

With that out of the way, there are only two and two-halves simple rules you need to know:

  1. If you declare a local variable, that variable goes to the stack. There's no implicit heap-allocation. (Conceptually at least – the compiler is free to optimize so that it doesn't even go to the stack and is stashed in a register instead.)
  2. If you put a value inside a container that actively heap-allocates it, then of course that value goes to the heap. (The container itself may go to the stack or the heap or wherever, really.)
  3. (statics go into static memory, but you don't seem to be asking about those.)
  4. A reference is just a pointer (with extra compile-time checks). It points to wherever its pointee is – be it the stack, the heap, the static segment, wherever, really.

So, in your code:

  • var_1 is on the stack, conceptually.
  • p_var_1 is on the stack. It points to var_1 (so it points into the stack).
  • var_2, the box itself, is on the stack. The wrapped data of the box, i.e. the 77, aka *var_2, is on the heap.
  • p_var_2 is on the stack. It points to the box, so it points to the stack.
  • Since a box in itself is a pointer-like type, you can say that var_2 and *p_var_2 point to the heap.

Absolutely not. They are stored as their raw byte representation.

3 Likes

Thanks for the answer. it's much clearer now.

What is that static memory or statics you mentioned ?

Is there something like a program, a GUI to show the user what the memory layout is and what is stored in the memory in real time ?

  1. Correct.
  2. The address 0x7ffe0364fc08 has 8 bytes and contains 0x7ffe0364fc04 (a pointer to #1).
  3. The address 0x55855ce9bba0 has 4 bytes and contains 77.
  4. The address 0x7ffe0364fcd0 has 8 bytes and contains 0x55855ce9bba0 (a pointer to #3).
  5. The address 0x7ffe0364fcd8 has 8 bytes and contains 0x7ffe0364fcd0 (a pointer to #4).
1 Like

They are data that live for the entire duration of the program.

None that I know of. Programmers usually use a debugger for similar purposes.

2 Likes