将 PowerBasic 的 DLL 调用转换为 Delphi
Translate a DLL call from PowerBasic to Delphi
我想从 Delphi 调用 SPSS 'backend'。有一个我可以使用的 DLL(似乎):SPSSio64.DLL
。但是我找不到接口定义。
我找到的是 PowerBasic 中的示例:
DECLARE FUNCTION spssOpenRead LIB "spssio32.dll" ALIAS "spssOpenRead@8" (BYVAL fileName AS STRING, BYREF hHandle AS LONG) AS LONG
DECLARE FUNCTION spssCloseRead LIB "spssio32.dll" ALIAS "spssCloseRead@4" (BYVAL hHandle AS LONG) AS LONG
因为我只需要读取和写入文件的函数(所有处理都将通过该文件中的语法完成),我认为这个例子可能足以推断出如何从 Delphi.
所以问题是:这些声明如何在 Delphi(64 位)中?
基于 SPSS 14.0 for Windows Developer's Guide, and PowerBasic documentation,尝试这样的操作:
32 位:
// spssio32.dll exports both 'spssOpenRead' and 'spssOpenRead@8', which are the same function...
function spssOpenRead(filename: PAnsiChar; var hHandle: Integer): Integer; stdcall; external 'spssio32.dll' {name 'spssOpenRead@8'};
// spssio32.dll exports both 'spssCloseRead' and 'spssCloseRead@4', which are the same function...
function spssCloseRead(hHandle: Integer): Integer; stdcall; external 'spssio32.dll' {name 'spssCloseRead@4'};
64 位:
// I can't find a copy of spssio64.dll to download, so I can't verify the exported names. Adjust if needed..
function spssOpenRead(filename: PAnsiChar; var hHandle: Integer): Integer; stdcall; external 'spssio64.dll' {name 'spssOpenRead@16'};
function spssCloseRead(hHandle: Integer): Integer; stdcall; external 'spssio64.dll' {name 'spssCloseRead@8'};
郑重声明,这有效:
function LoadDLL(DLLname : string) : Uint64;
var
em : TArithmeticExceptionMask;
begin
em:=GetExceptionmask;
SetExceptionmask(em+[exInvalidOp,exZeroDivide,exOverflow,exUnderflow]);
result:=LoadLibrary(PwideChar(DLLname));
SetExceptionmask(em);
end;
function RunSPSSio(filename : string; instructions : Tinstructions) : boolean;
// This will only read SAV files, not SPS files !
type
TspssOpenRead = function (filename: PAnsiChar; var hHandle: Uint64): Integer;
TspssCloseRead = function(hHandle: Uint64): Integer;
TspssGetInterfaceEncoding = function(hHandle : Uint64): Integer;
TspssSetInterfaceEncoding = function(encoding : integer; hHandle : Uint64): Integer;
const
SPSS_ENCODING_UTF8 = 1;
var
p : integer;
spssOpenRead : TspssOpenRead;
spssCloseRead : TspssCloseRead;
spssGetIFencoding : TspssGetInterfaceEncoding;
spssSetIFencoding : TspssSetInterfaceEncoding;
DLLhandle : Uint64;
fileref : PANSIchar;
begin
result:=false;
DLLhandle:=LoadDLL('C:\SPSS\spssio64.dll'); // hardcoded
if DLLhandle=0
then begin p:=GetLastError();
report('DLL load error '+IntToStr(p));
exit;
end;
try
@SPSSopenRead:=getProcAddress(DLLhandle,'spssOpenRead');
@SPSScloseRead:=getProcAddress(DLLhandle,'spssCloseRead');
@SPSSsetIFencoding:=getProcAddress(DLLhandle,'spssSetInterfaceEncoding');
SPSSsetIFencoding(SPSS_ENCODING_UTF8,DLLhandle);
fileref:=PANSIchar(ANSIstring(filename));
p:=SPSSopenRead(fileref,DLLhandle);
if p<>0
then report('*** SPSSio error '+IntToStr(p))
else begin // SPSS database interactions here
result:=SPSScloseRead(DLLhandle)=0;
end;
finally
freeLibrary(DLLhandle);
end;
end;
我想从 Delphi 调用 SPSS 'backend'。有一个我可以使用的 DLL(似乎):SPSSio64.DLL
。但是我找不到接口定义。
我找到的是 PowerBasic 中的示例:
DECLARE FUNCTION spssOpenRead LIB "spssio32.dll" ALIAS "spssOpenRead@8" (BYVAL fileName AS STRING, BYREF hHandle AS LONG) AS LONG
DECLARE FUNCTION spssCloseRead LIB "spssio32.dll" ALIAS "spssCloseRead@4" (BYVAL hHandle AS LONG) AS LONG
因为我只需要读取和写入文件的函数(所有处理都将通过该文件中的语法完成),我认为这个例子可能足以推断出如何从 Delphi.
所以问题是:这些声明如何在 Delphi(64 位)中?
基于 SPSS 14.0 for Windows Developer's Guide, and PowerBasic documentation,尝试这样的操作:
32 位:
// spssio32.dll exports both 'spssOpenRead' and 'spssOpenRead@8', which are the same function...
function spssOpenRead(filename: PAnsiChar; var hHandle: Integer): Integer; stdcall; external 'spssio32.dll' {name 'spssOpenRead@8'};
// spssio32.dll exports both 'spssCloseRead' and 'spssCloseRead@4', which are the same function...
function spssCloseRead(hHandle: Integer): Integer; stdcall; external 'spssio32.dll' {name 'spssCloseRead@4'};
64 位:
// I can't find a copy of spssio64.dll to download, so I can't verify the exported names. Adjust if needed..
function spssOpenRead(filename: PAnsiChar; var hHandle: Integer): Integer; stdcall; external 'spssio64.dll' {name 'spssOpenRead@16'};
function spssCloseRead(hHandle: Integer): Integer; stdcall; external 'spssio64.dll' {name 'spssCloseRead@8'};
郑重声明,这有效:
function LoadDLL(DLLname : string) : Uint64;
var
em : TArithmeticExceptionMask;
begin
em:=GetExceptionmask;
SetExceptionmask(em+[exInvalidOp,exZeroDivide,exOverflow,exUnderflow]);
result:=LoadLibrary(PwideChar(DLLname));
SetExceptionmask(em);
end;
function RunSPSSio(filename : string; instructions : Tinstructions) : boolean;
// This will only read SAV files, not SPS files !
type
TspssOpenRead = function (filename: PAnsiChar; var hHandle: Uint64): Integer;
TspssCloseRead = function(hHandle: Uint64): Integer;
TspssGetInterfaceEncoding = function(hHandle : Uint64): Integer;
TspssSetInterfaceEncoding = function(encoding : integer; hHandle : Uint64): Integer;
const
SPSS_ENCODING_UTF8 = 1;
var
p : integer;
spssOpenRead : TspssOpenRead;
spssCloseRead : TspssCloseRead;
spssGetIFencoding : TspssGetInterfaceEncoding;
spssSetIFencoding : TspssSetInterfaceEncoding;
DLLhandle : Uint64;
fileref : PANSIchar;
begin
result:=false;
DLLhandle:=LoadDLL('C:\SPSS\spssio64.dll'); // hardcoded
if DLLhandle=0
then begin p:=GetLastError();
report('DLL load error '+IntToStr(p));
exit;
end;
try
@SPSSopenRead:=getProcAddress(DLLhandle,'spssOpenRead');
@SPSScloseRead:=getProcAddress(DLLhandle,'spssCloseRead');
@SPSSsetIFencoding:=getProcAddress(DLLhandle,'spssSetInterfaceEncoding');
SPSSsetIFencoding(SPSS_ENCODING_UTF8,DLLhandle);
fileref:=PANSIchar(ANSIstring(filename));
p:=SPSSopenRead(fileref,DLLhandle);
if p<>0
then report('*** SPSSio error '+IntToStr(p))
else begin // SPSS database interactions here
result:=SPSScloseRead(DLLhandle)=0;
end;
finally
freeLibrary(DLLhandle);
end;
end;