Why does setting a value at an arbitrary memory location not work?

前端 未结 3 1126
我在风中等你
我在风中等你 2021-01-17 08:05

I have this code:

#include 
#include 
#include 
#include 

int main (int argc, char** argv)          


        
3条回答
  •  不思量自难忘°
    2021-01-17 08:57

    What you are doing:

    *(volatile uint8_t*)0x12345678u = 1;
    int var = *(volatile uint8_t*)0x12345678;
    

    is totally wrong.

    You have no guarantee whatsoever that an arbitrary address like 0x12345678 will be accessible, not to mention writable by your program. In other words, you cannot set a value to an arbitrary address and expect it to work. It's undefined behavior to say the least, and will most likely crash your program due to the operating system stopping you from touching memory you don't own.

    The "command terminated" that you get when trying to run your program happens exactly because the operating system is preventing your program from accessing a memory location it is not allowed to access. Your program gets killed before it can do anything.


    If you are on Linux, you can use the mmap function to request a memory page at an (almost) arbitrary address before accessing it (see man mmap). Here's an example program which achieves what you want:

    #include 
    #include 
    
    #define WANTED_ADDRESS (void *)0x12345000
    #define WANTED_OFFSET 0x678 // 0x12345000 + 0x678 = 0x12345678
    
    int main(void) {
        // Request a memory page starting at 0x12345000 of 0x1000 (4096) bytes.
        unsigned char *mem = mmap(WANTED_ADDRESS, 0x1000, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0);
    
        // Check if the OS correctly granted your program the requested page.
        if (mem != WANTED_ADDRESS) {
            perror("mmap failed");
            return 1;
        }
    
        // Get a pointer inside that page.
        int *ptr = (int *)(mem + WANTED_OFFSET); // 0x12345678
    
        // Write to it.
        *ptr = 123;
    
        // Inspect the results.
        printf("Value  : %d\n", *ptr);
        printf("Address: %p\n", ptr);
    
        return 0;
    }
    

提交回复
热议问题