referencerustmemory-address

Passing a memory address in Rust


I have a function where I need to pass a memory address. I only managed to find that we can print out a memory address by using println!("{:p}", number);.

How can I access the memory address and use it in a function?


Solution

  • Rust provides raw pointers, *const T and *mut T for this purpose. You can convert a usize to these types, and then dereference or create a Rust reference to that value, in an unsafe block.

    Rust references automatically ensure that they are always valid. i.e. if you use one in safe Rust, then value that it references will always be properly initialised, and it won't have been dropped. Once you deal with raw pointers and memory addresses, you are responsible for that yourself, and you can cause some pretty serious problems by getting it wrong.

    If you have a value on the stack, you can get it like this:

    fn main() {
        let my_value = 123;
        // get a reference to the value
        let my_value_ref = &my_value;
        // convert the reference to a raw pointer
        let my_value_raw_ptr = my_value_ref as *const i32;
        // convert the raw pointer to an integer
        let my_value_addr = my_value_raw_ptr as usize;
    
        println!("address = {:X}", my_value_addr);
    }
    

    If the value is heap-allocated, then usually there is a provided method to obtain a raw pointer. For example, Box and Rc have an into_raw() method while String and Vec have as_ptr():

    fn main() {
        let my_vec = vec![1, 2, 3];
        // get a raw pointer pointer to the data
        let my_vec_ptr = my_vec.as_ptr();
        // convert the raw pointer to an integer
        let my_vec_addr = my_vec_ptr as usize;
    
        println!("address = {:X}", my_vec_addr);
    }
    

    Obtaining the address like this is completely safe. However, you will need to use unsafe Rust to actually do anything useful with it. It will be up to you to make sure that the value at that address is valid whenever it is accessed.