Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Начинающим";
Текущий архив: 2006.09.17;
Скачать: [xml.tar.bz2];

Вниз

Как правильно вызывать функцию из ДЛЛ?   Найти похожие ветки 

 
alles ©   (2006-08-30 17:22) [0]

Здраствуйте.
Ребята, пожалуста скажите как правильно вызывать функцию из ДЛЛ.
В ДЛЛ имеем
function MessageDetails(FileName:ShortString):TPackageMessageDetails;export; stdcall;
var MessageText:String;
   i,j:integer;
begin
MessageText:=LOADFROMFILE(FileName);
if (Copy(MessageText,i,4)=":21:") then
                                   begin
                                        Inc(Result.NrMessages);
                                        SetLength(Result.IDoc,Result.NrMessages);
                                        Result.IDoc[Result.NrMessages-1]:="";
                                        j:=i+4;
                                        while (MessageText[j]<>":") do
                                                            begin
                                                                 Result.IDoc[Result.NrMessages-1]:=Result.IDoc[Result.NrMessages-1]+MessageText[j];
                                                                 inc(j);
                                                            end;
                                   end;
end;

exports
MessageDetails;


и рекорд

type TPackageMessageDetails=record
    NrMessages:byte;
    IDoc: array of ShortString;
end;


В прожект пишу обьявление функций так
MessageDetails: function (FileName:ShortString):TPackageMessageDetails; stdcall;
Вызываю процедуру из прожекта так

procedure TForm1.btnTestClick(Sender: TObject);
var DLLInstanceRole:THandle;
   a:TPackageMessageDetails;
var I:integer;
begin
DLLInstanceRole := LoadLibrary(PChar(Edit1.Text));
 @MessageDetails := GetProcAddress(DLLInstanceRole, "MessageDetails");
  if Assigned(@MessageDetails)then
              begin
                  a:= MessageDetails("C:\FV12269363.SWF");
                  Showmessage(a.NrMessages);
             end;
FreeLibrary(DLLInstanceRole);
end;


Если убираю эти строчки из функцию ДЛЛ-а то все работает нормально

           SetLength(Result.IDoc,Result.NrMessages);
           Result.IDoc[Result.NrMessages-1]:="";
           j:=i+4;
           while (MessageText[j]<>":") do
             begin
                   Result.IDoc[Result.NrMessages-1]:=Result.IDoc[Result.NrMessages-1]+MessageText[j];
      inc(j);
  end;

то есть как пишу эту строку то прожект показывает сначяло Showmessage(a.NrMessages);
а потом AV
Спасибо


 
han_malign ©   (2006-08-30 17:28) [1]

type TPackageMessageDetails=record
   NrMessages:byte;
   IDoc: array of ShortString;
end;


- на динамические массивы распространяются те же ограничения, что и на "длинные" строки... То бишь - sharemem...


 
alles ©   (2006-08-30 17:36) [2]

2 han_malign ©
скажите плиз как использовать в данном случяе sharemem


 
alles ©   (2006-08-30 17:39) [3]

нашел в справку

Если Вы используете длинные строки как аргументы или результаты для функций, располагающихся в DLL, то в DLL надо использовать модуль ShareMem;
Не используйте длинные строки как члены структур типа record. Используйте там короткие строки или array[0..n] of char. Также нельзя использовать в структурах типа record динамические массивы. Данные ограничения отсутствуют для классов.

где и как испльзовать модуль ShareMem?


 
alles ©   (2006-08-30 17:45) [4]

поставил я в uses sharemem.
Все работает но при закрытий программы пишет invalid pointer operation, но это уже другой вопрос


 
Джо ©   (2006-08-30 18:13) [5]


> alles ©   (30.08.06 17:45) [4]
>
> поставил я в uses sharemem.
> Все работает но при закрытий программы пишет invalid pointer
> operation, но это уже другой вопрос

Его нужно поставить ПЕРВЫМ модулем как в DLL, так и в вызывающей программе (в файле dpr).
Кстати, при распространении программы нужно также поставлять файл borlndmm.dll.

П.С. Интересно, почему никто не читает длинный и подробный комментарий, помещаемый в начало автоматически сгенерированного проекта DLL?


 
DiamondShark ©   (2006-08-30 18:16) [6]


> if (Copy(MessageText,i,4)=":21:")

в этой точке i равно среднесуточной температуре на Марсе за прошлый год в градусах Фаренгейта.

Не знаю, как к этому отнесётся Copy, но, скорее всего, она-таки не вернёт ":21:" в подавляющем большинстве случаев, значит if не выполнится, и Result останется неинициализированным.
Но это ещё пол-беды.

При особо неудачном расположении звёзд тело условного оператора может выполниться.


> Inc(Result.NrMessages);

К счастью, размер в один байт не позволит использовать в качестве значения текущую сумму на счету Била Гейца, выраженную в японских йенах, и оператор

> SetLength(Result.IDoc,Result.NrMessages);

не попытается захватить больше 64кб памяти.


> j:=i+4;
>                                         while (MessageText[j]<>":
> ") do

Хвала Аллаху, вероятность встретить в памяти байт, со значением ":" равна 1/256, а значительная часть ВАП всё-таки доступна для чтения.


> Showmessage(a.NrMessages);

Если это скомпилировалось, то, скорее всего, код компилятора серьёзно повреждён. Стоит попробовать переустановить Дельфи. Возможно, ошибки исчезнут.


 
alles ©   (2006-08-30 18:40) [7]

2 DiamondShark ©   (30.08.06 18:16) [6]
Ну я же не буду писАть весь ДЛЛ сюда
эта строка  
if (Copy(MessageText,i,4)=":21:") находится в цикле
for i:=1 to Length(MessageText) do
А скажите плчему после добавлений шаремем в прожекте и в длл эта строка
Showmessage(a.NrMessages);
возвращяет иероглифы.


 
alles ©   (2006-08-30 18:43) [8]

и что странно: если в ДЛЛ пишу
Showmessage(inttostr(Result.NrMessages));
то показывается как Result.NrMessages растет


 
alles ©   (2006-08-30 19:10) [9]

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


 
medved_68 ©   (2006-08-30 22:32) [10]


> Все работает.

Это плохо!!!!

> Оказывается что если менять хоть чтото в обьявление рекорда
> в длл или в пожект, то тогда все, кирдык

Это хорошо!!!

> Ничего не показывает

Это плохо!!!!

> Всем спасибо

И тебе тоже мил человек!!!!!


 
Германн ©   (2006-08-31 01:41) [11]


> Джо ©   (30.08.06 18:13) [5]
>
...
> П.С. Интересно, почему никто не читает длинный и подробный
> комментарий, помещаемый в начало автоматически сгенерированного
> проекта DLL?
>


Так сей текст на аглицком! А у нас до сих пор "чистят кирпичём"! :-)



Страницы: 1 вся ветка

Форум: "Начинающим";
Текущий архив: 2006.09.17;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.49 MB
Время: 0.048 c
2-1156248788
GTAID
2006-08-22 16:13
2006.09.17
Не сворачиваемое окно!


15-1156046543
PSPF2003
2006-08-20 08:02
2006.09.17
Альтернатива Adobe Reader


6-1146115348
sadel
2006-04-27 09:22
2006.09.17
Работа с telnet


15-1156998605
cyborg
2006-08-31 08:30
2006.09.17
Кто тут монитор хотел?


11-1132642153
MTsv DN
2005-11-22 09:49
2006.09.17
Удержание кнопки мыши и кнопки...





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский