информационная безопасность
без паники и всерьез
 подробно о проектеRambler's Top100
Все любят медЗа кого нас держат?Страшный баг в Windows
BugTraq.Ru
Русский BugTraq
 Анализ криптографических сетевых... 
 Модель надежности двухузлового... 
 Специальные марковские модели надежности... 
 Простое пробивание рабочего/провайдерского... 
 400 уязвимостей в процессорах Snapdragon 
 Яндекс неуклюже оправдался за установку... 
главная обзор RSN блог библиотека закон бред форум dnet о проекте
bugtraq.ru / форум / programming
Имя Пароль
ФОРУМ
все доски
FAQ
IRC
новые сообщения
site updates
guestbook
beginners
sysadmin
programming
operating systems
theory
web building
software
hardware
networking
law
hacking
gadgets
job
dnet
humor
miscellaneous
scrap
регистрация





Легенда:
  новое сообщение
  закрытая нитка
  новое сообщение
  в закрытой нитке
  старое сообщение
  • Напоминаю, что масса вопросов по функционированию форума снимается после прочтения его описания.
  • Новичкам также крайне полезно ознакомиться с данным документом.
Дык я передаю истинный размер буфера. Винда просто не... 21.02.05 17:28  Число просмотров: 1564
Автор: amirul <Serge> Статус: The Elderman
<"чистая" ссылка>
> GetModuleBaseName(hProcess, hModule, ProcessName,
> sizeof(ProcessName-1));
>
> Или
> char ProcessName[MAX_PATH+1];
Дык я передаю истинный размер буфера. Винда просто не завершит строку нулем (или вернет статус - недостаточно места) если ей не хватит места развернуться.
В данном конкретном случае:
[out] Pointer to the buffer that receives the base name of the module. If the base name is longer than maximum number of characters specified by the nSize parameter, the base name is truncated

> Твой код потенциально уязвим.
Нет, тот что я привел не содержит уязвимости, но вот в обработке имени она уже может появиться (если надеяться на null-terminator).

> По поводу статики. Если библиотека не найдена, при
> динамической загрузке есть возможность отследить ошибку и
> нормально оповестить пользователя, при статической - полная
> лажа.
Ну дык psapi.dll она вроде стандартная.

> Кроме того goto басиком пахнет Ну и
> вынеси:
Ничуть. "Отец" структурного программирования и лозунгов "Долой goto" Дональд Кнут в конце концов пришел к выводу, что в некоторых случаях использование goto дает более качественный и более ПОНЯТНЫЙ код. Есть два простых правила по использованию goto: 1) Переходить только вперед 2) Переходить границы блоков (compound-statements) только в направлении выхода из них. В этом случае структурность не нарушается, а понятность возрастает

Сравни:

int i, j;
BOOL flag = FALSE;
for (i = 0; i < MAX_I; i++) {
	for (j = 0; j < MAX_J; j++) {
		if (some_condition) {
			flag = TRUE;
			break;
		}
// do something
	}
	if (flag)
		break;
}

---

и

int i, j;
BOOL flag = FALSE;
for (i = 0; i < MAX_I; i++) {
	for (j = 0; j < MAX_J; j++) {
		if (some_condition) {
			goto some_condition_detected;
		}
// do something
	}
}
some_condition_detected:;
// do something more

---
Что эффективнее работает и лучше читается?
В perl-е для этого есть специальный синтаксис в самом языке.


Или даже так:
SOME_RESOURCE res1, res2, res3;
res1 = AllocateResource();
if (res1 == INVALID_RESOURCE)
	return -1;

res2 = AllocateResource();
if (res2 == INVALID_RESOURCE) {
	FreeResource(res1);
	return -1;
}

res3 = AllocateResource();
if (res3 == INVALID_RESOURCE) {
	FreeResource(res2);
	FreeResource(res1);
	return -1;
}
// do something
FreeResource(res3);
FreeResource(res2);
FreeResource(res1);

---
Мало того, что этот метод плохо масштабируется, так он еще и потенциально подвержен ошибкам

Попытки разрешить это дело вложенными if-ами немного помогают, но когда if-ов становится штук 20 начинаешь теряться

Решение проблемы
SOME_RESOURCE res1 = INVALID_RESOURCE, res2 = INVALID_RESOURCE, res3 = INVALID_RESOURCE;
res1 = AllocateResource();
if (res1 == INVALID_RESOURCE)
	goto fail;

res2 = AllocateResource();
if (res2 == INVALID_RESOURCE)
	goto fail;

res3 = AllocateResource();
if (res3 == INVALID_RESOURCE) {
	goto fail;

//do something
	return 0;

fail:
	if (res3 != INVALID_RESOURCE)
		FreeResource(res3);
	if (res2 != INVALID_RESOURCE)
		FreeResource(res2);
	if (res1 != INVALID_RESOURCE)
		FreeResource(res1);

	return -1;

---
Решение хорошо масштабируется, весь код обработки ошибок сведен в одно место, а не рассыпан по функции и выглядит это понятнее. В C++ для этого есть исключения и деструкторы локальных переменных.

> if (!EnumProcesses(Processes, sizeof(Processes),
> &Needed))
> {
> return -1;
> }
"Ну ты меня понял, да?" (с) народная мудрость :-)
<programming> Поиск 








Rambler's Top100
Рейтинг@Mail.ru


  Copyright © 2001-2020 Dmitry Leonov   Page build time: 0 s   Design: Vadim Derkach