2012-04-13 11 views
1

どうすればその行をC++で記述できますか? Delphiコードで1つのデルファイコード行をC++に変換

(このコードはここに掲載されていない)私は、ファイルをexeファイルにするいくつかの情報をとC++のコードで満たされ、そのレコードを書き込みます私はthhisレコードを読んで、構造体に

を情報を渡します。これは、コードですデルファイ

​​

C++コード(残りはOKであると思います)私の悪い英語のための

struct TSettings{ 
    char sFileName[50]; 
    byte siInstallFolder; 
    bool bRunFile; 
    ... 
} Settings; 

... 
DWORD i; 
LPBYTE sZdData; 

     ZeroMemory(&Settings, sizeof(TSettings)); 
     Settings = ????? // im failing here i dunno what to do // i need same as in delphi code above 

とsory .. :(

これは、ここでDelphiコード

function GetInfoSettings(FileName: String; // filename from where to get data 
         var lpData: PChar; // where to write data 
         var dwSettingsLen: DWORD // returns the length of all bound files 
         ): Boolean; 
var 
    hFile: THandle; 
    DosHeader: TImageDosHeader; 
    NtHeaders: TImageNtHeaders; 
    SectionHeader: TImageSectionHeader; 
    dwReadBytes, dwOrginalFileSize, dwFileSize, dwSettingsLength: DWORD; 
begin 
    Result := False; 
    hFile := Createfile(PChar(FileName), GENERIC_READ, FILE_SHARE_READ, nil, OPEN_EXISTING, 0, 0); 
    SetFilePointer(hFile, 0, nil, FILE_BEGIN); 
    ReadFile(hFile, DosHeader, sizeof(DosHeader), dwReadBytes, nil); 
    if dwReadBytes = sizeof(DosHeader) then 
    begin 
    SetFilePointer(hFile, DosHeader._lfanew, nil, FILE_BEGIN); 
    ReadFile(hFile, NtHeaders, sizeof(NtHeaders), dwReadBytes, nil); 
    if dwReadBytes = sizeof(NtHeaders) then 
    begin 
     SetFilePointer(hFile, sizeof(SectionHeader) * (NtHeaders.FileHeader.NumberOfSections -1), nil, FILE_CURRENT); 
     ReadFile(hFile, SectionHeader, sizeof(SectionHeader), dwReadBytes, nil); 
     dwOrginalFileSize := SectionHeader.PointerToRawData + SectionHeader.SizeOfRawData; 
     dwFileSize := GetFileSize(hFile, nil); 
     dwSettingsLength := dwFileSize - dwOrginalFileSize; 
     if dwSettingsLength > 0 then 
     begin 
     SetFilePointer(hFile, dwOrginalFileSize, nil, FILE_BEGIN); 
     GetMem(lpData, dwSettingsLength); 
     ReadFile(hFile, lpData^, dwSettingsLength, dwReadBytes, nil); 
     if dwReadBytes = dwSettingsLength then 
     begin 
      Result := True; 
      dwSettingsLen := dwSettingsLength; 
     end; 
     end; 
    end; 
    end; 
    CloseHandle(hFile); 
end; 

とある私はここで私、//はすでに行われているどのくらいのバイトが保存されます

VAR ...情報またはバインドさファイルを取得。.. dwDaSize:DWORD; //すべてのセクションの後のデータの長さ。 dwFilenaam、sFileName:string; sZdData:PChar; //ここでは多分(私はこのコードはゴミLOLを探します知っている)ファイルが抽出されます「EOF」(全区間のデータの終わり) //ファイル名の後にすべてのデータ..

Settings: Tsettings; 


// writting 
    hFile: THandle; 
    lpNumberOfBytesWritten: DWORD; 
begin 
    GetMem(dwFilenaam, MAX_PATH); 
    GetModuleFileName(GetModuleHandle(nil), dwFilenaam, MAX_PATH); 
    if GetInfos(dwFilenaam, sZdData, dwDaSize) then 
    begin 
    i := 0; 
    repeat 

     ZeroMemory(@Settings, sizeof(Tsettings)); 
     settings := Tsettings(Pointer(@sZdData[i])^); 

私の試みとなりますない?

bool getSettingsInfo(LPSTR FileName, LPBYTE lpdata, DWORD dwSettingsLen) 
{ 
    HANDLE HandleFile ; 
    DWORD dwReadBytes; 
    DWORD dwOrginalFileSize; 
    DWORD dwFileSize; 
    DWORD dwSettingsLength; 
    PIMAGE_DOS_HEADER pidh ; 
    PIMAGE_NT_HEADERS pinh ; 
    PIMAGE_SECTION_HEADER pish; 

    return false; 
    HandleFile = CreateFile(FileName, GENERIC_READ, FILE_SHARE_READ, 0,OPEN_EXISTING,0, NULL); 
    SetFilePointer(HandleFile, 0,0, FILE_BEGIN); 
     ReadFile(HandleFile, pidh, sizeof(pidh), &dwReadBytes,NULL); 
    if (dwReadBytes == sizeof(pidh)) 
    { 
    SetFilePointer(HandleFile, pidh->e_lfanew , NULL, FILE_BEGIN); 
    ReadFile(HandleFile, pidh,sizeof(pinh), &dwReadBytes, NULL); 
    if (dwReadBytes == sizeof(pinh)) 
    { 
     SetFilePointer(HandleFile, sizeof(pish) * (pinh->FileHeader.NumberOfSections -1), NULL, FILE_CURRENT); 
     ReadFile(HandleFile, pish, sizeof(pinh), &dwReadBytes, NULL); 
     dwOrginalFileSize = pish->PointerToRawData + pish->SizeOfRawData; 
     dwFileSize = GetFileSize(HandleFile, NULL); 
     dwSettingsLength = dwFileSize - dwOrginalFileSize; 
     if (dwSettingsLength > 0) 
     { 

     SetFilePointer(HandleFile, dwOrginalFileSize, NULL, FILE_BEGIN); 
     realloc(lpdata, dwSettingsLength); 
     ReadFile(HandleFile, lpdata, dwSettingsLength, &dwReadBytes, NULL); 
     if (dwReadBytes == dwSettingsLength) 
     { 
     return true; 
      dwSettingsLen = dwSettingsLength; 
     } 
     } 
    } 
    } 
    CloseHandle(HandleFile); 
} 

それが何の情報を抽出するためのコード...

DWORD i; // here will be saved how much bytes are already done .. 
    DWORD dwDaSize; // length of data after all sections .. 

    LPSTR dwFilenaam; 
    LPBYTE sZdData; // here will be all data after "EOF" (End of all sections data) 
    LPSTR sFileName;// the filename where the file will be extracted .. 

    char * Installpath; 
    char * buffer; 

    HFILE hFile; 
    DWORD lpNumberOfBytesWritten; 

    memset(dwFilenaam,0, MAX_PATH); 
    GetModuleFileName(GetModuleHandle(NULL), dwFilenaam, MAX_PATH); 
    if (getSettingsInfo(dwFilenaam, sZdData, dwDaSize) == true) 
    { 
     i = 0; 
    // REPEAT 


     ZeroMemory(&Settings, sizeof(TSettings)); 

Settings = ??? 
+1

sFileName [0]は文字列の長さを保持するため、Delphiの短い文字列(String [50])のサイズは51バイトです。 –

+0

+1のファンキーなコード。 –

+0

省略したコードの一部を '...'で掲示する必要があります。どこかで、コンテンツが 'sZdData'に割り当てられていました。そのコードには他の情報があります。 –

答えて

0
struct TSettings{ 
    uchar length ; // shortstrings have an implicit length byte 
    char sFileName[50]; 
    byte siInstallFolder; 
    bool bRunFile; // one byte, 1=true, 0=false any other value undefined 
    ... 
    } Settings; 


    DWORD i; 
    LPBYTE sZdData; 

    ZeroMemory(&Settings, sizeof(TSettings)); 

    literally it is something like 
    Settings = (struct Settings) (*((void *)&sZDData[i]) 

    essentially it does 

    memcpy (&sZDData[i],&settings,sizeof(TSettings)); 

はsZSdataのi番目の要素(@sZDDATA [i])とのアドレスを取得し、それをキャストです型なしのポインタ。 (^ Cの接頭辞演算子として*)(これは基本的にはその結果です。) (void)ptrが指すアドレスであり、長さのデータが付いていないメモリのブロックです)。

これが設定に割り当てられている場合は、そのアドレスからlvalue(設定)までのlvalue(= sizeof(設定))バイトのサイズだけ移動することを意味します。

これは非常にファンキーな構造で、以前見たことがあるかわかりません。私はDelphiとFPCの両方のasmレベルにチェックし、同じ動作をしました。

+0

これは、Delphiコードがまったく何をするのではなく、C++コードが行うべきことではありません。関係するmemcpyはありません。これは、ポインタ 'sZdData'によって参照される内容のレコードへの直接型変換です。 IOWでは、 'TSettings'変数の内容を' sZdData [i] 'アドレスのメモリブロックに割り当てます(同じ場所への型付きポインタを作成します)。 「移動」や「コピー」はまったくありません。投稿されたコードでは、 'Settings'と' sZdData [i] 'は同じメモリブロックを参照しています。 –

+0

iveはすべてのコードを追加しますmybeそれはあなたに私が必要なものを理解するのに役立つ人たちのために感謝します – user1332636

+0

投稿は「本質的に」と言いました。それは読者のためにそれを簡素化することを意味した。実際にはインライン・リペアです。 movsd + movsw/bステートメントが必要な場合は、私はCのためにそれを表示する方法はわかりません。あなたは説明が間違っています。これはブロック/ TO/TSettingsの値を割り当てますが、それ以外の方法ではありません。私が(追加の前に)見たコードでは、szddataが何を指しているかを知る方法がありませんでした。私はそれが無関係なファイルバッファであると仮定しました。 –

0

それは、DelphiよりもCで簡単にする必要があります:

typedef struct 
{ 
    uchar length ; // shortstrings have an implicit length byte 
    char sFileName[50]; 
    byte siInstallFolder; 
    bool bRunFile; // one byte, 1=true, 0=false any other value undefined 
    ... 
} TSettings; 

TSettings settings; 
DWORD i; 
LPBYTE sZdData; 

settings = *(TSettings*)(&sZdData[i]); 

は、これは、TSettings構造を割り当てるのではなく、理由鋳物、memcpyのを呼び出します。あなたはTSettingsへのポインタを使用する場合は、コピーせずにアクセスすることができます。

TSettings* pSettings; 
DWORD i; 
LPBYTE sZdData; 

pSettings = (TSettings*)(&sZdData[i]); 
printf("%d\n", pSettings->siInstallFolder); // example 

ところで、位置合わせのため注意してください。アイテム間のギャップのために、構造体の合計サイズが予想を超えることがあります。

+0

Btwほぼすべての32/64ビットコンパイラは、パスカル。この例は複雑です。 –

関連する問題