2016-10-07 2 views
1

У меня есть назначение, которое должно было оценить некоторые выражения манипуляции указателями и ситуации утечки памяти в C/C++. Там в один я застрял:Передача от шестнадцатеричного до unsigned int * в C++

unsigned int* pInt = (unsigned int*) 0x403004;

Сразу это мне подозрительным, но в задании эта линия теоретически работает, однако, запустив программу я получить Segfault право на этой линии ,

Вопрос в следующем: возможно ли это или возможно, или профессор просто обманывает нас, говоря это правильно? Я видел несколько примеров и вопросы с строкой «Hex» в целом, но ничего относительно «чистый» гекса с Int или междунара *

+3

Если ваша программа не была выделена память по адресу 0x403004 и вы пытаетесь использовать его для чего-нибудь, выдаёт ошибку сегментации является одним из лучшие результаты. – user4581301

+3

проблема не в актере. Проблема заключается в том, что вы делаете с этим указателем впоследствии. В 90% случаев созданный таким образом указатель является фиктивным, и любая попытка сделать что-либо с ним связана с получением segfault. Итак, вы можете рассказать нам больше о задании. –

+0

Вот быстрый эксперимент. Сделайте такую ​​программу: 'int main() {unsigned int * pInt = (unsigned int *) 0x403004; } 'Все, что он делает, это назначить указатель и должен быть действительным, даже если адрес 100% BS, потому что к нему не обращаются. – user4581301

ответ

3
unsigned int* pInt = (unsigned int*) 0x403004; 

Две вещей подозрительными здесь:

  • Если, вы пишете какое-то специализированное программное обеспечение, такое как драйверы устройств или ОС, или вы находитесь в какой-либо встроенной или специальной системе, где память исправлена, поскольку жестко закодированный адрес памяти является подозрительным. Ваша программа (в лучшем случае) потерпит неудачу, если попытается получить доступ к памяти, к которой у нее нет прав доступа.

  • С правой стороны компилятор сначала выводит значение 0x403004, как в int, и будет правильно преобразовывать его в указатель. Таким образом, ваш Segfault, вероятно, является результатом первой точки.

+0

@ пользователь4581301. Этого не было, но я только объясню, насколько опасны перед этим что-то вроде 'unsigned int * pInt = (unsigned int *) myInt;'. Тем не менее, ответ изменился. – WhiZTiM

3

беззнаковое INT * Pint = (беззнаковое INT *) 0x403004;

Возможные ?: да (компилирует, строит просто отлично)

Является ли это правильно ?: зависит от чего. Очевидно, это полезно для иллюстрации в задании класса.

Рекомендуется ли? нет. Он будет вызывать undefined behavior. Вы создаете переменную, указывающую на место в памяти, которое может иметь или не иметь прав. Если вы никогда не используете его, хорошо. Но если вы его используете, результаты будут неопределенными.

+0

Это неопределенное поведение для выполнения приведения, если в местоположении нет объекта. –

2

он отлично работает, только если это число представляет собой уже выделенную память например:

#include <iostream> 

int main() 
{ 
    int i = 7; 
    std::cout << "i: " << i << std::endl; // 7 
    std::cout << "&i: " << &i << std::endl; // in my case: 0018FF44 
    unsigned int* ptr = (unsigned int*)0x0018FF44; // it's ok 

    /* 
    this is just for explaining because the address of i may differ at anytime the program 
    launches thus 0018FF44 will no longer be assigned to i and consequently segfault. 

    the right thing is to make pointer points always to whatever i may take as an address. 
    to do so: 
    */ 

    //int* ptr = (unsigned int*)&i; // not i but the address of i  

    (*ptr)++; 

    std::cout << i << std::endl; // 8 
    // above we changed i through pointer ptr 

    int* pRandom = (int*)0xAB2FC0DE0; // this causes me segfault 
    *pRandom = 5; // segfault 

    std::cout << "*pRandom: " << *pRandom << std::endl; // segfault 

    std::cout << std::endl; 
    return 0; 
} 
+1

Эта вторая часть - это именно то, что я делал, этот пример разъясняет вещи –

+0

ОК, это как ставка. правильно, мы правы только в выделенной памяти, иначе мы столкнулись с катастрофой в любое время. – Raindrop7

+0

Да, я запускаю ваш код, и этот адрес разбился на моем компьютере. Установленный жесткий код адрес, который я положил & i –