@Linda-chan

Linda-chan

Линда Кайе
Linda-chan

Дата рождения: 01.11.1983

Тотальная неудачница и убийца жёстких дисков. Самая большая поклонница Ариэль. Член ордена Вселенского тормоза имени Осаки-сан. Любительница каваййных переднеприводных машинок. Суккуб на полставки. Когти прилагаются.

https://www.lindachan.net

10 я читаю 59 меня читают
15542 постов
26273 комментариев
Linda-chan
04 Feb 2022

Короче, есть библиотека на FreeBasic, которую я использую в программах на VB6. Все объявления функций – в TLB файле. Добавила пару функций для кое-каких манипуляций с датой. Функция принимает один параметр типа Date (Double), производит манипуляции и возвращает дату в другой параметр того же типа. Возвращаемое значение Boolean (VARIANT_BOOL) сообщает, получилось произвести манипуляции или нет. Внутрях в том числе используются функции вроде VariantTimeToSystemTime() для конвертации в SYSTEMTIME. Вооот. Начались вылеты тестовой программы. Сначала выполнялась функция, а в конце случалось исключение. При чём WinDbg говорил, что беда случается в функциях категории SysStringLen(), которые работают с BSTR. Учитывая, что проблемный код не оперирует никакими BSTR, зато в тестовой программе функции вызывались прямо при конструировании строки с «отчётом» о проверке, выглядело всё так, словно где-то в библиотеке портится память, а потом всё ломается в программе. Ибо в программе не использовалось ничего особенного кроме для манипуляций со строками. Я долго вдумчиво смотрела в код, думала, какие-то проблемы с указателями, что-то не так передаётся во второй параметр, который указатель, либо не так вызываются функции конвертации даты из Date в SYSTEMTIME. Но там всё выглядело нормально. Кроме того, меня как-то настораживало сообщение: «Инструкция по адресу "0x77159d90" обратилась к памяти по адресу "0x0000fffb"». И второй адрес-то был всегда один и тот же. Откуда же он такой интересный? В общем, я посмотрела ещё раз исходник TLB и обнаружила, что по причине, связанной с ночным копипастингом, у меня возвращаемое значение (на самом деле – последний параметр функции) объявлено не как VARIANT_BOOL, а как BSTR. Я сваяла объявления в самом начале и больше даже не заглядывала туда. И вот что происходило. VARIANT_BOOL – это двухбайтовое целое со знаком (потому что совместимость с OLE в Win16), которое принимает значения 0 или -1 (кстати, частый вопрос, почему именно -1, а не 1), а BSTR – это четырёхбайтовый указатель на массив двухбайтных символов. Функция, возвращая True, записывала -1 в параметр, а код на VB6 получал указатель 0x0000FFFF. «FFFF» – потому что -1, а нули, полагаю, из-за выравнивания. Так как рантайм думал, что получает BSTR, а VB код возвращаемое значение прямо к строке присобачивал, полагаясь на автоматическую конвертацию, то рантайм вызывал BSTR функцию. Функция, чтобы получить реальный адрес строки, вычитала четыре байта (перед массивом у BSTR идёт длина строки), получала 0x0000FFFB, обращалась к этому адресу и благополучно вылетала. Вот такая история невнимательности.

04 Feb 2022

Linda-chan, господи, на что только люди не идут, что б не юзать питон)))

04 Feb 2022

Linda-chan, ну, как минимум, на странные конструкции в даркбейсике

#zlgwd/3 в ответ на /2
05 Feb 2022

кстати, частый вопрос, почему именно -1, а не 1

Так почему же? Не томи!

05 Feb 2022

0x0000 против 0xFFFF же. Хоть там и Signed Short.

#zlgwd/6 в ответ на /5

Добавить пост

Вы можете выбрать до 10 файлов общим размером не более 10 МБ.
Для форматирования текста используется Markdown.