2014-06-10 9 views
1

저는 많은 다른 작은 라이브러리들과 상호 작용하는 Delphi 프로젝트를 작업합니다. FastMM4를 사용하며 dll 매개 변수에 전달 된 복잡한 클래스로 작업하고 싶습니다.is 연산자가 다른 모듈의 인스턴스를 전달할 때 예상 한 값을 반환하지 않는 이유는 무엇입니까?

예를 들어 내 양식을 내 dll로 보냅니다. dll에 연산자 "IS"를 사용하여 매개 변수 유형을 테스트합니다.

그러나 DLL을 운영자에

Exemple

library Dll; 

uses 
    FastMM4, 
    System.SysUtils, 
    System.Classes, 
    Vcl.Dialogs, 
    Vcl.Forms; 

{$R *.res} 

procedure Complex(L : TObject);stdcall; 
begin 
    if L is TForm then 
     showmessage('Ok') 
    else 
     showmessage('Pas ok') ; 

    if L is TCustomFrame then 
     showmessage('Ok') 
    else 
     showmessage('Pas ok') 
end; 

exports 
    Complex; 

begin 
end. 

그리고 첫째

procedure TffsIsOperator.Button2Click(Sender: TObject); 
var 
MaDLL : THandle; 
Proc : procedure (l : TObject); 
begin 
    try 
     MaDLL := LoadLibrary(PChar('Dll.dll')); 
     @Proc := GetProcAddress(MaDLL, 'Complex'); 
     Proc(self); 
    finally 
     FreeLibrary(MaDLL); 
    end; 
end; 
+0

호출 규칙에주의하십시오. 귀하의 선언이 서로 일치하지 않습니다. –

+0

물론이 예제에서는 코드를 줄이기 위해 마지막으로 변경합니다. 죄송합니다. "Proc : procedure (l : TObject) – Joc02

답변

6

전화를 항상 "false"를 반환 "IS", 당신은 호출 규칙을 잘못 일치가 . interop 경계의 양쪽에서 호출 규칙을 동일하게 만들어야합니다.

심지어는 is 운영자의 명백한 부정 행위가 예상 할 수있는 것을 수정합니다. 프로세스에 두 개의 VCL 인스턴스가 있습니다. 하나는 호스트에, 다른 하나는 DLL에 있습니다. 이들은 각각 VCL에 정의 된 클래스의 고유 한 버전을 가지고 있습니다. 따라서 DLL의 TForm은 호스트의 TForm과는 다른 클래스 형식입니다. 그리고 그 이유는 is가 false를 평가합니다.

이 처리하는 전통적인 방법은 단지 당신의 과정에서 RTL/VCL의 한 인스턴스를 가지고 준비하는 것입니다. 그리고 런타임 패키지 사용을 통해이를 달성 할 수 있습니다. 런타임 패키지는 당신을 위해 실행 가능한 옵션이 아니며, 당신은 DLL을 사용해야하는 경우

는, 당신은 DLL 경계를 넘어 어떤 델파이 클래스를 통과 포기해야합니다. 나는 이것이 이것이 환영받지 못하는 뉴스가 될 것이라고 충분히 기대하지만, 그것이 바로 그 방법입니다. TObject 인스턴스를 DLL 경계에 전달할 수 없으며 메소드, 쿼리 유형 ID 등을 호출 할 수 없습니다. DLL에서는 지원되지 않습니다. 런타임 패키지에만 해당됩니다.

DLL을 사용해야하는 경우 간단한 유형을 고수해야합니다. 정수, 부동 소수점 값, 문자 유형, 배열 (동적 배열 아님), 레코드, 이러한 유형의 포인터, 인터페이스. Win32에서 제안 된 interop의 예를 찾을 수 없다면, 아마 유효하지 않을 것입니다.

+0

감사합니다. 런타임 패키지를 사용해 보았습니다. – Joc02