bin2obj.pp 5.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265
  1. program bin2obj;
  2. {
  3. This file is part of the Free Pascal run time library.
  4. Copyright (c) 1999-2000 by Michael Van Canneyt, member of the
  5. Free Pascal development team
  6. Binary file to include file converter.
  7. See the file COPYING.FPC, included in this distribution,
  8. for details about the copyright.
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  12. **********************************************************************}
  13. {$mode objfpc}
  14. uses classes,getopts, iostream,zstream,idea,sysutils,dos;
  15. var
  16. ConstName,
  17. OutFileName,
  18. UnitName : String;
  19. WriteAsciiData,
  20. CompressData,
  21. EnCodeData,
  22. CompileUnit,
  23. WriteHex : Boolean;
  24. Cryptkey : IDEAcryptKey;
  25. InStream,
  26. MemStream,
  27. CryptStream,
  28. CompStream : TStream;
  29. Procedure Usage;
  30. begin
  31. Writeln ('Usage: bin2obj [options] -c constname [infile] ');
  32. Writeln ('Where options is a combination of : ');
  33. Writeln (' -a write asciii data instead of bytes');
  34. Writeln (' -x write numerical values as hexadecimal numbers');
  35. Writeln (' -z compress data.');
  36. Writeln (' -e key encrypt data with key (must have 8 characters)');
  37. Writeln (' -o output filename');
  38. Writeln (' -u [name] make a unit instead of an include file (unit name is outfile)');
  39. Writeln (' -U [name] same as -u, and compile the unit. (requires outfile)');
  40. Halt(1);
  41. end;
  42. Procedure ProcessCommandLine;
  43. Var C : Char;
  44. I : longint;
  45. NeedUnitName : Boolean;
  46. begin
  47. OptErr:=False;
  48. ConstName:='';
  49. CompressData:=False;
  50. EncodeData:=False;
  51. CompileUnit:=False;
  52. UnitName:='';
  53. NeedUnitName:=False;
  54. WriteAsciiData:=False;
  55. WriteHex:=False;
  56. Repeat
  57. c:=GetOpt('ac:e:o:zhu::U::x');
  58. Case C of
  59. 'a' : WriteAsciiData:=True;
  60. 'c' : ConstName:=OptArg;
  61. 'h','?' : usage;
  62. 'z' : CompressData := True;
  63. 'x' : WriteHex := True;
  64. 'e' : begin
  65. EncodeData:=True;
  66. If Length(OptArg)<8 then
  67. Usage;
  68. For I:=0 to 7 do
  69. CryptKey[i]:=Ord(OptArg[I+1]);
  70. end;
  71. 'o' : OutFileName:=optArg;
  72. 'u','U':
  73. begin
  74. UnitName:=OptArg;
  75. If Length(UnitName)=0 then
  76. NeedUnitName:=True;
  77. If C='U' then
  78. CompileUnit:=True;
  79. end;
  80. end;
  81. until C=EndOfOptions;
  82. if ConstName='' then
  83. usage;
  84. If NeedUnitName then
  85. If Length (OutFileName)=0 then
  86. begin
  87. Writeln ('Error : cannot determine unitname from filename');
  88. Usage;
  89. end
  90. else
  91. UnitName:=ExtractFileName(OutFileName);
  92. if CompileUnit and (Length(OutFileName)=0) then
  93. usage;
  94. end;
  95. Function SetupInput : TStream;
  96. begin
  97. if OptInd=ParamCount then
  98. InStream:=TFileStream.Create(Paramstr(Optind),fmOpenRead)
  99. else
  100. InStream:=TIOStream(iosInput);
  101. Result:=InStream;
  102. end;
  103. Function SetupOutput : TStream;
  104. Var Key : ideaKey;
  105. begin
  106. MemStream:=TMemoryStream.Create;
  107. Result:=MemStream;
  108. If ComPressData then
  109. begin
  110. CompStream:=TCompressionStream.Create(cldefault,Result);
  111. Result:=CompStream;
  112. end;
  113. if EncodeData Then
  114. begin
  115. EnKeyIdea(CryptKey,Key);
  116. CryptStream:=TIDEAEncryptStream.Create(Key,Result);
  117. Result:=CryptStream;
  118. end;
  119. end;
  120. Procedure CopyStreams (Ins,Outs : TStream);
  121. Const BufSize = 1024;
  122. Var Buffer : Array[1..BufSize] of byte;
  123. Count : longint;
  124. begin
  125. repeat
  126. Count:=Ins.Read(Buffer,SizeOf(Buffer));
  127. If Count>0 then
  128. Outs.Write(Buffer,Count);
  129. until Count<SizeOf(Buffer);
  130. {
  131. freeing these streams will flush their buffers.
  132. Order is important !!!
  133. }
  134. CryptStream.Free;
  135. CompStream.Free;
  136. // Now Out stream has all data.
  137. end;
  138. Procedure WriteMemStream;
  139. Var OutStream : TStream;
  140. Procedure WriteStr(Const St : String);
  141. begin
  142. OutStream.Write(St[1],Length(St));
  143. end;
  144. Procedure WriteStrLn(Const St : String);
  145. Const
  146. {$ifdef unix}
  147. Eoln : String = #10;
  148. {$else}
  149. Eoln : String = #13#10;
  150. {$endif}
  151. begin
  152. OutStream.Write(St[1],Length(St));
  153. OutStream.Write(Eoln[1],Length(Eoln));
  154. end;
  155. Const Prefix = ' ';
  156. MaxLineLength = 72;
  157. Var I,Count : longint;
  158. b : byte;
  159. Line,ToAdd : String;
  160. begin
  161. If Length(OutFileName)=0 Then
  162. OutStream:=TIOStream.Create(iosOutput)
  163. else
  164. OutStream:=TFileStream.Create(OutFileName,fmCreate);
  165. If UnitName<>'' then
  166. begin
  167. WriteStrLn(Format('Unit %s;',[UnitName]));
  168. WriteStrLn('');
  169. WriteStrLn('Interface');
  170. WriteStrLn('');
  171. end;
  172. WriteStrLn('');
  173. WriteStrLn('Const');
  174. MemStream.Seek(0,soFromBeginning);
  175. Count:=MemStream.Size;
  176. If WriteAsciidata then
  177. WriteStrLn(Format(' %s : Array[0..%d] of char = (',[ConstName,Count-1]))
  178. else
  179. WriteStrLn(Format(' %s : Array[0..%d] of byte = (',[ConstName,Count-1]));
  180. Line:=Prefix;
  181. For I:=1 to Count do
  182. begin
  183. MemStream.Read(B,1);
  184. If Not WriteAsciiData then
  185. begin
  186. if WriteHex then
  187. ToAdd:=Format('$%2.2x',[b])
  188. else
  189. ToAdd:=Format('%3d',[b]);
  190. end
  191. else
  192. If (B in [32..127]) and not (B in [10,13,39]) then
  193. ToAdd:=''''+Chr(b)+''''
  194. else
  195. // ToAdd:=Format('''%s''',[Chr(b)]);
  196. begin
  197. if WriteHex then
  198. ToAdd:=Format('#$%x',[B])
  199. else
  200. ToAdd:=Format('#%d',[B]);
  201. end;
  202. If I<Count then
  203. ToAdd:=ToAdd+',';
  204. Line:=Line+ToAdd;
  205. If Length(Line)>=MaxLineLength Then
  206. begin
  207. WriteStrLn(Line);
  208. Line:=PreFix;
  209. end;
  210. end;
  211. WriteStrln(Line+');');
  212. If Length(UnitName)<>0 then
  213. begin
  214. WriteStrLn('');
  215. WriteStrLn('Implementation');
  216. WriteStrln('');
  217. WriteStrLn('end.')
  218. end;
  219. MemStream.Free;
  220. end;
  221. Procedure CompileTheUNit;
  222. begin
  223. Exec('ppc386',' -Un '+UnitName);
  224. end;
  225. begin
  226. ProcessCommandline;
  227. CopyStreams(SetupInput,SetupOutPut);
  228. WriteMemStream;
  229. If CompileUNit then
  230. CompileTheUnit;
  231. end.