在Delphi编程中使用C语言代码

delphi介绍 delphi 阅读详情

在Delphi编程中使用C语言代码

  陈经韬
    Windows下编程的工具有很多,例如VB,Delphi,VC等等.我在这里不想讨论"它们的具体哪个更好一点"这种幼稚的问题.玩过DOS程序设计的人都知道,DOS下很多语言的实质核心还是调用系统提供的汇编中断函数.到了Windows下,它就变成了我们常说的API了.而在Windows下写程序很多时候都是调用API,语言,只不过是一个表达工具而已.
    我现在已经参加工作大约有半年左右,我们公司是用Borland公司的Delphi作为主开发工具.本着未偏袒任何一个工具的立场,我说句公道话:Delphi是目前Win32下开发程序的最快速,最有效率的工具.
    Delphi适合用来开发应用程序,但是有时侯一些底层的东西可以直接使用C语言来开发.我在公司经常开发跟硬件相关的项目,而很多硬件的SDK包是用C来写的.这个时候我一般把它们转换成Delphi(PASCAL)语法的代码.下面谈一下我的个人粗浅经验.因为当时学校教的是Pascal语言,所以我对C语言并不是太熟手.下面的观点或者代码如有错漏之处希望高手们放小弟一马:)

一:将C语言的程序编译成DLL供Delphi调用.这种方法过于简单,而且需要额外带一个DLL文件,所以不在本文的讨论范围之内.

:直接转换C语言代码到DELPHI代码


   C语言的函数格式与Delphi不同,它们是函数返回类型在前,函数声明在后.对于没有任何返回类型的函数则定义为VOID类型.
   例如:Delphi中函数function MyFunction:(intIN:integer):Bool;相应的C语言代码就变成Bool MyFunction(int intIN);又例如procedure MyProcedure;====>void MyProcedure;采用这种方法,一般要求对C语言比较熟悉.我一般是采用这种方法.下面是我收集整理的自己常用的Delphi与C之间的类型对应表.其中左边是C类型,右边是对应的Delphi类型:

ABC -> TABC 
ACCEL -> TAccel 
ATOM -> TAtom 
BITMAP -> TBitMap 
BITMAPCOREHEADER -> TBitmapCoreHeader 
BITMAPCOREINFO -> TBitmapCoreInfo 
BITMAPFILEHEADER -> TBitmapFileHeader 
BITMAPINFO -> TBitmapInfo 
BITMAPINFOHEADER -> TBitmapInfoHeader 
BOOL -> Bool 
CBT_CREATEWND -> TCBT_CreateWnd 
CBTACTIVATESTRUCT -> TCBTActivateStruct 
CHAR -> Char 
CHAR* -> PChar 
CLIENTCREATESTRUCT -> TClientCreateStruct 
COLORREF -> TColorRef 
COMPAREITEMSTRUCT -> TCompareItemStruct 
COMSTAT -> TComStat 
CREATESTRUCT -> TCreateStruct 
CTLINFO -> TCtlInfo 
CTLSTYLE -> TCtlStyle 
CTLtype -> TCtltype 
DCB -> TDCB 
DDEAACK -> TDDEAck 
DDEADVISE -> TDDEAdvise 
DDEDATA -> TDDEData 
DDEPOKE -> TDDEPoke 
DEBUGHOOKINFO -> TDebugHookInfo 
DELETEITEMSTRUCT -> TDeleteItemStruct 
DEVMODE -> TDevMode 
DOUBLE -> Double 
DRAWITEMSTRUCT -> TDrawItemStruct 
DWORD -> LongInt 
ENUMLOGFONT -> TEnumLogFont 
EVENTMSG -> TEventMsg 
FARPROC -> TFarProc 
FIXED -> TFixed 
FLOAT -> Single 
GLYPHMETRICS -> TGlyphMetrics 
HANDLE -> THandle 
HANDLETABLE -> THandleTable 
HARDWAREHOOKSTRUCT -> THardwareHookStruct 
HELPWININFO -> THelpWinInfo 
INT -> Integer 
KERNINGPAIR -> TKerningPair 
LOGBRUSH -> TLogBrush 
LOGFONT -> TLogFont 
LOGPALETTE -> TLogPalette 
LOGPEN -> TLogPen 
LONG -> LongInt 
LONG DOUBLE -> Extended 
LONG INT -> LongInt 
LPSTR -> PChar 
LPWSTR -> PWideChar 
MAT2 -> TMat2 
MDICREATESTRUCT -> TMDICreateStruct 
MEASUREITEMSTRUCT -> TMeasureItemStruct 
MENUITEMTEMPLATE -> TMenuItemTemplate 
MENUITEMTEMPLATEHEADER -> TMenuItemTemplateHeader
METAFILEPICT -> TMetaFilePict 
METAHEADER -> TMetaHeader 
METARECORD -> TMetaRecord 
MINMAXINFO -> TMinMaxInfo 
MOUSEHOOKSTRUCT -> TMouseHookStruct 
MSG -> TMsg 
MULTIKEYHELP -> TMultiKeyHelp 
NCCALCSIZE_PARAMS -> TNCCalcSize_Params 
NEWTEXTMETRIC -> TNewTextMetric 
OFSTRUCT -> TOFStruct 
OUTLINETEXTMETRIC -> TOutlineTextMetric 
PAINTSTRUCT -> TPaintStruct 
PALETTEENTRY -> TPaletteEntry 
PANOSE -> TPanose 
PATTERN -> TPattern 
POINTFX -> TPointFX 
PSTR -> PChar 
PWSTR -> PWideChar 
RASTERIZER_STATUS -> TRasterizer_Status 
RGBQUAD -> TRGBQuad 
RGBTRIPLE -> TRGBTriple 
SEGINFO -> TSegInfo 
SHORT -> SmallInt 
SHORT INT -> SmallInt 
SIZE -> TSize 
TEXTMETRIC -> TTextMetric 
TPOINT -> TPoint 
TRECT -> TRect 
TTPOLYCURVE -> TTTPolyCurve 
TTPOLYGONHEADER -> TPolygonHeader 
UINT -> Word 
UNSIGNED -> Word 
UNSIGNED CHAR -> Byte 
UNSIGNED INT -> Word 
UNSIGNED LONG -> LongInt(DWORD) 
UNSIGNED LONG INT -> LongInt 
UNSIGNED SHORT -> Word 
UNSIGNED SHORT INT -> Word 
VOID* -> Pointer 
WINDOWPLACEMENT -> TWindowPlacement 
WINDOWPOS -> TWindowPos 
WNDCLASS -> TWndClass 
WORD -> Word 

三:在Delphi中直接链接C语言的OBJ文件.
   这种方法的好处在于最终EXE不用带任何外部文件.也不用对C语言过于熟悉.
   我们都知道,代码在编译成可执行文件(或DLL,OCX文件,下同)之前,都必须得先生成OBJ文件(DELPHI一般是DCU文件,但也可以通过编辑编译选项生成OBJ文件),然后把OBJ文件和资源文件(*.RES)链接成最终的可执行文件.利用这个方法,我们可以直接把OBJ文件链接到我们的程序里面.
   不过需要注意的是,编译器不同,生成的OBJ文件也不一样.Microsoft的编译器生成的OBJ文件是COFF格式,而Borland的C++Builder生成的是OMF格式.因为我们需要在Delphi中链接,所以必须使用CBC,或者Borland官方站点带的免费编译工具.下面我们通过一个简单的例子来说明具体操作步骤:
   这个例子是简单的提供一个函数,用来判断一个文件是否为Dat格式的VCD文件.头文件声明如下:


/*
文件名称:DatFormat.h
*/
#ifndef DatFormat_H
#define DatFormat_H
#include <windows.h>
#pragma pack(push, 1)//这个与下面的配对,一般用到记录类型的时候需要定义,这里实际不用


#ifdef __cplusplus
extern "C" {
#endif

extern BOOL CheckIsDatFile(const char * FileName,BOOL *IsDatFile);

#ifdef __cplusplus
}
#endif


#pragma pack(pop)

#endif // DatFormat_H

  具体实现代码DatFormat.c如下:

#include "DatFormat.h"
BOOL CheckIsDatFile(const char * FileName,BOOL *IsDatFile)
/*
函数说明:该函数用于判断一个文件是否为Dat文件(即VCD文件)格式.
参数:
IN:
FileName:欲判断的文件名称
IN,OUT:
IsDatFile:是否为Dat格式文件
OUT:
读文件失败返回FALSE,否则返回TRUE.
------------------------------------
作者:陈经韬.2004,01,17. http://www.138soft.com,lovejingtao@21cn.com
*/
{
HANDLE hFile;
DWORD dwBytesRead;
BOOL re;
char MyBuf[4];

*IsDatFile=FALSE;

//建立读文件句柄
hFile = CreateFile(FileName,
GENERIC_READ,
FILE_SHARE_READ,
NULL,
OPEN_EXISTING,
0,
0);


if (hFile == INVALID_HANDLE_VALUE) return FALSE;

//读文件
re = ReadFile(hFile,
&MyBuf,
4,
&dwBytesRead,
NULL);

if (dwBytesRead!=4)
{
CloseHandle(hFile);
return FALSE;
}

//读文件失败的时候
if (re!=TRUE)
{
CloseHandle(hFile);
return FALSE;
}
CloseHandle(hFile);
*IsDatFile=(MyBuf[0]=='R' && MyBuf[1]=='I' && MyBuf[2]=='F' && MyBuf[3]=='F');

return(TRUE);
}

  运行CBC,新建一个工程,然后把DatFormat.c添加到工程里面,编译整个工程,将得到我们需要的OBJ文件:DatFormat.OBJ.然后我们关闭CBC即可,因为下面不再需要用到它了.
  运行Delphi,新建一个工程并保存.然后把DatFormat.OBJ拷贝到它的目录之下.在单元的implementation下面添加如下代码:

{$LINK 'DatFormat.obj'} //链接外部OBJ文件
function _CheckIsDatFile(const FileName:Pchar;IsDatFile:PBool):Bool;cdecl;external;//定义函数.其中cdecl进栈方式说明采用C语言格式传递参数.external说明是个外部声明函数.

  注意函数声明的原形与C定义的不一样.必须在前面添加一个下划线.原因是因为编译器的链接符号中.C与C++是不一样的.因为这个不是本文重点,所以这里不作讨论.请感兴趣的朋友自行参阅相关资料.
  然后我们写如下代码调用此函数:

procedure TFrmMain.Button1Click(Sender: TObject);
var
IsDatFile:Bool;
begin
if OpenDialog1.Execute then
if _CheckIsDatFile(Pchar(OpenDialog1.FileName),@IsDatFile) then
if IsDatFile then ShowMessage('恭喜!该文件是一个Dat格式的视频文件!')
else ShowMessage('不好意思,该文件不是一个Dat格式的视频文件!')
else ShowMessage('读文件错误!');
end;

  编译这个程序,将得到一个干净的可执行EXE文件了.

四:C++Builder中使用Delphi单元

  这个实际是题外话了,不过这里还是提一提:假设我们有一个获取BIOS密码的Delphi单元

unit AwardBiosPas;

{=======================================================
项目:
在Delphi编程中使用C语言代码- 演示程序
模块: 获取BIOS密码单元
描述:
版本:
日期: 2004-01-17
作者: 陈经韬.lovejingtao@21cn.com,http://www.138soft.com
更新: 2004-01-17
=======================================================}

interface
uses
windows, SysUtils;

function My_GetBiosPassword: string;

implementation

function CalcPossiblePassword(PasswordValue: WORD): string;
var
I: BYTE;
C: CHAR;
S: string[8];

begin
I := 0;
while PasswordValue <> 0 do
begin
Inc(I);
if $263 > PasswordValue then
begin
if $80 > PasswordValue then
S[I] := CHAR(PasswordValue)
else if $B0 > PasswordValue then
S[I] := CHAR(PasswordValue and $77)
else if $11D > PasswordValue then
S[I] := CHAR($30 or (PasswordValue and $0F))
else if $114 > PasswordValue then
begin
S[I] := CHAR($64 or (PasswordValue and $0F));
if '0' > S[I] then
S[I] := CHAR(BYTE(S[I]) + 8);
end
else if $1C2 > PasswordValue then
S[I] := CHAR($70 or (PasswordValue and $03))
else if $1E4 > PasswordValue then
S[I] := CHAR($30 or (PasswordValue and $03))
else
begin
S[I] := CHAR($70 or (PasswordValue and $0F));
if 'z' < S[I] then
S[I] := CHAR(BYTE(S[I]) - 8);
end;
end
else
S[I] := CHAR($30 or (PasswordValue and $3));
PasswordValue := (PasswordValue - BYTE(S[I])) shr 2;
end;

S[0] := CHAR(I);
PasswordValue := I shr 1;
while PasswordValue < I do
begin {this is to do because award starts calculating with the last letter}

C := S[BYTE(S[0]) - I + 1];
S[BYTE(S[0]) - I + 1] := S[I];
S[I] := C;
Dec(I);
end;
CalcPossiblePassword := S;
end;

function readcmos(off: byte): byte;
var
value: byte;
begin
asm
xor ax, ax
mov al, off
out 70h, al
in al, 71h
mov value, al
end;
readcmos := value;
end;

function My_GetBiosPassword: string;
var
superpw, userpw: word;
begin
if Win32Platform <> VER_PLATFORM_WIN32_NT then //不是NT
begin
pchar(@superpw)[0] := char(readcmos($1C));
pchar(@superpw)[1] := char(readcmos($1D));
pchar(@userpw)[0] := char(readcmos($64));
pchar(@userpw)[1] := char(readcmos($65));
Result:= ('************BIOS密码**********************')+#13+'超级用户密码为:' + CalcPossiblePassword(superpw) + #13 + '用户密码为:' + CalcPossiblePassword(userpw);
end
else
Result := '用户系统为NT,无法获取BIOS密码!';
end;
end.

  如何直接在CBC中使用它呢?新建一个CBC工程,然后把这个单元加到项目里面去.具体操作为:Add to Project--->文件类型:pascal unit(*.pas),然后Build Demo1.这个时候将在AwardBiosPas.pas的同目录下生成一个AwardBiosPas.hpp文件.把它引用到我们的需要调用的单元.然后直接调用即可:
void __fastcall TFrmMain::Button1Click(TObject *Sender)
{
ShowMessage(My_GetBiosPassword());
}

五:其它方法.当然可以用RES将C语言生成的二进制文件,但这个方法与第一种方法差不多.优点是不怕文件丢失.缺点是很容易被别人直接用资源修改工具打开修改.这个时候可以使用笔者写的自制编程序工具PasAnywhere.不过这已经是另外一个话题了.

 
C-To-Delphi:C到Delphi转换器 德尔福 描述 该工具将转换您的大多数标准C代码。 。 在此处可执行文件。 它包含一个拆分视图,左侧为C,右侧为Delphi。 当您编辑C代码时,Delphi代码会实时更新。 编辑器保持同步,因此您可以轻松地找到特定代码段的转换方式。 已验证生成代码的语法检查。 (使用DelphiAST) 您甚至可以按F9键来运行生成的代码使用DWS) 您可以将多个C文件拖放到应用程序中。 它会找到属于它的.h文件,并将所有文件转换为同一文件夹中的.pas文件。 特征: 如果存在main函数,则将生成一个程序。 否则,带有接口/实现部分的Pascal单元。 转换例程和参数 转换循环 转换案例陈述 转换结构 转换枚举 转换1和2维数组 将许多其他常用例程转换为等效的Delphi(strcpy,strcat,strlen,printf,argv,argc等) 转换类 立即下载

相关推荐

C 2 Delphi Converter

C文件转Delphi DEMO版,但是破解了可以直接复制出转换后的内容,转换质量还可以,不过要用还得手工修改。

Delphi创建服务程序

作者: 陈经韬 Windows 2000/XP和2003等支持一种叫做"服务程序"的东西.程序作为服务启动有以下几个好处:   (1)不用登陆进系统即可运行.   (2)具有SYSTEM特权.所以你在进程管理器里面是无法结束它的.   笔者在2003年为一公司开发机顶盒项目的时候,曾经写过课件上传和媒体服务,下面就介绍一下如何用Delphi7创建一个Service程序.   运行Delp

abin30的专栏 1301

delphi两种方法调用本地程序

delphi编程实现调用本地程序,本实例可调用本地 截图工具、步骤记录器、画图工具、计算器、记事本、屏幕键盘、放大镜、任务管理器、命令提示符、控制面板、word和excel,用的是WinExec和ShellExecute方法,需要实现引用Winapi.shellapi, WinProcs,

C语言程序的封装

所谓程序的封装就是把源代码隐藏,但是功能依旧可以正常使用,当我们想把代码的功能给出,但又不想暴露源码时,可以用到C语言程序的封装。废话不多讲,直接讲操作步骤。 举一个例子,方便说明,就举一个加法程序吧。 生成静态库(.lib) 将头文件和源代码生成静态库。 这是加法程序的源代码和头文件 在add的属性栏将配置属性中的常规的配置类型改为静态库。 在运行程序时会报错,没关系,因为没有主函数,没有办法运行,但是可以编译。 在add文件的debug文件中找到静态库文件。 将静态库文件和

lyzzs222的博客 7322

老陈---Usb摄像头专题讲座

文档作者:陈经韬本文主要讲述视频数据获取、保存为mpeg、调用Mpeg4压缩算法、自己用Delphi写编解码器和如何防范Usb偷窥。一:获取摄像头数据    获取数据可以使用Directx或Vfw接口。一般来说,Directx比较占用cpu,而且com接口是比较麻烦的,所以一般使用vfw。不过,如果想直接捕获视频和声音保存为wmv文件,那么就要使用Directx。我们这里先讲vfw的。

2320

C语言代码套用在Delphi编程中(C++Builder(VC++)与 Delphi

Delphi适合用来开发应用程序,但是有时侯一些底层的东西可以直接使用C语言来开发.我在公司经常开发跟硬件相关的项目,而很多硬件的SDK包是用C来写的.这个时候我一般把它们转换成Delphi(PASCAL)语法的代码. 一:将C语言的程序编译成DLL供Delphi调用.这种方法过于简单,而且需要额外带一个DLL文件,所以不在本文的讨论范围之内.   二:直接转换C语言代码DELPHI代码

345

delphi加载c语言dll文件,在Delphi编程使用C语言代码 - 调用C语言编写的DLL文件(3页)-原创力文档...

1、 使用Visual C++ 6.0编写和链接DLL打开Visual C++ 6.0集成开发环境,新建一个Win32 Dynamic-Link Library类型的工程CDLL,在工程中新建一个C语言源文件cdll.c。源文件中的内容如下:__declspec(dllexport) int max(int x,int y) /* 比较两个整型变量大小的函数max */{???if (x>y...

weixin_36054444的博客 280

delphi源码转换为C++ Builder源码

本人80年代初出生,正好赶上电子信息高速发展的时代。记得刚接触的计算机高级语言就是PASCAL,但只是草草学了点语法。但开始接触C时,一发不可收拾,C->TBC->C++->BC++->VC++->GUN  C->C++ Builder->VC++ .NET,踏踏实实、一步一个脚印,程序员的人生乐趣在哪??? 最近拿到一个Delphi源码,准备在这个基础上进行扩充,但Delphi总是没有C用起来得

lyc96532的专栏 3948

五种语言写数组

c语言 #include<stdio.h> int main(){ int i,j; int a[10]; for(i=0;i<10;i++){ for(j=0;j<10;j++){ scanf("%d",&a[i][j]); } } } java public class Shuzu { public static void main(string args[] ...

weixin_45601812的博客 177

陈经韬Delphi资料

陈经韬Delphi资料2000~2001

LRC校验码 c,delphi c# 别人现成的

c:static unsigned char LRC(auchMsg,usDataLen)    unsigned char *auchMsg ; /* 要进行计算的消息 */    unsigned short usDataLen ; /* LRC 要处理的

2004v2004的专栏 3087

分享:用四十种语言分别写一个MD5算法 之11 Frink语言MD5算法

分享:用四十种语言分别写一个MD5算法 之11 Frink语言MD5算法 println[messageDigest["hello csdner", "MD5"]] 版权所有:百万商业圈 未经许可不得转载,有任何疑问请与我本人联系 QQ 99923309 Mail:bwsyq@bwsyq.com 更多详情>> 开源:完全自主研发搜索引擎1.0源代码及...

117

如何在 "万一的 Delphi 博客" 回复自动格式化的着色代码?

1、先提交回复, 第一次提交时先不要代码, 可有文字; 2、再修改回复, 修改时包其中的 &lt;br/&gt; 换行标记, 也可以用 &lt;br/&gt; 添加新的换行; 3、然后按下面方式提交回复: //Delphi 代码... //C/C++ 代码... //C# 代码... 注意: 重新开启才能看到效果;...

weixin_34113237的博客 74

三种语言的下载者源代码:C Delphi Vb

三种语言的下载者源代码:C Delphi Vb 2010年01月25日   查看文章   三种语言的下载者源代码:C Delphi Vb2007年10月27日 星期六 下午 07:20   Code Language : C   #include   #include   #include   #include //这里这个头文件是对ShellExecut...

gas17gas 201

我常去的编程技术网站

[汇编语言] http://www.asmcommunity.net/ http://www.masm32.com/ [Win32 Asm] http://www.cs.cmu.edu/~ralf/files.html [x86中断列表] http://www.nasm

特权份子的专栏 378

用XML实现编程语言间的互译

  编程语言间的隔阂虽然不如人类语言间的隔阂那么大,但确实是比较困挠程序员的一个问题。如果能通过某种方法实现象Delphi->c之类的转换,将是一件引人注目的事情,但这也许并不能使人们花大量的时间来实现这样的转换。我们来看,如果你是一个DelphiC++Builder的高手,你一定做过这两者间的转换吧。每天都有大量的人做这类事的事情将带来多么大的浪费呀。而且,如果真的有可能实现的话,无疑会为开发

smhpnuaa的专栏 1098

编程语言大盘点

开放源代码的必要性 在介绍编程语言之前,先说说开放源代码的必要性。现在,在软件生产领域存在巨大的智利浪费,大家把大量的精力用在编写别人已经实现的程序代码上。看看,文本编辑器有多少,看看ftp程序有多少,看看字处理程序有多少,这些程序虽然有差别,但主要的功能都是一样的。要实现个性化的功能,在已有的软件基础上修改会节省多少时间呀!而每个程序各编一套,又浪费多少时间?如果,没有这些重复的工作量,世

goustzhu地盘 2414

重写了博客上的代码着色脚本

目前支持 Delphi、C#、C/C++, 以后我学到什么会让它支持什么; 欢迎你也使用. 使用方法: 首先在 HTML 的 &lt;head&gt; 和 &lt;/head&gt; 之间加上: 然后: Delphi 代码 C# 代码 C 或 C++ 代码 样例: 代码着色测试 //Delphi 代码: progra...

weixin_34362875的博客 94
上一篇: FASM
下一篇: 老陈---Usb摄像头专题讲座
iiprogram
博客等级 码龄25年 1066粉丝 1515原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值