Deiphi的代码怎么转换成C或者C ++

john_hoff 2019-04-10 02:34:10
我手里有一段用Delphi写的源码,好像是用来生成一个DLL文件的。
我想把它里面的函数内容转化为C语言或者C++编写的,不知道哪位大佬能帮我看一看,不胜感激~
library PSIdll;
const
Pkg8400Len = 4120;
Pkg8400ChNum = 1024;
type
Byte69 = array[0..68] of Byte;
Single16 = array[0..15] of Single;
Byte8400 = array[0..Pkg8400Len-1] of Byte;
Single8400 = array[0..Pkg8400ChNum-1] of Single;
DataPkgType =packed record
st: Byte;
SN: integer;
ChData: Single16;
end;

//以下是PSI扫描器数据包解码函数
//单个4字节格式7->单精度浮点数
Function ToSingle(s1,s2,s3,s4:byte): Single; stdcall;
Var spt:^single;
sary:array[0..3] of byte;
begin
sary[0]:=s4;
sary[1]:=s3;
sary[2]:=s2;
sary[3]:=s1;
spt:=@sary;

ToSingle:=spt^;
end;

//单个4字节格式8->单精度浮点数
Function ToSingle8(s1,s2,s3,s4:byte): Single; stdcall;
Var spt:^single;
sary:array[0..3] of byte;
begin
sary[0]:=s1;
sary[1]:=s2;
sary[2]:=s3;
sary[3]:=s4;
spt:=@sary;

ToSingle8:=spt^;
end;


//单个69字节数据包->16个单精度浮点数
Function Decode9000(var rBuff: Byte69; psiFormat:integer;var SN:Longint; var ChData:Single16): integer;stdcall;
var
myData: ^DataPkgType;
byteAry: Byte69;
i: integer;

Begin
if (rBuff[0]>3) or (rBuff[0]<1) then
begin
Decode9000:=1;
for i:=0 to 15 do
begin
ChData[i] := 0.0;
end;

SN:= 0;
exit;

end;

case psiFormat of
7:
begin
byteAry[0]:= rBuff[0];
for i:=0 to 16 do
begin //交换字节顺序,格式7->格式8
byteAry[i*4+1]:= rBuff[i*4+4];
byteAry[i*4+2]:= rBuff[i*4+3];
byteAry[i*4+3]:= rBuff[i*4+2];
byteAry[i*4+4]:= rBuff[i*4+1];
end;
myData:=@byteAry;
end;

8:
myData:=@rBuff;

else
Decode9000:=1;
exit;
end;
Decode9000:=0;
ChData :=myData^.ChData;
SN:= myData^.SN;
End;

//==============================
//Decode DTCInitium 和8400数据包
Function DecodeDTC8400(var rBuff: Byte8400; var SN:Longint; var ChData:Single8400): integer;stdcall;
Var spt:^single;
sary:array[0..3] of byte;
DataNum: integer;
i: integer;

Begin
DecodeDTC8400:=1;
//报头解析:应答包
case rBuff[1] of
4,8,9,128: //简单应答包
begin
DecodeDTC8400:=1;
for i:=0 to 63 do
begin
ChData[i] := 0.0;
end;

SN:= 0;
end;

19: //数据流包
if rBuff[0] = 250 then
begin
DecodeDTC8400:=0;
SN := rBuff[4];
SN := SN *256 + rBuff[5];
DataNum := rBuff[6];
DataNum := DataNum *256 + rBuff[7]; //得到数据点数

//字节倒序,8400总是使用格式7,大头格式
for i:=0 to DataNum-1 do //DataNum-1
begin //交换字节顺序,格式7->格式8
sary[0]:= rBuff[i*4+24+3];
sary[01]:= rBuff[i*4+24+2];
sary[02]:= rBuff[i*4+24+1];
sary[03]:= rBuff[i*4+24];
spt:=@sary;
ChData[i] := spt^;
end;
end;

else //其它不解码
begin
DecodeDTC8400:=1;
for i:=0 to 63 do
begin
ChData[i] := 0.0;
end;

SN:= 0;
end;
end;

End;

exports

ToSingle ,
ToSingle name 'Tosingle',
ToSingle name 'ToSingle7',
ToSingle8,
DecodeDTC8400,
Decode9000;
begin

end.
...全文
377 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
john_hoff 2019-04-16
  • 打赏
  • 举报
回复
引用 8 楼 早打大打打核战争 的回复:
我编译了32位和64位两种,你试一下:https://www14.zippyshare.com/v/LyRQVrvk/file.html
大佬,您的两个DLL我这还是用不了。。。 我联系了NI 的工程师,他们说如果使用他们旗下的Labview/CVI来生成DLL文件的话肯定可以用,但是这个编译器是只支持C语言生成DLL的,所以可能还是需要重构成C…… 为什么会有这样的问题啊……
john_hoff 2019-04-16
  • 打赏
  • 举报
回复
引用 12 楼 早打大打打核战争 的回复:
可以明确的说,没有C语言生成的DLL可以用,Delphi生成的DLL不能用这种事,要么是调用约定的问题,你把stdcall改成cdecl再编译试一下(只限于32位DLL,64位DLL只有一种调用约定),要么是你们的开发人员对函数原型没有正确声明,或者他没有从DLL导出.lib,可以用EMB的工具implib(32位)/mkexp.exe或者VS中的dumpbin和lib建立导入库文件。
感谢您的回复,我让人去试试~
  • 打赏
  • 举报
回复
可以明确的说,没有C语言生成的DLL可以用,Delphi生成的DLL不能用这种事,要么是调用约定的问题,你把stdcall改成cdecl再编译试一下(只限于32位DLL,64位DLL只有一种调用约定),要么是你们的开发人员对函数原型没有正确声明,或者他没有从DLL导出.lib,可以用EMB的工具implib(32位)/mkexp.exe或者VS中的dumpbin和lib建立导入库文件。
浪子家园 2019-04-13
  • 打赏
  • 举报
回复
Delphi本来就可以编译原生代码(绿色且不要任何运行库)的dll,为什么还非得要转成c/c++呢?而且只要你按照Windows标准动态库构建代码就可以编译出给任何语言调用的动态库的。
john_hoff 2019-04-10
  • 打赏
  • 举报
回复
引用 8 楼 早打大打打核战争 的回复:
我编译了32位和64位两种,你试一下:https://www14.zippyshare.com/v/LyRQVrvk/file.html
感谢~~我让人试一下
  • 打赏
  • 举报
回复
我编译了32位和64位两种,你试一下:https://www14.zippyshare.com/v/LyRQVrvk/file.html
john_hoff 2019-04-10
  • 打赏
  • 举报
回复
引用 6 楼 pzx521521 的回复:
[quote=引用 5 楼 john_hoff 的回复:] [quote=引用 4 楼 早打大打打核战争 的回复:] 不可能Delphi编译出来的DLL它用不了,C语言编译的可以,估计是32位还是64位DLL的问题
这个DLL的位数问题取决于编译器所在的系统是32位还是64位吗[/quote] 不是的哦, xe一下只有32的 xe以上可以选择平台(32,64,phone,linux,etc..)的[/quote] 意思是如果我是在XP下使用Delphi7编译出来的应该就是32位的了吧?
pzx521521 2019-04-10
  • 打赏
  • 举报
回复
引用 5 楼 john_hoff 的回复:
[quote=引用 4 楼 早打大打打核战争 的回复:] 不可能Delphi编译出来的DLL它用不了,C语言编译的可以,估计是32位还是64位DLL的问题
这个DLL的位数问题取决于编译器所在的系统是32位还是64位吗[/quote] 不是的哦, xe一下只有32的 xe以上可以选择平台(32,64,phone,linux,etc..)的
john_hoff 2019-04-10
  • 打赏
  • 举报
回复
引用 4 楼 早打大打打核战争 的回复:
不可能Delphi编译出来的DLL它用不了,C语言编译的可以,估计是32位还是64位DLL的问题
这个DLL的位数问题取决于编译器所在的系统是32位还是64位吗
  • 打赏
  • 举报
回复
不可能Delphi编译出来的DLL它用不了,C语言编译的可以,估计是32位还是64位DLL的问题

john_hoff 2019-04-10
  • 打赏
  • 举报
回复
引用 2 楼 早打大打打核战争 的回复:
编译一下直接用就可以了 非要翻译,也很容易

// PSIdll.cpp

#include <windows.h>

const int Pkg8400Len = 4120;
const int Pkg8400ChNum = 1024;

typedef unsigned char byte;
typedef byte Byte69[69];
typedef float Single16[16];
typedef byte Byte8400[Pkg8400Len];
typedef float Single8400[Pkg8400ChNum];
#pragma pack(push, 1) 
typedef struct tagDataPkgType
{
  byte st;
  int SN;
  Single16 ChData;
} DataPkgType;
#pragma pack(pop) 

__declspec(dllexport) __stdcall float ToSingle(byte s1, byte s2, byte s3, byte s4)
{
  int result = (int)s4 + ((int)s3 << 8) + ((int)s2 << 16) + ((int)s1 << 24);

  return *(float *)&result;
}

// 剩下的你自己转吧

BOOL APIENTRY DllMain(HANDLE hModule, DWORD dwReason, void *lpReserved)
{
  switch(dwReason)
  {
    case DLL_PROCESS_ATTACH:
      // ...
      break;

    case DLL_PROCESS_DETACH:
      // ...
      break;
  }

  return true;
}
感谢大佬的回复。我是想要在Labview的RT系统中使用,但是Delphi编译出来的DLL它用不了。。。NI的工程师说用C语言编译的应该可以。。。所以才会来问这么一个问题 另外关于代码的部分,由于我很少使用C和Delphi所以十分的小白………… 您应该是转换了数据类型定义的那些吧?剩下的4个函数我如果要转换应该放在代码的哪个地方呢,还请指教一下,蟹蟹蟹蟹~~~
  • 打赏
  • 举报
回复
编译一下直接用就可以了
非要翻译,也很容易

// PSIdll.cpp

#include <windows.h>

const int Pkg8400Len = 4120;
const int Pkg8400ChNum = 1024;

typedef unsigned char byte;
typedef byte Byte69[69];
typedef float Single16[16];
typedef byte Byte8400[Pkg8400Len];
typedef float Single8400[Pkg8400ChNum];
#pragma pack(push, 1)
typedef struct tagDataPkgType
{
byte st;
int SN;
Single16 ChData;
} DataPkgType;
#pragma pack(pop)

__declspec(dllexport) __stdcall float ToSingle(byte s1, byte s2, byte s3, byte s4)
{
int result = (int)s4 + ((int)s3 << 8) + ((int)s2 << 16) + ((int)s1 << 24);

return *(float *)&result;
}

// 剩下的你自己转吧

BOOL APIENTRY DllMain(HANDLE hModule, DWORD dwReason, void *lpReserved)
{
switch(dwReason)
{
case DLL_PROCESS_ATTACH:
// ...
break;

case DLL_PROCESS_DETACH:
// ...
break;
}

return true;
}

john_hoff 2019-04-10
  • 打赏
  • 举报
回复
如果方法可行,另有报酬,感谢感谢

16,748

社区成员

发帖
与我相关
我的任务
社区描述
Delphi 语言基础/算法/系统设计
社区管理员
  • 语言基础/算法/系统设计社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧