Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Общие вопросы Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 03.10.2008, 10:14   #1
FaTaL
Участник клуба
 
Аватар для FaTaL
 
Регистрация: 09.11.2007
Сообщений: 1,762
По умолчанию Явная загрузка DLL

Пытаюсь явно загрузить DLL и выполнить функцию, но либо выдает ошибку Acess Volation, либо считает неправильно. Может я что забыл?
Код DLL
Код:
library Summ;

uses
  SysUtils,
  Classes;

function Summa (x:integer; y:integer):integer; stdcall;
begin
  result:=x+y;
end;

exports Summa;
{$R *.res}

begin
end.
Код программы:
Код:
unit Proga;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;

type
  TForm1 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
var
dll : THandle;
Sum : function (x:integer; y:integer):integer;
begin
  @Sum:=nil;
  dll:=LoadLibrary('Summ');
  if dll<>0 then
    begin
      @Sum:=GetProcAddress(dll,'Summa');
      if @Sum<>nil then
        begin
          ShowMessage(IntToStr(Sum(5,2)));
        end else
        begin
          ShowMessage('Функция не найдена');
          exit;
        end;
    end else
    begin
      ShowMessage('DLL не найдена');
      exit;
    end;
end;

end.
FaTaL вне форума Ответить с цитированием
Старый 03.10.2008, 10:22   #2
_SERGEYX_
Участник клуба
 
Аватар для _SERGEYX_
 
Регистрация: 07.07.2007
Сообщений: 1,518
По умолчанию

Добавь
function Summa (x:integer; y:integer):integer; external 'Summ.dll';
_SERGEYX_ вне форума Ответить с цитированием
Старый 03.10.2008, 10:59   #3
alexBlack
Участник клуба
 
Регистрация: 12.10.2007
Сообщений: 1,204
По умолчанию

Цитата:
Сообщение от FaTaL Посмотреть сообщение
Пытаюсь явно загрузить DLL и выполнить функцию, но либо выдает ошибку Acess Volation, либо считает неправильно. Может я что забыл?

Код:
var dll : THandle;
    Sum : function (x:integer; y:integer):integer; stdcall;   // <- добавить stdcall как в dll
begin
  Sum:=nil;
  dll:=LoadLibrary('Summ');
  if dll<>0 then begin
     Sum := GetProcAddress(dll,'Summa');
     if @Sum <> nil then begin           
        ShowMessage(IntToStr(Sum(5,2)));
     end else begin
        ShowMessage('Функция не найдена');
        exit;
     end;
  end else begin
     ShowMessage('DLL не найдена');
     exit;
  end;
end;
2_SERGEYX_ . Тогда будет статическая загрузка, а ему нужно динамическую.

Последний раз редактировалось alexBlack; 03.10.2008 в 11:08.
alexBlack вне форума Ответить с цитированием
Старый 03.10.2008, 11:11   #4
FaTaL
Участник клуба
 
Аватар для FaTaL
 
Регистрация: 09.11.2007
Сообщений: 1,762
По умолчанию

Цитата:
Сообщение от alexBlack Посмотреть сообщение
Код:
var dll : THandle;
    Sum : function (x:integer; y:integer):integer; stdcall;   // <- добавить stdcall как в dll
begin
  Sum:=nil;
  dll:=LoadLibrary('Summ');
  if dll<>0 then begin
     Sum := GetProcAddress(dll,'Summa');
     if @Sum <> nil then begin           
        ShowMessage(IntToStr(Sum(5,2)));
     end else begin
        ShowMessage('Функция не найдена');
        exit;
     end;
  end else begin
     ShowMessage('DLL не найдена');
     exit;
  end;
end;
2_SERGEYX_ . Тогда будет статическая загрузка, а ему нужно динамическую.
Спасибо. Вон он что оказывается забыл
FaTaL вне форума Ответить с цитированием
Старый 03.10.2008, 11:30   #5
FaTaL
Участник клуба
 
Аватар для FaTaL
 
Регистрация: 09.11.2007
Сообщений: 1,762
По умолчанию

И ещё вопросик. Если DLL загружать по пути вот так
Код:
dll:=LoadLibrary(ExtractFilePath(ParamStr(0))+'Summ');
То компилятор выдает ошибку
[DCC Error] Proga.pas(32): E2010 Incompatible types: 'string' and 'PWideChar'

Как исправить?
FaTaL вне форума Ответить с цитированием
Старый 03.10.2008, 12:27   #6
alexBlack
Участник клуба
 
Регистрация: 12.10.2007
Сообщений: 1,204
По умолчанию

Вообще-то простое приведение:

dll:=LoadLibrary(PChar(ExtractFileP ath(ParamStr(0))+'Summ'));

только почему PWidePchar ? Должно быть PAnsiChar. Вы используете LoadLibraryW ?
тогда:

Код:
    S : WideString;
begin

  S := ExtractFilePath(ParamStr(0))+'Summ';
  dll:=LoadLibraryW(PWideChar(S));
alexBlack вне форума Ответить с цитированием
Старый 03.10.2008, 12:52   #7
FaTaL
Участник клуба
 
Аватар для FaTaL
 
Регистрация: 09.11.2007
Сообщений: 1,762
По умолчанию

Цитата:
Вы используете LoadLibraryW ?
Нет.
Цитата:
S : WideString;
begin

S := ExtractFilePath(ParamStr(0))+'Summ' ;
dll:=LoadLibraryW(PWideChar(S));
Сделал так, тоже работает.
dll:=LoadLibrary(PWideChar(ExtractF ilePath(ParamStr(0))+'Summ'));

Спасибо.
FaTaL вне форума Ответить с цитированием
Старый 08.10.2008, 13:05   #8
FaTaL
Участник клуба
 
Аватар для FaTaL
 
Регистрация: 09.11.2007
Сообщений: 1,762
По умолчанию

Ещё одни вопросик. Не начинал новую тему, потому что в принципе и в эту тему подходит.
Есть DLL с экпортируемой процедурой:
Код:
procedure FileSearch(FromPath:String; ToPath:String); StdCall;
Что дальше она делает не столь важно, скажу что ей нужны пути (происходит копирование).

Когда я её вызываю так, то всё нормально работает:
Код:
procedure TForm1.Button1Click(Sender: TObject);
var
Run  : procedure (FromPath:String; ToPath:String); StdCall;
DLL : THandle;
begin
Dll:=LoadLibrary('Copy.dll');
      if DLL=0 then
        begin
          ShowMessage('DLL не найдена');
          exit;
        end else
        begin
          @Run:=GetProcAddress(DLL,'FileSearch');
          if @Run<>nil then
            begin
              Run('C:\Archiv\','C:\Arch22222\');
            end else
            ShowMessage ('Функция не найдена');
        end;

end;
Но когда её вызываю ещё через другую процедуру, она не пашет:
Сама процедура вызова:
Код:
procedure CallDll (FFrom:String; TTo:String);
var
DLL : THandle;
Run : procedure (FromPath:String; ToPath:String); StdCall;
begin
  DLL:=LoadLibrary('Copy.dll');
  If DLL<>0 then
    begin
      @Run:=GetProcAddress(DLL, 'FileSearch');
      If @Run<>nil then
        begin
          Run(FFrom,TTo);
        end else
         MessageBox(Application.Handle, 'Нужная функция не найдена', 'Ошибка', mb_OK or mb_IconError);
    end else
    MessageBox(Application.Handle, 'Не найдена библиотека Copy.dll', 'Ошибка', mb_OK or mb_IconError);
  FreeLibrary(DLL);
end;
Вызов процедуры вызова:
Код:
CallDLL('C:\Archiv\','C:\Arch22222\'));
В чем может быть проблема?

Последний раз редактировалось FaTaL; 08.10.2008 в 13:08.
FaTaL вне форума Ответить с цитированием
Старый 08.10.2008, 13:10   #9
alexBlack
Участник клуба
 
Регистрация: 12.10.2007
Сообщений: 1,204
По умолчанию

В первом случае -
Run('C:\Archiv\','C:\Arch22222\');

нет распределения памяти под строки. Во втором - есть.
Возможно ShareMem не подключен или не первый в списке uses.
alexBlack вне форума Ответить с цитированием
Старый 08.10.2008, 13:24   #10
FaTaL
Участник клуба
 
Аватар для FaTaL
 
Регистрация: 09.11.2007
Сообщений: 1,762
По умолчанию

Цитата:
Сообщение от alexBlack Посмотреть сообщение
В первом случае -
Run('C:\Archiv\','C:\Arch22222\');

нет распределения памяти под строки. Во втором - есть.
Возможно ShareMem не подключен или не первый в списке uses.
И как это решить?
FaTaL вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Загрузка Witaliy PHP 3 12.07.2008 18:06
Предварительная загрузка GAGARIN-NEW JavaScript, Ajax 10 26.11.2007 22:55
Загрузка ЦП HelloZAPOR Win Api 7 05.11.2007 15:43
Загрузка UnD)eaD)Snake Общие вопросы Delphi 10 19.08.2007 11:24
Загрузка DLL Hollander Общие вопросы Delphi 3 21.05.2007 20:19