Re[2]: Возврат адреса локальной переменной
От: Erop Россия  
Дата: 26.04.12 05:09
Оценка:
Здравствуйте, dilmah, Вы писали:

D>Нигде не регламентируется, что для хранения автоматических переменных используется стандартный стек. Могут использоваться регистры.


Могут, но таки если мы берём адрес переменной, то оптимизатор несколько связан в своих действиях, вообще-то...

D>В данном случае оптимизирующий компилятор имеет полное право вообще вернуть мусор и будет прав.

Сложный это вопрос. Он в любом случае должен вернуть адрес из фрейма функции. Это наблюдаемое поведение же. Что должно лежать по адресу -- вопрос мутный. Например, можно переменную обозначить как волотильную
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re[4]: Пример
От: watch-maker  
Дата: 26.04.12 11:57
Оценка:
А вот и пример, как такой сценарий происходит в дикой природе — http://ideone.com/3wHAj

Тут есть два процесса. Первый в цикле вызывает функцию check. Эта функция вызывает f, в которой записывается в локальную переменную константа и возвращается указатель на эту переменную, после чего функция check проверяет что по указателю записана та же константа.
В таком состоянии первый процесс может работать очень долго — http://ideone.com/ynHNY (тут убран fork)

Но тут в дело вступает второй процесс. Он, конечно, никак напрямую не влияет на контекст первого процесса. Единственное, что он делает — это посылает сигналы.
И вот в момент, когда приходит сигнал, ОС приостанавливает первый процесс и выделяет в его стеке новый фрейм и попутно уничтожает все локальные переменных, из уже отживших функций.

Таким образом, если сигнал приходит в момент между строчками 21 и 22, то происходит перезапись памяти, а value оказывается равным другому значению — в этом случае программа печатает oops.
Re[4]: Возврат адреса локальной переменной
От: salvequick  
Дата: 26.04.12 11:59
Оценка:
Здравствуйте, watch-maker, Вы писали:

S>>У такого обработчика дожен быть совершенно другой контекст по идее.

WM>По какой ещё идее? Обработчик же может принадлежать программе.
По той идее, что никаких обработчиков сигналов в данном примере нет.

S>>И следовательно другой стек.

WM>Создавать новый полноценный стек на каждый приход сигнала. Шутишь?
Я имел ввиду, что если в программе своего обработчика сигналов нет то значит имеется ввиду какой другой процесс и другой стек.
Re[3]: Возврат адреса локальной переменной
От: ДимДимыч Украина http://klug.org.ua
Дата: 26.04.12 16:23
Оценка: 1 (1)
Здравствуйте, salvequick, Вы писали:

S>между int *m=f();

S>и value=m;
S>никаких вызовов нет. ничего не вызывается ,никто не трогает стек.

Между этими действиями в системе может образоваться дефицит памяти, ядро имеет право отправить процесс в своп, сохранив при этом только действительную часть стека, и отбросив все, что за указателем его вершины. При определенных условиях (например, вершина находится на границе страниц) после восстановлении процесса в памяти за пределами вершины может быть мусор.
Обязательно бахнем! И не раз. Весь мир в труху! Но потом. (ДМБ)
Re[5]: Возврат адреса локальной переменной
От: ДимДимыч Украина http://klug.org.ua
Дата: 26.04.12 16:27
Оценка:
Здравствуйте, salvequick, Вы писали:

S>По той идее, что никаких обработчиков сигналов в данном примере нет.


В той части процесса, которая получается из вышеприведенного кода — нет. А во всем процессе, в том числе в системных библиотеках — никто не знает, может и быть.
Обязательно бахнем! И не раз. Весь мир в труху! Но потом. (ДМБ)
Re: Возврат адреса локальной переменной
От: Кодт Россия  
Дата: 26.04.12 18:58
Оценка: +1
Здравствуйте, salvequick, Вы писали:

S>Я сам прокручивал самые разные версии вплоть до влияния ОС, процессорной архитектуры, типа компилятора и ключей оптимизации кода. Никаких результатов стабильно держится value=5 при всех комбинациях.


Влияние ОС? Да пожалуйста. Берём любую ОС без защиты памяти. Хоть MS-DOS, хоть что-нибудь микроконтроллерное.
Как там устроены прерывания? Очень просто. Это внезапный вызов системной функции, прямо на пользовательском стеке. (А уже оттуда система может переключить контекст, подменить стек и всё такое).
Естественно, что всё, что лежит ниже указателя стека, — затирается.

В отличие от процессоров с защитой, где прерывание — это сперва смена контекста (хотя бы по-простому, переключение банка регистров), а уже потом всё остальное.
Перекуём баги на фичи!
Re[2]: Возврат адреса локальной переменной
От: Erop Россия  
Дата: 26.04.12 19:03
Оценка:
Здравствуйте, rg45, Вы писали:

R>В отладочной конфигурации компилятор вполне может помечать освобожденную стековую память каким-нибудь определенным значением — для облегчения диагностики подобных ошибок.


А интерпретатор может вообще стек на списке фреймов залудить, например
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.