Господа, следующий вопрос:
Как написать функцию, которой в качестве параметра передаётся указатель на некую ячейку памяти, а она в соответсвии с тем принадлежит ли эта ячейка кучи или находиться в стэке "ведёт себя определённым образом" .
Т.е. вопрос сводится к такому виду:
Как определить, зная указатель на переменную, является ли переменна статической или была создана динамически во время выполнения программы?
void what_is(char *s)
{
/*собственно код, пример которого хотелось бы увидеть*/
}
int _tmain(int argc, _TCHAR* argv[])
{
char m[10]; // массив в стекеchar *p; // указатель на динамически создаваемый массив
p=(char*)malloc(10);
//Следом идут два вызова "той саммой" функции
what_is(&m[0]);
what_is(p);
return 0;
}
P.S. Если чё путаю в формулировках, плз, поправьте.
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
11.01.07 20:18: Перенесено модератором из 'C/C++' — Кодт
Re: Статическая или динамическая переменная? В стэке или в к
Здравствуйте, Kv1z, Вы писали:
K>Господа, следующий вопрос: K>Как написать функцию, которой в качестве параметра передаётся указатель на некую ячейку памяти, а она в соответсвии с тем принадлежит ли эта ячейка кучи или находиться в стэке "ведёт себя определённым образом" . K> Т.е. вопрос сводится к такому виду: K>Как определить, зная указатель на переменную, является ли переменна статической или была создана динамически во время выполнения программы?
Вообще-то Скотт Мейерс об этом писал...
По бестиповому указателю — никак... Да и с типизированным — в общем случае — никак...
Хочешь быть счастливым — будь им!
Без булдырабыз!!!
Re: Статическая или динамическая переменная? В стэке или в к
K> Т.е. вопрос сводится к такому виду: K>Как определить, зная указатель на переменную, является ли переменна статической или была создана динамически во время выполнения программы?
Это можно сделать только платформо зависимым способом.
Например под Windows берешь файлы vmquery.h(cpp) из главы 14 книжки Рихтера
и пользуешься его функцией VMQuery.
С её помощью можно ответить на вопрос стек или не стек.
Re: Статическая или динамическая переменная? В стэке или в к
Здравствуйте, Kv1z, Вы писали:
K>Господа, следующий вопрос: K>Как написать функцию, которой в качестве параметра передаётся указатель на некую ячейку памяти, а она в соответсвии с тем принадлежит ли эта ячейка кучи или находиться в стэке "ведёт себя определённым образом" . K> Т.е. вопрос сводится к такому виду: K>Как определить, зная указатель на переменную, является ли переменна статической или была создана динамически во время выполнения программы?
Задача не имеет решения.
Например я пишу свой менеджер памяти, который на стеке выделяет кусок памяти, а при динамичеси выделении делает placement new на стек.
Итог:
Это на стеке — ДА
Это динамически во время выполнения программы — ДА
- Eugeny
Re: Статическая или динамическая переменная? В стэке или в к
K>Народ, должно же быть как-то проще!? Адреса же разные, как узнать нужный диапазон? Место где куча начинается, стек?
на каких-то платформах стек растет в сторону больших адресов, на каких-то в сторону меньших.
На третьих стеков может быть несколько (обычно разные DSP).
Так что это все платформо зависимо. Для Windows 9x/2k+ на X86 решение приведено, а судя по результатам примера у тебя Windows.
Re[2]: Статическая или динамическая переменная? В стэке или
Здравствуйте, Kv1z, Вы писали:
K>Народ, должно же быть как-то проще!? Адреса же разные, как узнать нужный диапазон? Место где куча начинается, стек?
K>
Здравствуйте, Сергей Мухин, Вы писали:
СМ>Здравствуйте, rm822, Вы писали:
СМ>ну и загнули , TIB текущего thread сидит по FS: т.е. достаточно что-то вроде этого:
Спасибо я в курсе, только вот он там не сидит а мэпиться
метод с функциями был выбран намеренно, pTIB->StackBase, согласитесь, более выразительно чем mov StackBase,fs:[4]
Здравствуйте, Kv1z, Вы писали:
K>Господа, следующий вопрос: K>Как написать функцию, которой в качестве параметра передаётся указатель на некую ячейку памяти, а она в соответсвии с тем принадлежит ли эта ячейка кучи или находиться в стэке "ведёт себя определённым образом" .
int* g_stack_begin; // Здесь начало стекаvoid f(int* p)
{
int local_stack; // Здесь текущая позиция в стекеif (p < g_stack_begin && p > &local_stack)
std::cout << "stack" << std::endl;
else
std::cout << "heap" << std::endl;
}
int main()
{
// Инициализируем начало стекаint stack_begin;
g_stack_begin = &stack_begin;
int iii;
f(&iii);
int* ppp = new int;
f(ppp);
}
На многих платформах будет работать. Где то надо будет заменить ">" на "<" и "<" на ">".
Можно перегрузить оператор new для своего класса.
Там хранить вектор указателей, которые он выделяет.
Если указатель в векторе, то объект создан через new
Не забудте при delete удалять указатель из вектора.
Все остальные классы наследовать от того.
class base
{
private:
static vector<void *> items;
public
void * operator new(size_t size)
{
void * h= ::operator new(size);
items.push_back(h);
return h;
}
void operator delete(void * h)
{
// удаляем h из вектора
::operator delete(h);
}
static bool is_dynamic(void * h)
{
return/* проверяем, есть ли он в векторе */;
}
};