簡體   English   中英

在Delphi XE4 Win64平台中無法使用由cl.exe編譯的C.OBJ文件

[英]Unable to use C's .OBJ files compiled by cl.exe in Delphi XE4 Win64 platform

我想將7Zip的SDK轉換為Delphi / Pascal的單位文件。 首先,我嘗試使用用於Win32平台的BCC32.exe編譯C文件:

bcc32.exe -c -D_LZMA_PROB32 -D_WIN32 -v -y Threads.c LzFind.c LzFindMt.c LzmaDec.c LzmaEnc.c

它產生的.OBJ文件很少,而且我可以在Delphi單元中毫無問題地使用這些對象。

unit Threads;

interface

uses System.Win.Crtl, Winapi.Windows, LzmaTypes, System.Classes;

{$Z4}
type
  TCEvent = THandle;

  TCSemaphore = THandle;

  TCCriticalSection = TRTLCriticalSection;

  TCAutoResetEvent = TCEvent;

  TCThread = THandle;

  TThread_Func_Type = Pointer;

function __beginthreadex(__security_attr: Pointer; __stksize: Cardinal; __start:
    TThread_Func_Type; __arg: Pointer; __create_flags: Cardinal; var
    __thread_id: Cardinal): Cardinal; cdecl; external msvcrt name _PU +
    '_beginthreadex';

function _Event_Reset(var p: TCEvent): TWRes; cdecl; external name _PU +
    'Event_Reset';

function _Event_Set(var p: TCEvent): TWRes; cdecl; external name _PU +
    'Event_Set';

function _Handle_WaitObject(h: THandle): TWRes; cdecl; external name _PU +
    'Handle_WaitObject';

function _Semaphore_Release1(var p: TCSemaphore): TWRes; cdecl; external name
    _PU + 'Semaphore_Release1';

function _HandlePtr_Close(var h: THandle): TWRes; cdecl; external name _PU +
    'HandlePtr_Close';

function _CriticalSection_Init(var p: TCCriticalSection): TWRes; cdecl; external
    name _PU + 'CriticalSection_Init';

function _AutoResetEvent_CreateNotSignaled(var p: TCAutoResetEvent): TWRes;
    cdecl; external name _PU + 'AutoResetEvent_CreateNotSignaled';

function _Semaphore_Create(var p: TCSemaphore; initCount: UInt32; maxCount:
    UInt32): TWRes; cdecl; external name _PU + 'Semaphore_Create';

function _Thread_Create(var p: TCThread; func: TThread_Func_Type; param:
    LPVOID): TWRes; cdecl; external name _PU + 'Thread_Create';

implementation

{$ifdef Win64}
  {$L Win64\Threads.o}
{$else}
  {$L Win32\Threads.obj}
{$endif}

end.

然后,我嘗試使用用於Win64平台的BCC64.exe編譯這些目標文件:

bcc64.exe -c -D_LZMA_PROB32 -D_WIN64 -v -y Threads.c LzFind.c LzFindMt.c LzmaDec.c LzmaEnc.c

這次,它生成的.o文件很少,但是在編譯Delphi單元時出現錯誤:

[dcc64 Fatal Error] LzFind.pas(128): F2084 Internal Error: AV0756F5D3-R2D06DB90-0

我了解到,Delphi Win64可以識別的目標文件格式是64位COFF,而BCC64.exe可以生成ELF64格式。

然后,我嘗試使用Microsoft Windows SDK中的cl.exe生成Win32和Win64 .OBJ文件,

cl.exe -c -D_LZMA_PROB32 -D_WIN32 Threads.c LzFind.c LzFindMt.c LzmaDec.c LzmaEnc.c

x86_amd64\cl.exe -c -D_LZMA_PROB32 -D_WIN64 Threads.c LzFind.c LzFindMt.c LzmaDec.c LzmaEnc.c

但我得到這些錯誤:

[dcc32 Error] Threads.pas(64): E2065 Unsatisfied forward or external declaration: '__imp__CloseHandle@4'
[dcc32 Error] Threads.pas(64): E2065 Unsatisfied forward or external declaration: '__imp__GetLastError@0'
[dcc32 Error] Threads.pas(64): E2065 Unsatisfied forward or external declaration: '__imp__InitializeCriticalSection@4'

有什么想法如何使用cl.exe生成可以由Win32和Win64平台中的Delphi單元編譯的.OBJ文件嗎?

這有點令人困惑,但是在Delphi中,

  • 對於64位,您可以使用由Microsoft的64位編譯器生成的64位COFF文件。 據報道,Delphi XE6 64位也能夠鏈接64位ELF文件,因為C ++ Builder 64位會生成它們。

  • 對於32位,您可以使用C ++ Builder生成的32位OMF C對象文件。 Delphi XE2和更高版本(請參閱David Heffernan的評論中的此鏈接 )也允許您鏈接到32位COFF。

有關此主題的更多信息: 在Delphi中使用C對象文件

因此,從Delphi XE6開始,您實際上可以使用C ++ Builder再次為兩個平台生成可與Delphi鏈接的目標文件。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM