DavidB
DavidB

Reputation: 177

How to add version informations to another exes in Delphi?

I want to add version informations (for a specific language) to another exes that does not have such informations (at all).

I tried with BeginUpdateResource/UpdateResource/EndUpdateResource but all I succedeed is to create "Version >> 1 >> Unknown string", not "Version >> 1 >> CompanyName/VersionNumber/Description..." and their values.

I searched on Google and here but I couldn't find something useful. Only incomplete code which I didn't know how to finish.

Thank you.

Edit:

Here is the code that I use now:

procedure SetExeInfo(const ExeName, ResName, ResValue: string);
var
   ResourceHandle: THandle;
   DataLength: DWord;
   Data: array of Char;
   Ok: Boolean;
   i: Integer;

begin
   ResourceHandle := BeginUpdateResource(pChar(ExeName), False);
   if (ResourceHandle <> 0) then
   begin
      DataLength := 8;
      SetLength(Data, 8);
      for i := 0 to 7 do
         Data[i] := 'z';
      Ok := True;
      if (not UpdateResource(ResourceHandle, RT_VERSION, pChar(#49#0), LANG_SYSTEM_DEFAULT {MakeLangID(LANG_NEUTRAL, SUBLANG_NEUTRAL)}, Data, DataLength)) then
         Ok := False;

      if (not EndUpdateResource(ResourceHandle, False)) then
         Ok := False;

      if (Ok) then
         ShowMessage('Update of resources successful!')
      else
         ShowMessage('Update of resources failed!');

   end;
end;

Last edit:

I haven't specified in my question that I can't transfer the informations from another exe because I haven't seen the point to do this, since I haven't said specifically that I take the version info from another exe. Looks I was wrong, sorry.

Upvotes: 2

Views: 1625

Answers (2)

Arnaud Bouchez
Arnaud Bouchez

Reputation: 43023

Here is some working code to add or replace the version numbers:

type
 VERSIONHEADER = packed record
   wLength: word;
   wValueLength: word;
   wType: word;
   Key: array[0..16] of WideChar;   // 'VS_VERSION_INFO'
   Version: VS_FIXEDFILEINFO;
 end;

  (...)
  var ToolPath: TFileName;    // = exe containing a reference version resource
      ExeFullPath: TFileName; // = destination exe
      Maj, Min: cardinal; // expected UPDATED Version number
      VersionHandle, VersionRes: THandle;
      VersionSize: DWORD;
      Version: array of AnsiChar;
      Ver: ^VERSIONHEADER;
  (...)
  VersionSize := GetFileVersionInfoSize(pointer(ToolPath),VersionHandle);
  if (VersionSize<>0) and (Maj<>0) then
  begin
    SetLength(Version,VersionSize);
    Ver := pointer(Version);
    GetFileVersionInfo(pointer(ToolPath),0,VersionSize,Ver);
    if Ver^.Version.dwSignature=$feef04bd then
    begin
      Ver^.Version.dwFileVersionMS := MAKELONG(Min,Maj);
      Ver^.Version.dwProductVersionMS := Ver^.Version.dwFileVersionMS;
      VersionRes := BeginUpdateResource(Pointer(ExeFullPath),False);
      UpdateResource(VersionRes,RT_VERSION,MAKEINTRESOURCE(VS_VERSION_INFO),
        1033,Ver,VersionSize);
      EndUpdateResource(VersionRes,false);
    end;
  end;

It will add or update the numeric version numbers of an existing executable (ExeFullPath), replacing it with a supplied executable resource (ToolPath - may be paramstr(0) to copy some existing generic version information, or even ExeFullPath to update the version numbers).

Upvotes: 4

Roman Ryltsov
Roman Ryltsov

Reputation: 69632

RT_VERSION resource is not just eight bytes long. It's VERSIONINFO instead, with fixed size and variable strings. See VERSIONINFO resource - MSDN for details.

CodeProject has some sample code for you: Updating version information at run-time.

Upvotes: 2

Related Questions