Как сохранить литерал указателя объединения в C - PullRequest
0 голосов
/ 30 января 2020

Я пытаюсь сохранить указатель литерала, который я определил в переменной сначала в функции mem_init, я попытался сделать это как оператор #define, const header_t * type и header_t *, я также создал функцию ASM для вызова который возвращает значение, каждый раз, когда я делаю один из них, он сохраняет 0x0 в переменной, а не литерал указателя, который я пытаюсь сохранить, я перечислю некоторый код ниже.

Всякий раз, когда функция mem_init запускает указатель Сначала запоминается 0x0.

typedef char ALIGN[16];

// Header for all of the memory blocks
union header {
    struct {
        // Size of block
        size_t size;
        // Is the end of heap space
        unsigned is_end;
        // Is the memory free
        unsigned is_free;
        // Pointer to location of next block
        union header *next;
    } s;
    // Makes header 16 bytes because this is a union
    ALIGN stub;
};
typedef union header header_t;

// The start of the heap space
//extern header_t* START(void);
//#define START (void*) (0x100000 + 20000)
header_t* START = (header_t*) (0x100000 + 20000);

void mem_init() {
    // Initializing first block
    header_t* first = START;
    first->s.is_free = 1;
    first->s.size = MEM_AMOUNT;

    // The ending block
    first->s.next = (START + MEM_AMOUNT);
    first->s.next->s.is_end = 1;
    first->s.next->s.size = 1;
}

Я изменил код на этот, но он по-прежнему не будет хранить правильный указатель, и я не знаю почему. first должен быть равен 1068576, но всегда хранит 0, это скомпилировано с g cc -m32 -g - c -nostdin c -nostdlib, это распределитель памяти для пользовательского ядра / ОС, которое я пытаюсь сделать .

Я компилирую это для i386, это скомпилировано на x86_64 arch linux мое ядро ​​linux -lts 4.19.99-1, g cc версия 9.2.0, binutils версия 2.33. 1-2, nasm 2.14.02, в моей программе нет библиотек, весь код написан мной, отлажен с использованием gdb и qemu-system-x86_64 без ускорения

#define MEM_AMOUNT 0x10000

// Used to make header be 16 bytes long
typedef char ALIGN[32];

// Header for all of the memory blocks
union header {
    struct {
        // Size of block
        size_t size;
        // Is the end of heap space
        unsigned is_end;
        // Is the memory free
        unsigned is_free;
        // Pointer to location of next block
        union header *next;
    } s;
    // Makes header 16 bytes because this is a union
    ALIGN stub;
};
typedef union header header_t;

// The start of the heap space
//extern header_t* START(void);
//#define START (void*) (0x100000 + 20000)
header_t* START = (header_t*) (0x100000 + 20000);

void mem_init() {
    // Initializing first block
    header_t* first = (header_t*) 1068576;//START;
    //1068576;
    first->s.is_free = 1;
    first->s.size = MEM_AMOUNT;

    // The ending block
    first->s.next = (START + MEM_AMOUNT);
    first->s.next->s.is_end = 1;
    first->s.next->s.size = 1;
}

В gdb это значение, которое я всегда вижу при попытке отладки,

Точка останова 6, mem_init () в памяти. c: 42

42 first-> s .is_free = 1;

(gdb) p первый

$ 10 = (header_t *) 0x0

Если вам нужна дополнительная информация, пожалуйста, спросите, я ничего не могу найти с информацией об этом, искал 2 недели.

...