Отладка DLL

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

Отладка DLL

Сообщение Alex. S » 21.02.2016 14:07:06

Здравствуйте.

Написал DLL библиотеку и программу (которая будет её использовать через статическую линковку) в Lazarus'е. Пытаюсь протестировать dll, добавив в параметрах запуска свою программу, которую я переместил в папку dll проекта. Однако, когда я запускаю dll проект, появляется окно программы, но при нажатии кнопки в окне, которая вызывает функцию из dll не происходит остановка программы, хотя breakpoint стоит в начале этой функции :(

Подскажите, почему такое может быть?
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

Re: Отладка DLL

Сообщение Sharfik » 21.02.2016 14:41:12

Alex. S писал(а): Пытаюсь протестировать dll, добавив в параметрах запуска свою программу, которую я переместил в папку dll проекта.

Параметр называется "Главное приложение" ?
Аватара пользователя
Sharfik
энтузиаст
 
Сообщения: 809
Зарегистрирован: 20.07.2013 01:04:30

Re: Отладка DLL

Сообщение Alex. S » 21.02.2016 14:54:29

Sharfik, да.
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

Re: Отладка DLL

Сообщение Sharfik » 21.02.2016 15:04:01

У меня работает такое, но использую динамическую линковку.
Попробуй динамически обратится, может в этом дело.
Аватара пользователя
Sharfik
энтузиаст
 
Сообщения: 809
Зарегистрирован: 20.07.2013 01:04:30

Re: Отладка DLL

Сообщение Alex. S » 21.02.2016 16:01:35

Пробовал динамически, тоже безуспешно.

Sharfik, не можете скинуть пустой dll-проект, который у Вас успешно проходит отладку?

P.S. Передаю в процедуру из dll массив как переменную, заполняю его в dll, в итоге: External "SIGSEGV".

Частичный код DLL:
Код: Выделить всё
...
TDWordArray = array of Cardinal;
...
procedure GetData(var Data: TDWordArray);
begin
//
SetLength(Data, 1);
//
Data[0]:=5;
end;


Код программы:

Код: Выделить всё
...
procedure GetData(Data: TDWordArray); external 'MyDLL.dll';
...
var
//
i, k: Cardinal;
//
Data: TDWordArray;
begin
//
GetData(Data);

//
k:=Length(Data);
//
if k > 0 then
  begin
  //
  Dec(k);

  //
  for i:=0 to k do
  //
  ShowMessage(IntToStr(Data[i]));
  end;
end.
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

Re: Отладка DLL

Сообщение vitaly_l » 21.02.2016 17:18:12

Alex. S писал(а):Частичный код DLL: Код программы:

Попробуйте название: GetData, переименовать на GetDataTest.
Есть предположение, что у Вас получается рекурсия и валит программу.


.
Аватара пользователя
vitaly_l
долгожитель
 
Сообщения: 3333
Зарегистрирован: 31.01.2012 16:41:41

Re: Отладка DLL

Сообщение Alex. S » 21.02.2016 18:20:24

vitaly_l, в реальности, вместо GetData используется другое название, это я использовал доя тестирования...

По поводу рекурсии, я её тут не вижу. Если вместо массива, передать простую переменную, и присвоить ей значение в процедуре GetData, то всё нормально работает...
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

Re: Отладка DLL

Сообщение vitaly_l » 21.02.2016 18:44:35

Alex. S писал(а):По поводу рекурсии, я её тут не вижу.

А по моему это вечный цикл:
Код: Выделить всё
procedure GetData(Data: TDWordArray); external 'MyDLL.dll';
var
Data: TDWordArray;
begin
//
GetData(Data); <==== вот она, рекурсия. Процедура ссылается на саму себя.

// Всё! <== дальше - программа, никогда не перейдёт, т.к. вызовется GetData(Data); ,
// которая дойдёт до предыдущей строки GetData(Data); и снова вызовет GetData(Data);
и так до бесконечности, пока не закончится память, допустимое значение вариантов или бсода.



Впрочем я могу заблуждаться, если Вы привели не точный код.


.
Аватара пользователя
vitaly_l
долгожитель
 
Сообщения: 3333
Зарегистрирован: 31.01.2012 16:41:41

Re: Отладка DLL

Сообщение Alex. S » 21.02.2016 18:56:52

vitaly_l, это не рекурсия, это я так отформатировал код, не совсем понятно :)

Код: Выделить всё
procedure GetData(Data: TDWordArray); external 'MyDLL.dll';

Это импорт процедуру из dll в программе.

Код: Выделить всё
var
//
i, k: Cardinal;
//
Data: TDWordArray;
begin
//
GetData(Data);

//
k:=Length(Data);
//
if k > 0 then
  begin
  //
  Dec(k);

  //
  for i:=0 to k do
  //
  ShowMessage(IntToStr(Data[i]));
  end;
end.


А это уже код программы, который выполняется при её запуске.

Извините, что ввёл Вас в заблуждение.

Проверил, если заменить тип переменной Data с TDWordArray на Cardinal в программе и в dll, и просто присвоить значение этой переменной, в процедуру GetData, то программа выполняется без ошибок. А вот если, передавать уже массив, и обрабатывать его, будет ошибка :(
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

Re: Отладка DLL

Сообщение vitaly_l » 21.02.2016 19:11:00

У Вас два раза вот это объявлено: Data: TDWordArray; обычно Лазарус на такое ругается, до компиляции.
там где VAR, делайте: var DataX: TDWordArray; Получится: GetData(DataX); (либо Data второй раз не объявляйте)



.
Аватара пользователя
vitaly_l
долгожитель
 
Сообщения: 3333
Зарегистрирован: 31.01.2012 16:41:41

Re: Отладка DLL

Сообщение Alex. S » 21.02.2016 19:20:34

vitaly_l, это только в тестовом коде, я упростил код программы, так как он слишком громоздкий, переписав с него только тот участок, где происходит ошибка.

Сейчас вот ещё заметил, что если установить размер массива Data в программе, а в dll устанавливать только значения для массива, ошибки тоже не будет...
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

Re: Отладка DLL

Сообщение Sharfik » 21.02.2016 20:26:54

Такой вариант работает.
Код: Выделить всё
library edt_cablelaying;

{$mode objfpc}{$H+}

uses
  windows, Classes, SysUtils, FileUtil, Interfaces,
  Forms, Controls, Graphics, Dialogs;

const
  PackageName               = 'Plugin';
  PackageAuthor             = 'My';
  PackageVersion            = '0.4';
  PackageLic                = 'Freeware';
  PackageMenuCaption        = 'Прокладка кабелей';
  PackageLibName            = 'edt_cablelaying.dll';

//var
  //ThisApp                  :TCustomAssiApp;

function PluginInit(AppClass: Pointer):Boolean; stdcall;
begin
    //проверки
    //ThisApp :=TCustomAssiApp((AppClass);
    Result    :=True;
end;

procedure PluginDeinit(AppClass: Pointer); stdcall;
begin

end;

procedure PluginProjectInit(AppClass: Pointer;AStr:WideString); stdcall;
begin

end;

procedure PluginProjectDeinit(AppClass: Pointer;AStr:WideString); stdcall;
begin

end;

function PluginType: WideString; stdcall;
begin
   //PT_EDITFORM        - Редактор с формой
   Result:=  PT_EDITFORM;
end;

function PluginName: WideString; stdcall;
begin
     Result:=  Utf8ToAnsi(PackageName);
end;

function PluginMenuCaption: WideString; stdcall;
begin
     Result:=  Utf8ToAnsi(PackageMenuCaption);
end;

function PluginAuthor: WideString; stdcall;
begin
     Result:=  Utf8ToAnsi(PackageAuthor);
end;

function PluginVersion: WideString; stdcall;
begin
     Result:=  PackageVersion;
end;

function PluginLicense: WideString; stdcall;
begin
     Result:= Utf8ToAnsi(PackageLicDescriptionStr);
end;

function PluginWindow: Pointer; stdcall;
begin
  Result := nil;
  if Assigned(ThisApp) then
  begin

  //Процедура вызывается если PluginType возвращает PT_EDITFORM, PT_EXPORTIMPORT
  end;
end;

exports
        PluginInit            name 'PluginInit',
        PluginDeinit          name 'PluginDeinit',
        PluginProjectInit     name 'ProjectInit',
        PluginProjectDeinit   name 'ProjectDeinit',
        PluginType            name 'PluginType',
        PluginName            name 'PluginName',
        PluginAuthor          name 'PluginAuthor',
        PluginVersion         name 'PluginVersion',
        PluginLicense         name 'PluginLicense',
        PluginWindow          name 'PluginWindow',
        PluginMenuCaption     name 'PluginMenuCaption';

{$R *.res}

begin
  Application.Initialize;
end.
Аватара пользователя
Sharfik
энтузиаст
 
Сообщения: 809
Зарегистрирован: 20.07.2013 01:04:30

Re: Отладка DLL

Сообщение Alex. S » 21.02.2016 20:43:12

Sharfik, спасибо, буду тестировать :)
А в программе у вас mode ObjFPC, или Delphi?

У меня, с динамической линковкой не получается собрать при mode ObjFPC, строка
Код: Выделить всё
@some_proc:=getProcAddress(DLLHandle, 'proc_name');


не хочет компилироваться.
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

Re: Отладка DLL

Сообщение Sharfik » 21.02.2016 20:54:47

Там mode ObjFPC
Код: Выделить всё
function TFLauncher.LoadPlugin(Filename: String): Boolean;
var
  PluginPath   :PChar;
  newPlugin    :TPluginItem;
  PluginCorrect:Boolean;
  DLLHandle    :THandle;
  sResult      :WideString;
  i            :Integer;
begin
  try
    PluginCorrect:=true;
    Result:=false;
    // загружаем dll динамически
    PluginPath:=pchar(UTF8ToSys(Filename));
    DLLHandle := loadLibrary (PluginPath);
    if DLLHandle > 32 then
    begin
      newPlugin :=TPluginItem.Create;
      newPlugin.LibHandle:=DLLHandle;

      newPlugin.PluginFileName       :=Filename;
      newPlugin.faRun                :=GetProcAddress( DLLHandle, 'PluginRun');
      newPlugin.faWindow             :=GetProcAddress( DLLHandle, 'PluginWindow');
     ///property faWindow            :Pointer read FPluginWindow
     ///                                                    write FPluginWindow;
      newPlugin.faVersion            :=GetProcAddress( DLLHandle, 'PluginVersion');
      //**

      if newPlugin.faVersion         =nil then PluginCorrect:=false;
      //**
      if newPlugin.faProjectInit     =nil then PluginCorrect:=false;

      if not PluginCorrect then
      begin
        ThisApp.SystemLog('', Format('Плагин %s не загружен. Необходимые ресурсы не найдены.',[ExpandFileNameUTF8(Filename)]));
        newPlugin.Free;
        freeLibrary(DLLHandle);
      end
      else begin
          ThisApp.PluginAdd(newPlugin);
          Result:=true;
      end;
    end
    else begin
      // DLL не найдена
      ThisApp.SystemLog('', Format('Плагин %s не загружен. Не удалось прочитать.',[ExpandFileNameUTF8(Filename)]));
    end;
   
  except
    freeLibrary(DLLHandle);
    if assigned(newPlugin) then newPlugin.Free;
  end;
end;
Аватара пользователя
Sharfik
энтузиаст
 
Сообщения: 809
Зарегистрирован: 20.07.2013 01:04:30

Re: Отладка DLL

Сообщение Alex. S » 21.02.2016 21:09:43

Sharfik, большое спасибо. Буду анализировать, почему у меня не получается :)
Alex. S
новенький
 
Сообщения: 39
Зарегистрирован: 22.08.2015 11:37:00

След.

Вернуться в Lazarus

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 227

Рейтинг@Mail.ru