Гость
Форумы / Firebird, InterBase [игнор отключен] [закрыт для гостей] / Сбой приложения если оно получило SIGINT или SIGTERM / 25 сообщений из 31, страница 1 из 2
02.11.2018, 10:07
    #39727008
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Привет!
Пишу ПО, которое использует FB на Orange Pi Zero (там стоит Linux). Если я посылаю "kill -SIGINT <pid>" своей программе, то она крашится, даже try..except не помогает. Кроме того, программу я запускаю из терминала (я через VNC-клиент захожу на Orange и там использую терминал), и после SIGINT терминал начинает себя странно вести (видимо, тоже где-то память или стек портится). Вот пример простого приложения на Лазаре, в котором проявляется эта ошибка. В нем я ставлю свой обработчик на сигналы типа SIGINT и SIGTERM. Отмечу, что проблема возникает при SIGINT и SIGTERM, а с SIGHUP все норм.
код программы тут
Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
84.
85.
86.
87.
88.
89.
90.
91.
92.
93.
94.
95.
96.
97.
98.
99.
100.
101.
102.
103.
104.
105.
106.
107.
108.
109.
110.
111.
112.
113.
114.
115.
116.
117.
118.
119.
120.
121.
122.
123.
124.
125.
126.
127.
128.
129.
130.
131.
132.
133.
134.
135.
136.
137.
138.
139.
140.
141.
142.
143.
144.
145.
146.
147.
148.
149.
150.
151.
152.
153.
154.
155.
156.
157.
158.
159.
160.
161.
162.
163.
164.
165.
166.
167.
168.
169.
170.
171.
172.
173.
174.
program project1;

{$IFDEF FPC}
  {$MODE objfpc}{$H+}
{$ENDIF}

uses
  {$IFDEF UNIX}{$IFDEF UseCThreads}
  cthreads,
  {$ENDIF}{$ENDIF}
  crt, Classes, sysutils, BaseUnix, dynlibs;

//////////////////////////////////////////
/// FIREBIRD
//////////////////////////////////////////
const
  isc_dpb_version1 = 1;
  isc_dpb_user_name = 28;
  isc_dpb_password = 29;
  isc_dpb_sql_role_name = 60;
  isc_dpb_lc_ctype = 48;

type
  ISC_STATUS    = ptrint;
  UInt                 = DWord;
  Int                  = LongInt;
  PISC_STATUS = ^ISC_STATUS;
  FB_API_HANDLE = pointer;
  isc_db_handle   = FB_API_HANDLE;
  pisc_db_handle  =^isc_db_handle ;

var
  FSQLDatabaseHandle     : pointer;
  FStatus                : array [0..19] of ISC_STATUS;
  LibHandle : TLibHandle;

  fb_shutdown : function(_para1: UINT; _para2: integer):int; cdecl;
  isc_attach_database : function (_para1:PISC_STATUS; _para2:smallint; _para3:Pchar; _para4:Pisc_db_handle; _para5:smallint;_para6:Pchar):ISC_STATUS; cdecl;
  isc_detach_database : function (_para1:PISC_STATUS; _para2:Pisc_db_handle):ISC_STATUS; cdecl;

Function TryInitialiseIBase60(Const LibraryName : AnsiString) : Boolean;
begin
  Result := False;
  LibHandle := LoadLibrary(LibraryName);
  if LibHandle = nilhandle then
    Exit;
  pointer(fb_shutdown) := GetProcedureAddress(LibHandle,'fb_shutdown');
  pointer(isc_attach_database) := GetProcedureAddress(LibHandle,'isc_attach_database');
  pointer(isc_detach_database) := GetProcedureAddress(LibHandle,'isc_detach_database');
  Result := True;
end;

Procedure ReleaseIBase60;
begin
  if LibHandle <> NilHandle then
  begin
    // Shutdown embedded subsystem with timeout 300ms (Firebird 2.5+)
    // Required before unloading library; has no effect on non-embedded client
    if (pointer(fb_shutdown)<>nil) and (fb_shutdown(300,1)<>0) then
    begin
     //todo: log error; still try to unload library below as the timeout may have been insufficient
    end;
    if UnloadLibrary(LibHandle) then
      LibHandle := NilHandle;
  end;
end;

procedure ConnectFB(const UserName, Password, Role, CharSet, HostName, DatabaseName: string);
var
  ADatabaseName: String;
  DPB: string;
begin
  DPB := chr(isc_dpb_version1);
  if (UserName <> '') then
  begin
    DPB := DPB + chr(isc_dpb_user_name) + chr(Length(UserName)) + UserName;
    if (Password <> '') then
      DPB := DPB + chr(isc_dpb_password) + chr(Length(Password)) + Password;
  end;
  if (Role <> '') then
     DPB := DPB + chr(isc_dpb_sql_role_name) + chr(Length(Role)) + Role;
  if Length(CharSet) > 0 then
    DPB := DPB + Chr(isc_dpb_lc_ctype) + Chr(Length(CharSet)) + CharSet;

  FSQLDatabaseHandle := nil;
  if HostName <> '' then
    ADatabaseName := HostName+':'+DatabaseName
  else
    ADatabaseName := DatabaseName;
  if isc_attach_database(@FStatus[0], Length(ADatabaseName), @ADatabaseName[1],
       @FSQLDatabaseHandle, Length(DPB), @DPB[1]) <> 0 then
    if ((FStatus[0] = 1) and (FStatus[1] <> 0)) then
      WriteLn('ConnectFB ErrorCode ', FStatus[1]);
end;

procedure DisconnectFB;
begin
  if isc_detach_database(@FStatus[0], @FSQLDatabaseHandle) <> 0 then
    if ((FStatus[0] = 1) and (FStatus[1] <> 0)) then
      WriteLn('DisconnectFB ErrorCode ', FStatus[1]);
end;

//////////////////////////////////////////
/// SIG HANDLER
//////////////////////////////////////////
var
  terminated: boolean = False;
  new_act_term, new_act_int, new_act_hup, old_act: SigActionRec;

procedure DoSig(signal: longint; info: psiginfo; context: psigcontext); cdecl;
begin
  terminated := True;
end;

procedure SetSigHadnler(const Sig: cint; const new, old: PSigActionRec; const Handler: SigActionHandler);
begin
  new^.sa_handler := Handler;
  fillchar(new^.Sa_Mask, SizeOf(new^.sa_mask), #0);
  new^.sa_flags := 0;
  {$ifdef Linux}               // Linux specific
  new^.Sa_Restorer := nil;
  {$endif}
  fpSigAction(Sig, new, old);
end;

//////////////////////////////////////////
/// MAIN
//////////////////////////////////////////
const
  OS_USER_NAME = ;
begin
  SetSigHadnler(SIGTERM, @new_act_term, @old_act, @DoSig);
  SetSigHadnler(SIGINT, @new_act_int, @old_act, @DoSig);
  SetSigHadnler(SIGHUP, @new_act_hup, @old_act, @DoSig);

  {$if declared(UseHeapTrace)}
  GlobalSkipIfNoLeaks := True; // supported as of debugger version 3.1.1
  {$endif}

  if not TryInitialiseIBase60('libfbclient.so') then
  begin
    WriteLn('ibase lib init failed');
    exit;
  end;
  connectFB('SYSDBA', 'masterkey', '', 'UTF8', '127.0.0.1', '/home/' + OS_USER_NAME + '/EMPLOYEE.FDB');
  if not Assigned(FSQLDatabaseHandle) then
  begin
    WriteLn('db connect failed');
    exit;
  end;

  writeln('start PID:', FpGetPID, '..');
  while not terminated do
  begin
    sleep(250);
    if KeyPressed then
      if ReadKey = ^C then
      begin
        writeln('Ctrl-C pressed');
        Break;
      end;
  end;
  if terminated then
    writeln('terminated');
  writeln('..stop');

  try
    DisconnectFB;
    ReleaseIBase60;
  except
    writeln('exception occured!');
  end;
  writeln('end');
end.


В чем причина такого поведения? Как пофиксить или хотя бы workaround?

DB: Firebird classic 2.5
Device: OrangePi Zero
OS: ARMBIAN 5.35 user-built Ubuntu 16.04.3 LTS 3.4.113-sun8i
...
Рейтинг: 0 / 0
02.11.2018, 13:56
    #39727219
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Дополню: на Ubuntu 18.04 это приложение при SIGINT выдает ошибку "invalid database handle (no active connection)", когда выполняется isc_detach_database. Но почему? Кто уже закрыл соединение?
...
Рейтинг: 0 / 0
02.11.2018, 14:11
    #39727225
hvlad
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
fbclient устанавливает свои обработчики этих сигналов.
Они вызывают fb_shutdown, причём он выполняется в отдельном потоке.

Для начала, нужно смотреть дамп (core) и понять - в каком месте оно падает.
...
Рейтинг: 0 / 0
02.11.2018, 14:21
    #39727229
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Ставь свои обработчики сигналов после инициализации библиотеки.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
02.11.2018, 14:27
    #39727233
hvlad
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
sann-xДополню: на Ubuntu 18.04 это приложение при SIGINT выдает ошибку "invalid database handle (no active connection)", когда выполняется isc_detach_database.Т.е. не падает, всё в порядке ?

sann-xНо почему? Кто уже закрыл соединение?fb_shutdown, см выше
...
Рейтинг: 0 / 0
02.11.2018, 14:34
    #39727236
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
hvladsann-xДополню: на Ubuntu 18.04 это приложение при SIGINT выдает ошибку "invalid database handle (no active connection)", когда выполняется isc_detach_database.Т.е. не падает, всё в порядке ?
Не падает, да. Но там последняя версия из ветки 2.5. А на orange более ранняя 2.5 стоит. Да и не знаю, как сделать gcore процесса, если он уже завершен (упал после попытки закрыть соединение с БД).
...
Рейтинг: 0 / 0
02.11.2018, 14:40
    #39727240
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
sann-xДа и не знаю, как сделать gcore процесса

Попросить об этом систему (ulimit и т.д.).

И лучше убери вызов ReleaseIBase60, а то гонка "кто из под кого выбьет табуретку"
получается обоюдной: если ты выгрузишь библиотеку раньше, чем завершится упомянутый
фоновый поток - он упадёт, если позже - упадёшь ты.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
02.11.2018, 14:42
    #39727242
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Dimitry SibiryakovСтавь свои обработчики сигналов после инициализации библиотеки.

Замечательно! Превосходно! Супер! 3 дня с этим боролся! А все было так просто! Спасибо
...
Рейтинг: 0 / 0
02.11.2018, 14:46
    #39727246
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Dimitry SibiryakovИ лучше убери вызов ReleaseIBase60, а то гонка "кто из под кого выбьет табуретку"
получается обоюдной: если ты выгрузишь библиотеку раньше, чем завершится упомянутый
фоновый поток - он упадёт, если позже - упадёшь ты.

Совсем убрать? Или только в случае, когда придет сигнал типа SIGINT? Да и щас (по совету выше) я устанавливаю свой хэндлер сигналов уже ПОСЛЕ инициализиации библиотеки. Все равно убрать ReleaseIBase60 или как?
...
Рейтинг: 0 / 0
02.11.2018, 14:49
    #39727251
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
sann-xСовсем убрать?

Совсем убери. Ибо поток с shutdown - не единственные грабли на этом поле.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
02.11.2018, 14:55
    #39727254
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Dimitry SibiryakovСовсем убери. Ибо поток с shutdown - не единственные грабли на этом поле.

А файл с моей БД валидный останется, не битый? Тем более тут я выложил тестовый пример, здесь нет смысла убирать. Но в моем приложении, которое я разрабатываю, используются компоненты типа TIBConnection, TSQLQuery и т.д. В TIBConnection внутри идет вызов InitialiseIBase60 и ReleaseIBase60. Как этим быть?
...
Рейтинг: 0 / 0
02.11.2018, 15:13
    #39727264
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
sann-xА файл с моей БД валидный останется, не битый?

Если ты работаешь с сервером, а не в embedded варианте, то всё будет в порядке.

sann-xВ TIBConnection внутри идет вызов InitialiseIBase60 и ReleaseIBase60. Как
этим быть?
Вариантов два: заваливать трекер тикетами о некорректном поведении клиента или забить на
падения/зависания. Есть ещё вариант разбираться индивидуально и самостоятельно править
такие вот косяки, но это долго, муторно и требует квалификации.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
02.11.2018, 15:15
    #39727267
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Dimitry Sibiryakovsann-xА файл с моей БД валидный останется, не битый?

Если ты работаешь с сервером, а не в embedded варианте, то всё будет в порядке.

У меня как раз embedded..
...
Рейтинг: 0 / 0
02.11.2018, 15:16
    #39727270
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
FB classic я поставил после, для тестов, уже когда стал исследовать баг в ПО.
...
Рейтинг: 0 / 0
02.11.2018, 15:35
    #39727278
hvlad
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
sann-xА файл с моей БД валидный останется, не битый?
а) проверяй
б) закрывай явно все коннекты до вызова fb_shutdown
в) ещё проверяй
...
Рейтинг: 0 / 0
02.11.2018, 17:15
    #39727336
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
hvladб) закрывай явно все коннекты до вызова fb_shutdown

Может, стоит написать в трекер, что shutdown из фонового потока не даёт основному
приложению нормально завершить работу с базой?

А то обработчики сигналов безусловно перекрывать это какой-то кривоватый костыль, может,
клиент не только дурью в них мается, но и что-то полезное делает?..
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
02.11.2018, 18:18
    #39727363
hvlad
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Dimitry SibiryakovМожет, стоит написать в трекер, что shutdown из фонового потока не даёт основному
приложению нормально завершить работу с базойОтукуда такие сведения ?

Dimitry Sibiryakovобработчики сигналов безусловно перекрыватьОни разве не вызываются по цепочке ?
...
Рейтинг: 0 / 0
02.11.2018, 18:58
    #39727377
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
hvladDimitry SibiryakovМожет, стоит написать в трекер, что shutdown из фонового потока не даёт основному
приложению нормально завершить работу с базойОтукуда такие сведения ?
Я еще раз проверю после праздников, чтобы точно знать ответ на этот вопрос.

hvladDimitry Sibiryakovобработчики сигналов безусловно перекрыватьОни разве не вызываются по цепочке ?
Код: pascal
1.
fpSigAction(Sig, new, old);


Ф-ция установки обработчика выдает старое значение, но я его игнорирую.
...
Рейтинг: 0 / 0
02.11.2018, 20:11
    #39727416
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
hvladОтукуда такие сведения ?

Из данного топика.

hvladОни разве не вызываются по цепочке ?

Это как запрограммируешь. fbclient их вызывает по цепочке. Приложение ТС-а (и моё) - нет.

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

В противном случае выполняется обработчик в клиенте, потом в приложении, но к моменту
когда приложение не торопясь завершает операцию - шустрый фоновый поток клиента уже убил
всё что мог и приложение получает вышеназванную ошибку.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
02.11.2018, 20:17
    #39727418
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Dimitry SibiryakovВ противном случае выполняется обработчик в клиенте, потом в приложении, но к моменту
когда приложение не торопясь завершает операцию - шустрый фоновый поток клиента уже убил
всё что мог и приложение получает вышеназванную ошибку.

Да, так и происходит.
...
Рейтинг: 0 / 0
03.11.2018, 02:35
    #39727489
hvlad
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
Dimitry Sibiryakovприложение получает вышеназванную ошибку.И чем она ему мешает ?
...
Рейтинг: 0 / 0
03.11.2018, 08:09
    #39727501
sann-x
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
hvladИ чем она ему мешает ?
Мне нужно сохранить работу на диск, когда программа закрывается, иначе данные (могут быть важными для клиента) могут быть потеряны. А ошибка приводит к тому, что даже try except не срабатывает и программа вылетает, не сохранив все до конца.
...
Рейтинг: 0 / 0
03.11.2018, 12:22
    #39727527
hvlad
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
sann-x,

1. fb_shutdown как раз корректно закрывает коннекты и всё сохраняется
2. Не нравится, что клиент автоматом вызывает fb_shutdown ? А почему он это делает ? Так может что-то в консерватории не так ?
3. Программа вылетает на Ubuntu 16.04 и не вылетает на Ubuntu 18.04 но виноват, конечно же, Firebird
...
Рейтинг: 0 / 0
03.11.2018, 13:17
    #39727536
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
hvladИ чем она ему мешает ?
Продолжению работы. Ты не поверишь, но не все программы тупо закрываются по нажатию
Ctrl-C, некоторые считают себя достаточно важными и переспрашивают у пользователя "я ещё
не всё сохранила, ты действительно хочешь наплевать на два дня проделанной работы?"

hvlad1. fb_shutdown как раз корректно закрывает коннекты и всё сохраняется

При этом текущая транзакция откатывается, что несколько противоречит "всё сохраняется".

hvlad2. Не нравится, что клиент автоматом вызывает fb_shutdown ? А почему он это
делает ?
Потому что кое-кто не смог придумать лучшего способа для cleanup. Использовать, как все
люди, destructor-функции, видимо, показалось слишком просто.

hvladТак может что-то в консерватории не так ?
Да. И я даже знаю в чьей именно.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
03.11.2018, 14:09
    #39727561
Dimitry Sibiryakov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Сбой приложения если оно получило SIGINT или SIGTERM
hvlad3. Программа вылетает на Ubuntu 16.04 и не вылетает на Ubuntu 18.04 но виноват, конечно
же, Firebird

Учитывая, что имеют место быть гонки потоков, результат ещё и от фазы Луны зависит. И таки
да, виноват, конечно же, Firebird.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Форумы / Firebird, InterBase [игнор отключен] [закрыт для гостей] / Сбой приложения если оно получило SIGINT или SIGTERM / 25 сообщений из 31, страница 1 из 2
Целевая тема:
Создать новую тему:
Автор:
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]