Форум: "Прочее";
Текущий архив: 2013.06.16;
Скачать: [xml.tar.bz2];
ВнизОтладка VCL удаленно Найти похожие ветки
← →
Pit (2013-02-06 11:03) [0]Проблема - у одного клиента возникает стабильно EAccessViolation внутрях VCL, где-то внутри ADO, видимо.
Нужно разобраться конкретнее в проблеме - кто что посоветует? Можно собрать дебажную версию (выполнено в виде DLL для 1C) и прогнать у клиента.
Есть еврика, правда с ней проблема. Собрал DLL под евриков, все EAaccessViolation указал писать в лог (это по-умолчанию собственно), так вот прогнал - получил AV точно, а нигде лога еврики не видно, почему она ничего не вывела - непонятно.
Вот такая вот ситуация немного сумбурно описанная мной )
← →
sniknik © (2013-02-06 11:26) [1]> где-то внутри ADO
и не надейся...
> почему она ничего не вывела - непонятно.
может потому, что она ловит внутри кода, а ошибка "снаружи"? вне "защищаемого" ей кода, ну, например на взаимодействии 1С-а с твоей dll.
← →
Pit (2013-02-06 11:45) [2]подожди, я говорю же - исключение поднимается где-то внутри VCL, причем тут "снаружи".
Конкретно - есть вызов:try
[DataSetExample].LoadFromFile(...)
except on E: Exception do
Вывод в лог...
вот так вот я ловлю исключение и вижу его в логе. Но мне нужно подробнее разобраться где внутрях VCL оно возникает...
← →
Ega23 © (2013-02-06 11:58) [3]
> Проблема - у одного клиента возникает стабильно EAccessViolation
> внутрях VCL
Ты клиенту ПО с Delphi поставляешь? Оригинально...
← →
Pit (2013-02-06 12:03) [4]
> Ты клиенту ПО с Delphi поставляешь?
откуда такой вывод?! Я фигею...
Товарищи, давайте по теме)
← →
RWolf © (2013-02-06 12:07) [5]
> Можно собрать дебажную версию (выполнено в виде DLL для
> 1C) и прогнать у клиента.
а подключиться к ней через Remote Debugging можно?
← →
Pit (2013-02-06 12:08) [6]
> а подключиться к ней через Remote Debugging можно?
очень сложно осуществить. Там рабочий процесс, поэтому какой-никакой опыт поставить можно, но вот сидеть прыгать отладчиком - не получиться.
← →
sniknik © (2013-02-06 12:18) [7]> я говорю же - исключение поднимается где-то внутри VCL, причем тут "снаружи".
ты говоришь свои выводы без объяснений почему так решил, если бы твои выводы были 100% верными, настолько, что сказал значит так и есть. то не было бы последующих вопросов.
> Конкретно - есть вызов:
если ловится, в конкретном месте конкретным трай экцептом то не понятно в чем вообще проблема... оно найдено, осталось решить от чего. а для этого нужна инфа - код из этого трай экцепта и что точно говорит (там же даже инфа для поиска строки на которой вылетает в эксепте есть ... нафига вообще усложнять приплетать еврику и т.д.)
← →
sniknik © (2013-02-06 12:22) [8]>> Ты клиенту ПО с Delphi поставляешь?
> откуда такой вывод?! Я фигею...
VCL это код дельфи, если клиент видит, что ошибка именно в VCL... вывод очевиден.
← →
alexdn © (2013-02-06 12:24) [9]> Pit (06.02.13 11:03)
Т.е. он пишет только общую ошибку AaccessViolation такая то? Если ado, то конечно подключение/доступ. Как самый глупый способ пересобрать проект (если есть возможность) и расставить флажки (ну на этапы). Типа этап первый пройден, этап второй пройден ну и т.д.. Хотя конечно лучше теоретически найти ошибку.
← →
sniknik © (2013-02-06 12:35) [10]http://www.gunsmoker.ru/2009/05/access-violation.html
← →
Inovet © (2013-02-06 12:41) [11]А нельзя взять бэкап базы и промоделировать у себя?
← →
Pit (2013-02-06 12:45) [12]
> ты говоришь свои выводы без объяснений почему так решил
потому что я ловлю ошибку на вызове VCL кода. Приводил пример выше:try
[DataSetExample].LoadFromFile(...)
except on E: Exception do
Вывод в лог...
> чего. а для этого нужна инфа - код из этого трай экцепта
> и что точно говорит (там же даже инфа для поиска строки
> на которой вылетает в эксепте есть ... нафига вообще усложнять
> приплетать еврику и т.д.)
я же вроде сразу написал несколько раз - это Access Violation. Текст типа такого:Access violation at address 0F63BAE6 in module "MY_MOD~1.DLL". Read of address 00000008
Это Exception.Message
Собственно, какие-то вывода по данному сообщению сделать сложно, имхо.
> VCL это код дельфи, если клиент видит, что ошибка именно
> в VCL... вывод очевиден.
причем тут клиент. Это я вижу по логу
> http://www.gunsmoker.ru/2009/05/access-violation.html
не понимаю как это статья мне может помочь.
По-моему, не все внимательно прочитали заглавное сообщение темы.
← →
Pit (2013-02-06 12:47) [13]
> А нельзя взять бэкап базы и промоделировать у себя?
промоделировать нельзя, я же говорю. На моем компе ошибка не возникает.
Я показываю, что ошибка возникает на LoadFromFile у датасета. Даже если подсунуть тот же файл - на моем компе ошибки НЕ возникает.
← →
Rouse_ © (2013-02-06 12:48) [14]В логе выводи адрес исключения и hInstans библиотеки.
Вычтя из первого второе получишь оффсет в рамках своего модуля.
Загрузи библиотеку у себя, прибавь к новому инстансу полученный оффсет, поставь дам бряк, жди пока сработает - анализируй.
← →
sniknik © (2013-02-06 12:51) [15]> Это Exception.Message
тебе перевести? - Access violation at address 0F63BAE6 in module "MY_MOD~1.DLL". Read of address 00000008
если это вот именно та строка что показана, то у тебя DataSetExample не инициализирован.
> По-моему, не все внимательно прочитали заглавное сообщение темы.
по моему ты статью/комментарии вообще не читал.
← →
Rouse_ © (2013-02-06 12:51) [16]ЗЫ: а вообще судя по коду ошибки происходит обращение к полям обниленного объекта.
← →
sniknik © (2013-02-06 12:54) [17]> Я показываю, что ошибка возникает на LoadFromFile у датасета.
я сильно сомневаюсь, что виноват именно LoadFromFile... и тебе советую смотреть не на него но рядом.
← →
sniknik © (2013-02-06 13:14) [18]> не понимаю как это статья мне может помочь.
статья -
... Если ZZZ мало, то у вас идёт обращение по ссылке равной nil. ... В первом случае вам нужно искать, зачем же вы полезли по ссылке равной nil (или кто же освободил переменную раньше времени).
сам с удовольствием почитал...
← →
Pit (2013-02-06 13:14) [19]
> то у тебя DataSetExample не инициализирован.
> а вообще судя по коду ошибки происходит обращение к полям
> обниленного объекта.
а как вы это определили?
> Read of address 00000008
?
Типа объект nil, берется значение какого-то поля по смещению $08?
Ну логично, конечно, но ведь это и может быть обращение к какому-то совсем смежному объекту, в том числе обниленному. То есть, например, поле в виде объекта не инициализировано...
Сейчас проверим
← →
Pit (2013-02-06 13:16) [20]
> поставь дам бряк, жди пока сработает
а где ставится бряк по адресу?
← →
Pit (2013-02-06 13:18) [21]
> а где ставится бряк по адресу?
нашел, так и называется видимо: Address Breakpoint
← →
Rouse_ © (2013-02-06 13:22) [22]
> Ну логично, конечно, но ведь это и может быть обращение
> к какому-то совсем смежному объекту, в том числе обниленному.
Ну а какая разница? Объект то по любому обнилен, не важно смежный он или нет.
> Address Breakpoint
Угу, через него, но можно и проще. F7, переходим в CPU-View, там Ctrl+G, вбиваем требуемый адрес, ставим бряк.
← →
Pit (2013-02-06 13:27) [23]
> Ну а какая разница? Объект то по любому обнилен, не важно
> смежный он или нет.
важно. У меня же попадает в функцию ссылку на датасет. То есть, код аля:procedure fillData(ds: TCustomADODataSet);
begin
bla bla bla...
ds.LoadFromFile(xxx);
bla bla bla...
end;
Все таки проверить ds на то, что он не nil - можно и, видимо, нужно. А вот проверить все его поля на валидность - уже перебор, имхо. Это уже должен быть контроль внутри VCL, имхо.
← →
Pit (2013-02-06 13:28) [24]
> переходим в CPU-View, там Ctrl+G, вбиваем требуемый адрес,
> ставим бряк.
а если поставить на данные - будет срабатывать BP при считывании этой переменной?
← →
Rouse_ © (2013-02-06 13:41) [25]На данные работает через установку PAGE_GUARD, т.е. бряк поднимется в случае если произойдет запись по адресу переменной.
грубо если переменная TEST была обнилена и бы выставляешь бряк на данные по ее адресу, то бряк сработает в том случае когда он изменит значение с NIL на что-то другое. Т.е. только при записи.
На чтение меморибряки в дельфи почему-то не реализованы.
← →
Rouse_ © (2013-02-06 13:43) [26]зы: точнее в дельфи реализовано только PAGE_READ (а не более правильный PAGE_GUARD) чтобы отслеживать исключение при записи
← →
Pit (2013-02-06 13:52) [27]
> очнее в дельфи реализовано только PAGE_READ
судя по твоему же описанию логично было бы назвать это PAGE_WRITE )
← →
Pit (2013-02-06 13:55) [28]не, сам датасет задан, провел тест...
Pointer i_DataSet: 605665708
То есть перед вызовом LoadFromFile значение указателя было: 605665708
так что это какие-то внутренние структуры или типа того...
← →
Ega23 © (2013-02-06 14:13) [29]
> Все таки проверить ds на то, что он не nil - можно и, видимо,
> нужно. А вот проверить все его поля на валидность - уже
> перебор, имхо. Это уже должен быть контроль внутри VCL,
> имхо.
Это может ничего не дать:var
ds: TCustomADODataSet;
begin
ds := TCustomADODataSet.Create(nil);
try
/// bla-bla-bla
finally
ds.Free;
end;
FillData(ds);
end;
Ищи утечку памяти.
> А вот проверить все его поля на валидность - уже перебор,
> имхо. Это уже должен быть контроль внутри VCL, имхо.
VCL не очень хорошо с ADO работает. Точнее, работал в своё время. Как сейчас - ХЗ, но судя по тому, что проблему с BCD они так и не исправили, то также не очень хорошо работает. Лично я всегда даже параметры вручную добавлял, ибо напарывался несколько раз на ерунду.
← →
sniknik © (2013-02-06 14:13) [30]> Это уже должен быть контроль внутри VCL, имхо.
ошибка не в нем. не ИМХО.
> так что это какие-то внутренние структуры или типа того...
скорее твои обработчики событий или типа того...
p.s. но вообще, нафиг, партизан не разговорчивый/и не доверчивый попался, толку в "обсуждении" нет.
← →
Ega23 © (2013-02-06 14:15) [31]
> партизан не разговорчивый/и не доверчивый
Дык фирменный стиль же!
- Как сделать ХХХ?
- Вот так-то и так-то.
- Нет, так делать нельзя, надо делать вот так вот и вот так.
А нафига тогда спрашивать вообще?
← →
sniknik © (2013-02-06 14:15) [32]> что проблему с BCD они так и не исправили
его нет. есть тип "деньги". с ним работает правильно (но неожиданно, если ожидаешь BCD).
← →
Ega23 © (2013-02-06 14:21) [33]
> его нет. есть тип "деньги". с ним работает правильно (но
> неожиданно, если ожидаешь BCD).
А numeric, он как?
Чёрт, давно я не ковырялся, надо поставить какой-нить MSSQL поиграццо, что-ли...
← →
Rouse_ © (2013-02-06 14:22) [34]
> Pit (06.02.13 13:52) [27]
>
> > очнее в дельфи реализовано только PAGE_READ
>
> судя по твоему же описанию логично было бы назвать это PAGE_WRITE
Такой флаг не существует PAGE_WRITE. Т.е. нельзя разрешить писать, запретив при этом читать. Для этого как раз и используют комбинацию PAGE_GUARD где проверяют тип исключение - при чтении или при записи.
> То есть перед вызовом LoadFromFile значение указателя было:
> 605665708
ну для теста проверь все поля на клиенте и выведи тоже в лог, а то гадание на кофейной гуще получается.
← →
sniknik © (2013-02-06 14:23) [35]> А numeric, он как?
также. все через "деньги". во всяком случае до D7 включительно, дальше может поменяли и реальный BCD ввели.
← →
Ega23 © (2013-02-06 14:30) [36]
> также. все через "деньги". во всяком случае до D7 включительно,
> дальше может поменяли и реальный BCD ввели.
>
Вот я, фактически, на D7 c ADO работу и закончил. Но кто-то мне говорил (Димка Тимохов, вроде), что с numeric так до сих пор и никак.
Впрочем, это уже оффтоп.
← →
Pit (2013-02-06 15:15) [37]
> скорее твои обработчики событий или типа того...
ни одного обработчика на DataSet не назначено.
← →
sniknik © (2013-02-06 15:23) [38]> ни одного обработчика на DataSet не назначено.
рад за тебя.
← →
Pit (2013-02-06 15:46) [39]Блин, как же геморно так отлаживать...
Я модифицировал ADODB, DB немного и вот что вышло по логам.> procedure TCustomADODataSet.LoadFromFile(const FileName: WideString);
Close;
CommandType := cmdFile;
LockType := ltBatchOptimistic;
CommandText := FileName;
Open; // <--- ЗДЕСЬ
здесь исключение возникает на вызове Open.
Рассмотрим:> procedure TDataSet.SetActive(Value: Boolean);
begin
if (csReading in ComponentState) then
begin
FStreamedActive := Value;
end
else
if Active <> Value then
begin
if Value then
begin
DoBeforeOpen;
try
OpenCursor;
finally
if State <> dsOpening then
OpenCursorComplete; // < ----- ЗДЕСЬ
end;
end else
begin
if not (csDestroying in ComponentState) then DoBeforeClose;
SetState(dsInactive);
CloseCursor;
if not (csDestroying in ComponentState) then DoAfterClose;
end;
end;
end;
Здесь исключение на строчке: OpenCursorComplete
Дальше логирования не делал. Но видно, что внутрях OpenCursorComplete где-то еще несколько раз вызывается SetActive, который не отрабатывает (передается Value равное уже установленному), но один раз исполняется блок:if not (csDestroying in ComponentState) then DoBeforeClose;
SetState(dsInactive);
CloseCursor;
if not (csDestroying in ComponentState) then DoAfterClose;
То есть, соответствующийSetActive(False)
В результате из первого вызова OpenCursorComplete так и вылетает с AV, которое поднимается все дальше и выше, которое я уже и ловил в программе (точнее, модуле DLL).
← →
Ega23 © (2013-02-06 15:56) [40]Ты бы в первую очередь версию OLEDB проверил.
Страницы: 1 2 вся ветка
Форум: "Прочее";
Текущий архив: 2013.06.16;
Скачать: [xml.tar.bz2];
Память: 0.56 MB
Время: 0.004 c