mk68kreg.pp 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308
  1. {
  2. Copyright (c) 1998-2002 by Peter Vreman and Florian Klaempfl
  3. Convert spreg.dat to several .inc files for usage with
  4. the Free pascal compiler
  5. See the file COPYING.FPC, included in this distribution,
  6. for details about the copyright.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  10. **********************************************************************}
  11. {$mode objfpc}
  12. program mkspreg;
  13. const Version = '1.00';
  14. max_regcount = 200;
  15. var s : string;
  16. i : longint;
  17. line : longint;
  18. regcount:byte;
  19. regcount_bsstart:byte;
  20. names,
  21. regtypes,
  22. supregs,
  23. numbers,
  24. stdnames,
  25. gasnames,
  26. stabs : array[0..max_regcount-1] of string[63];
  27. regnumber_index,
  28. std_regname_index,gas_regname_index : array[0..max_regcount-1] of byte;
  29. function tostr(l : longint) : string;
  30. begin
  31. str(l,tostr);
  32. end;
  33. function readstr : string;
  34. begin
  35. result:='';
  36. while (s[i]<>',') and (i<=length(s)) do
  37. begin
  38. result:=result+s[i];
  39. inc(i);
  40. end;
  41. end;
  42. procedure readcomma;
  43. begin
  44. if s[i]<>',' then
  45. begin
  46. writeln('Missing "," at line ',line);
  47. writeln('Line: "',s,'"');
  48. halt(1);
  49. end;
  50. inc(i);
  51. end;
  52. procedure skipspace;
  53. begin
  54. while (s[i] in [' ',#9]) do
  55. inc(i);
  56. end;
  57. procedure openinc(out f:text;const fn:string);
  58. begin
  59. writeln('creating ',fn);
  60. assign(f,fn);
  61. rewrite(f);
  62. writeln(f,'{ don''t edit, this file is generated from m68kreg.dat }');
  63. end;
  64. procedure closeinc(var f:text);
  65. begin
  66. writeln(f);
  67. close(f);
  68. end;
  69. procedure build_regnum_index;
  70. var h,i,j,p,t:byte;
  71. begin
  72. {Build the registernumber2regindex index.
  73. Step 1: Fill.}
  74. for i:=0 to regcount-1 do
  75. regnumber_index[i]:=i;
  76. {Step 2: Sort. We use a Shell-Metzner sort.}
  77. p:=regcount_bsstart;
  78. repeat
  79. for h:=0 to regcount-p-1 do
  80. begin
  81. i:=h;
  82. repeat
  83. j:=i+p;
  84. if numbers[regnumber_index[j]]>=numbers[regnumber_index[i]] then
  85. break;
  86. t:=regnumber_index[i];
  87. regnumber_index[i]:=regnumber_index[j];
  88. regnumber_index[j]:=t;
  89. if i<p then
  90. break;
  91. dec(i,p);
  92. until false;
  93. end;
  94. p:=p shr 1;
  95. until p=0;
  96. end;
  97. procedure build_std_regname_index;
  98. var h,i,j,p,t:byte;
  99. begin
  100. {Build the registernumber2regindex index.
  101. Step 1: Fill.}
  102. for i:=0 to regcount-1 do
  103. std_regname_index[i]:=i;
  104. {Step 2: Sort. We use a Shell-Metzner sort.}
  105. p:=regcount_bsstart;
  106. repeat
  107. for h:=0 to regcount-p-1 do
  108. begin
  109. i:=h;
  110. repeat
  111. j:=i+p;
  112. if stdnames[std_regname_index[j]]>=stdnames[std_regname_index[i]] then
  113. break;
  114. t:=std_regname_index[i];
  115. std_regname_index[i]:=std_regname_index[j];
  116. std_regname_index[j]:=t;
  117. if i<p then
  118. break;
  119. dec(i,p);
  120. until false;
  121. end;
  122. p:=p shr 1;
  123. until p=0;
  124. end;
  125. procedure build_gas_regname_index;
  126. var h,i,j,p,t:byte;
  127. begin
  128. {Build the registernumber2regindex index.
  129. Step 1: Fill.}
  130. for i:=0 to regcount-1 do
  131. gas_regname_index[i]:=i;
  132. {Step 2: Sort. We use a Shell-Metzner sort.}
  133. p:=regcount_bsstart;
  134. repeat
  135. for h:=0 to regcount-p-1 do
  136. begin
  137. i:=h;
  138. repeat
  139. j:=i+p;
  140. if gasnames[gas_regname_index[j]]>=gasnames[gas_regname_index[i]] then
  141. break;
  142. t:=gas_regname_index[i];
  143. gas_regname_index[i]:=gas_regname_index[j];
  144. gas_regname_index[j]:=t;
  145. if i<p then
  146. break;
  147. dec(i,p);
  148. until false;
  149. end;
  150. p:=p shr 1;
  151. until p=0;
  152. end;
  153. procedure read_spreg_file;
  154. var infile:text;
  155. begin
  156. { open dat file }
  157. assign(infile,'m68kreg.dat');
  158. reset(infile);
  159. while not(eof(infile)) do
  160. begin
  161. { handle comment }
  162. readln(infile,s);
  163. inc(line);
  164. while (s[1]=' ') do
  165. delete(s,1,1);
  166. if (s='') or (s[1]=';') then
  167. continue;
  168. i:=1;
  169. names[regcount]:=readstr;
  170. readcomma;
  171. regtypes[regcount]:=readstr;
  172. readcomma;
  173. supregs[regcount]:=readstr;
  174. readcomma;
  175. stdnames[regcount]:=readstr;
  176. readcomma;
  177. gasnames[regcount]:=readstr;
  178. readcomma;
  179. stabs[regcount]:=readstr;
  180. { Create register number }
  181. if supregs[regcount][1]<>'$' then
  182. begin
  183. writeln('Missing $ before number, at line ',line);
  184. writeln('Line: "',s,'"');
  185. halt(1);
  186. end;
  187. numbers[regcount]:=regtypes[regcount]+'0000'+copy(supregs[regcount],2,255);
  188. if i<length(s) then
  189. begin
  190. writeln('Extra chars at end of line, at line ',line);
  191. writeln('Line: "',s,'"');
  192. halt(1);
  193. end;
  194. inc(regcount);
  195. if regcount>max_regcount then
  196. begin
  197. writeln('Error: Too much registers, please increase maxregcount in source');
  198. halt(2);
  199. end;
  200. end;
  201. close(infile);
  202. end;
  203. procedure write_inc_files;
  204. var
  205. norfile,stdfile,gasfile,supfile,
  206. numfile,stabfile,confile,
  207. rnifile,srifile,grifile:text;
  208. first:boolean;
  209. begin
  210. { create inc files }
  211. openinc(confile,'r68kcon.inc');
  212. openinc(supfile,'r68ksup.inc');
  213. openinc(numfile,'r68knum.inc');
  214. openinc(stdfile,'r68kstd.inc');
  215. openinc(gasfile,'r68kgas.inc');
  216. openinc(stabfile,'r68ksta.inc');
  217. openinc(norfile,'r68knor.inc');
  218. openinc(rnifile,'r68krni.inc');
  219. openinc(srifile,'r68ksri.inc');
  220. openinc(grifile,'r68kgri.inc');
  221. first:=true;
  222. for i:=0 to regcount-1 do
  223. begin
  224. if not first then
  225. begin
  226. writeln(numfile,',');
  227. writeln(stdfile,',');
  228. writeln(gasfile,',');
  229. writeln(stabfile,',');
  230. writeln(rnifile,',');
  231. writeln(srifile,',');
  232. writeln(grifile,',');
  233. end
  234. else
  235. first:=false;
  236. writeln(supfile,'RS_',names[i],' = ',supregs[i],';');
  237. writeln(confile,'NR_'+names[i],' = ','tregister(',numbers[i],')',';');
  238. write(numfile,'tregister(',numbers[i],')');
  239. write(stdfile,'''',stdnames[i],'''');
  240. write(gasfile,'''',gasnames[i],'''');
  241. write(stabfile,stabs[i]);
  242. write(rnifile,regnumber_index[i]);
  243. write(srifile,std_regname_index[i]);
  244. write(grifile,gas_regname_index[i]);
  245. end;
  246. write(norfile,regcount);
  247. close(confile);
  248. close(supfile);
  249. closeinc(numfile);
  250. closeinc(stdfile);
  251. closeinc(gasfile);
  252. closeinc(stabfile);
  253. closeinc(norfile);
  254. closeinc(rnifile);
  255. closeinc(srifile);
  256. closeinc(grifile);
  257. writeln('Done!');
  258. writeln(regcount,' registers processed');
  259. end;
  260. begin
  261. writeln('Register Table Converter Version ',Version);
  262. line:=0;
  263. regcount:=0;
  264. read_spreg_file;
  265. regcount_bsstart:=1;
  266. while 2*regcount_bsstart<regcount do
  267. regcount_bsstart:=regcount_bsstart*2;
  268. build_regnum_index;
  269. build_std_regname_index;
  270. build_gas_regname_index;
  271. write_inc_files;
  272. end.