2010-07-23 3 views
4

Delphi 2010에서 DLL 함수를 호출하려고합니다.이 함수는 문자열을 가져와 USB 인터페이스를 사용하여 프린터에 씁니다. 어떤 언어로 DLL이 개발되었는지 모르겠습니다. 문서에 따르면 함수의 구문은 다음과 같습니다.DLL에 대한 매개 변수로 Delphi 문자열 보내기

int WriteUSB(PBYTE pBuffer, DWORD nNumberOfBytesToWrite); 

Delphi에서 함수를 선언하고 사용하려면 어떻게해야합니까?

var 
function WriteUSB(myP:pByte;n:DWORD): integer ; external 'my.dll'; 

내가 선언에 stdcall 또는 cdecl을 사용해야합니다

나는 이런 식으로 함수를 선언?

나는이 같은 DLL 함수를 호출 :

procedure myProc; 
var 
    str : string: 
begin 
    str := 'AAAAAAAAAAAAAAAAAAAAA'; 
    WriteUSB(str,DWORD(length(tmp))); 
end; 

을하지만이 코드는 예외를 나에게 모든 시간을 제공합니다. 문제는 String이 유니 코드이고 각 문자가 1 바이트를 초과한다는 것입니다. 다른 문자열 유형 (AnsiCharShortString)으로 변환하려고 시도했지만 실패했습니다.

올바른 방법은 무엇입니까?

답변

1

는 전화에를 PChar로 캐스팅보십시오 :

WriteUSB(pchar(str),DWORD(length(tmp))); 
+0

이것은 작동하지 않습니다. OP는 D2010을 사용하고 있습니다. 즉, String 및 PChar는 유니 코드이며 char 당 1 바이트 이상일 수 있습니다. DLL이 BYTE에 대한 포인터를 찾고 있으며 DLL 함수가 유니 코드를 인식하고 있다는 표시가 없습니다. –

11

몇 가지. 이 그것이처럼 보이는 C 인터페이스 인 경우 첫째, 당신은 다음과 같이 가져 오기를 선언해야합니다

function WriteUSB(myP:pAnsiChar; n:DWORD): integer; cdecl; external 'my.dll'; 

그런 다음 함수를 호출하기 위해, 당신은 ANSI 문자열을 사용하여 변환해야 이 때문에 같은 PAnsiChar가로 :

procedure myProc; 
var 
    str : AnsiString; 
begin 
    str := 'AAAAAAAAAAAAAAAAAAAAA'; 
    WriteUSB(PAnsiChar(str), length(str)); 
end; 

(. DWORD로 캐스팅 불필요) 당신이 이런 식으로 할 경우, 그것은 당신에게 어떤 문제를 포기하지 않고 작동합니다.

3

Ansi 문자 만 사용하려는 경우 문자열을 AnsiString으로 변환 할 수 있지만 유니 코드 문자열을 사용하고 DLL/프린터에서 허용하는 경우 해당 행을 따라 무언가를 시도 할 수 있습니다. (안된하지만 난 그게 일반적으로 corrext 생각) :

procedure myProc; 
var 
    str: string; 
    buff: TBytes; 
begin 
    str := 'blahblahblah'; // plus additional unicode stuff 
    buff := TEncoding.Default.GetBytes(str); // of TEncoding.UTF8 or... etc 
    WriteUSB(@buff[0], Length(buff)); 
end; 

는이 특정 DLL 작동 여부를 몰라하지만 오히려 생각하는 것보다 유니 코드 문자열로의 전환에 대처하는 일반적인 방법입니다 (어디서나 AnsiString에 캐스트).

+0

'TEncoding.Default'를 사용하는 것은 기능적으로 (유니 코드) String을 AnsiString에 할당하는 것과 같습니다. 즉,'var str : AnsiString; str : = 'blah'; WriteUSB (PByte (PAnsiChar (str)), Length (str)); ' –

+0

그래, 나는 그것에 대해 완전히 확신하지 못했다. 그러나 TBytes를 사용하는 것이 앞뒤로 캐스팅하는 것보다 훨씬 좋으며 델파이와 PChar/PAnsiChar의 서로 다른 버전 간의 혼동의 위험을 줄일 수 있다고 생각합니다. 게다가 일반적으로 .Default보다는 TEncoding.UTF8을 사용할 것이지만 어떤 이유로 든 .Default를 사용하는 것이 더 좋다고 생각했습니다. 왜 몰라. – shunty

+0

으악 ... 그리고 네, TEncoding이 새로운 것이라는 것을 깨닫습니다. 그래서 이전 버전에서 ifdef가 어디에서나 필요하지만 TBytes가 혼란을 해결하는 데 도움이된다고 생각합니다. – shunty

1

모든 의견을 보내 주셔서 감사합니다. 나는 당신의 피드백을 결합하여 그것을 작동하게 만든다. 이 솔루션은 다음과 같습니다

선언 (내가 cdecl 규칙을 추가) :

function WriteUSB(pc:pByte;n:DWORD): integer ; cdecl; external 'my.dll'; 

그리고 전화 :

Procedure myProc; 
Var 
    str : string; 
    buff : TBytes; 
begin 
    str := 'My string"; 
    buff := TEncoding.Default.GetBytes(str); // of TEncoding.UTF8 or... etc 
      WriteUSB(pByte(@buff[0]), Length(buff)) 

... 
End; 

내가 스웨덴의 문자 몇 가지 문제가 있지만 나는 그것을 해결할 것입니다. 이제는 DLL 호출이 정확하다는 것을 알았습니다.

모든 의견을 보내 주셔서 다시 한 번 감사드립니다. 이것은 훌륭한 포럼입니다.

BR 델파이 사용자

관련 문제