OVL.LST 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673
  1. Listing:
  2. 1 MODULE ovl;
  3. 2 (* Copyright (C) 1987-1992 Clarion Software Corporation *)
  4. 3 IMPORT Lib,Str,FIO,IO,Storage;
  5. 4
  6. 5 (*%F _fdata*) Make program in XLarge or MThread model (*%E*)
  7. 6
  8. 7 CONST
  9. 8 MaxOverlay = 9;
  10. 9
  11. 10 TYPE
  12. 11 String = ARRAY [0..99] OF CHAR;
  13. ***** ^ not supported yet
  14. ***** ^ not supported yet
  15. 12
  16. 13 tUnit = RECORD
  17. 14 Name:String;
  18. 15 Start:LONGCARD;
  19. ***** ^ undeclared identifier
  20. 16 StartSeg:CARDINAL; (* == CARDINAL(Start DIV 16) *)
  21. 17 Diff:CARDINAL; (* in paras between new and old position *)
  22. 18 Overlay:[0..MaxOverlay];
  23. ***** ^ not supported yet
  24. 19 UnitPadding:ARRAY [1..128-( SIZE(String)+4+2+2+2 )] OF BYTE;
  25. ***** ^ undeclared identifier
  26. ***** ^ not supported yet
  27. ***** ^ not supported yet
  28. ***** ^ undeclared identifier
  29. 20 END;
  30. ***** ^ not supported yet
  31. 21
  32. 22 tfix=RECORD
  33. 23 locoff:SHORTCARD; (* high 4 bits = overlay number *)
  34. 24 locseg:CARDINAL;
  35. 25 target:CARDINAL;
  36. 26 END;
  37. ***** ^ not supported yet
  38. 27
  39. 28 texeheader = RECORD
  40. 29 magic : CARDINAL;
  41. 30 sizemod512 : CARDINAL;
  42. 31 sizediv512 : CARDINAL;
  43. 32 numrelocitem : CARDINAL;
  44. 33 headerparas : CARDINAL;
  45. 34 heapminparas : CARDINAL;
  46. 35 heapmaxparas : CARDINAL;
  47. 36 initialss : CARDINAL;
  48. 37 initialsp : CARDINAL;
  49. 38 checksum : CARDINAL;
  50. 39 initialip : CARDINAL;
  51. 40 initialcs : CARDINAL;
  52. 41 relocations : CARDINAL;
  53. 42 ovrlay : CARDINAL;
  54. 43 undocumented : CARDINAL;
  55. 44 (* relocation items follow *)
  56. 45 END;
  57. ***** ^ not supported yet
  58. 46
  59. 47 Str4 = ARRAY[0..3] OF CHAR ;
  60. ***** ^ not supported yet
  61. ***** ^ not supported yet
  62. 48
  63. 49
  64. 50 VAR
  65. 51 exefile,exefile1,mapfile,ovlfile,newmapfile:FIO.File;
  66. ***** ^ not supported yet
  67. 52
  68. 53 nmap:CARDINAL;
  69. 54 map:ARRAY [1..300] OF tUnit;
  70. ***** ^ not supported yet
  71. ***** ^ not supported yet
  72. 55
  73. 56 ovlheaders:ARRAY [0..MaxOverlay] OF RECORD
  74. ***** ^ not supported yet
  75. 57 Alloc: LONGCARD; (* total size *)
  76. ***** ^ undeclared identifier
  77. 58 Init: LONGCARD; (* size of initialised part *)
  78. ***** ^ undeclared identifier
  79. 59 nifix: CARDINAL;
  80. 60 nefix: CARDINAL;
  81. 61 copyr: Str4 ; (* used for checking overlay version *)
  82. 62 END;
  83. ***** ^ not supported yet
  84. 63
  85. 64 ovlfiles:ARRAY [0..MaxOverlay] OF CARDINAL;
  86. ***** ^ not supported yet
  87. ***** ^ not supported yet
  88. 65
  89. 66 PROCEDURE Erase(a:ARRAY OF CHAR);
  90. ***** ^ not supported yet
  91. 67 BEGIN
  92. 68 IF FIO.Exists(a) THEN FIO.Erase(a); END;
  93. ***** ^ not supported yet
  94. ***** ^ not supported yet
  95. ***** ^ not supported yet
  96. ***** ^ not supported yet
  97. ***** ^ not supported yet
  98. ***** ^ not supported yet
  99. 69 END Erase;
  100. ***** ^ not supported yet
  101. 70
  102. 71 PROCEDURE GiveBuf( f:FIO.File );
  103. ***** ^ not supported yet
  104. 72 TYPE buf = ARRAY [0..517] OF BYTE;
  105. ***** ^ not supported yet
  106. ***** ^ undeclared identifier
  107. 73 VAR bufp :POINTER TO buf;
  108. ***** ^ not supported yet
  109. 74 BEGIN
  110. 75 Storage.ALLOCATE(bufp,SIZE(buf));
  111. ***** ^ not supported yet
  112. ***** ^ not supported yet
  113. ***** ^ not supported yet
  114. ***** ^ undeclared identifier
  115. ***** ^ not supported yet
  116. 76 FIO.AssignBuffer(f,bufp^);
  117. ***** ^ not supported yet
  118. ***** ^ not supported yet
  119. ***** ^ not supported yet
  120. ***** ^ not supported yet
  121. 77 END GiveBuf;
  122. ***** ^ not supported yet
  123. 78
  124. 79 PROCEDURE ReadHex(s:ARRAY OF BYTE;i:CARDINAL):LONGCARD;
  125. ***** ^ undeclared identifier
  126. ***** ^ undeclared identifier
  127. 80 VAR res:LONGCARD; c:SHORTCARD;
  128. ***** ^ undeclared identifier
  129. 81 BEGIN
  130. 82 res := 0;
  131. ***** ^ not supported yet
  132. 83 LOOP
  133. 84 c := SHORTCARD(s[i]);
  134. ***** ^ not supported yet
  135. ***** ^ not supported yet
  136. 85 INC(i);
  137. ***** ^ undeclared identifier
  138. ***** ^ not supported yet
  139. 86 CASE CHAR(c) OF
  140. ***** ^ not supported yet
  141. 87 'A'..'F': c := c - ( SHORTCARD('A') - 10 ) ;
  142. ***** ^ not supported yet
  143. 88 | '0'..'9': c := c - SHORTCARD('0');
  144. ***** ^ not supported yet
  145. 89 ELSE EXIT;
  146. 90 END;
  147. 91 res := res * 16 + VAL(LONGCARD, c );
  148. ***** ^ not supported yet
  149. ***** ^ not supported yet
  150. ***** ^ undeclared identifier
  151. ***** ^ undeclared identifier
  152. ***** ^ not supported yet
  153. 92 END;
  154. 93 RETURN res;
  155. ***** ^ not supported yet
  156. 94 END ReadHex;
  157. ***** ^ not supported yet
  158. 95
  159. 96 PROCEDURE ReadMap;
  160. 97 CONST
  161. 98 delim = Str.CHARSET{' '};
  162. ***** ^ not supported yet
  163. ***** ^ not supported yet
  164. 99 VAR
  165. 100 done:BOOLEAN; i:CARDINAL;
  166. 101 sname,gname,token,line:String;
  167. 102 start:LONGCARD;
  168. 103 BEGIN
  169. 104 nmap := 0;
  170. 105 REPEAT
  171. 106 FIO.RdStr(mapfile,line) ;
  172. 107 UNTIL (line[0]<>CHAR(0)) AND (line[1]>='0') AND (line[1]<='9') ;
  173. 108 LOOP
  174. 109 (* IO.WrStr(line);IO.WrLn; *)
  175. 110 IF Str.Length(line) < 60 THEN EXIT END;
  176. 111
  177. 112 Str.Item( token, line, delim, 0 );
  178. 113 start := ReadHex( token,0 );
  179. 114
  180. 115 Str.Item( sname, line, delim, 3 );
  181. 116
  182. 117 Str.Item( gname, line, delim, 5 );
  183. 118
  184. 119 IF ( Str.Compare(gname,'(none)') = 0 ) THEN
  185. 120 gname := sname;
  186. 121 END;
  187. 122
  188. 123 IF ( nmap = 0 )
  189. 124 OR ( Str.Compare(gname,map[nmap].Name) <> 0 )
  190. 125 THEN
  191. 126 INC(nmap);
  192. 127 WITH map[nmap] DO
  193. 128 Name := gname;
  194. 129 Start := start;
  195. 130 StartSeg := CARDINAL(start DIV 16);
  196. 131 Overlay := 0;
  197. 132 END;
  198. 133 END;
  199. 134 FIO.RdStr(mapfile,line);
  200. 135 END;
  201. 136 map[nmap+1] := map[nmap]; (* sentinel *)
  202. 137 END ReadMap;
  203. 138
  204. 139 PROCEDURE too_small_check;
  205. 140 VAR i:CARDINAL;
  206. 141 BEGIN
  207. 142 FOR i := 1 TO nmap-1 DO
  208. 143 IF ( map[i+1].StartSeg = map[i].StartSeg )
  209. 144 AND ( map[i+1].Overlay <> map[i].Overlay ) THEN
  210. 145 IO.WrStr( map[i].Name);
  211. 146 IO.WrStr(' too small !!');
  212. 147 IO.WrLn;
  213. 148 HALT;
  214. 149 END;
  215. 150 END;
  216. 151 END too_small_check;
  217. 152
  218. 153 PROCEDURE ReadOvl;
  219. 154 VAR c:CHAR;
  220. 155
  221. 156 PROCEDURE nextc;
  222. 157 BEGIN
  223. 158 c := FIO.RdChar(ovlfile);
  224. 159 END nextc;
  225. 160
  226. 161 VAR
  227. 162 ovln:CARDINAL;
  228. 163 name:String;
  229. 164 i:CARDINAL;
  230. 165 BEGIN
  231. 166 LOOP
  232. 167 LOOP
  233. 168 nextc;
  234. 169 WHILE c <= ' ' DO
  235. 170 IF c = CHAR(1AH) THEN EXIT END;
  236. 171 nextc;
  237. 172 END;
  238. 173 IF c = ';' THEN (* comment *)
  239. 174 WHILE c >= ' ' DO nextc END ;
  240. 175 ELSE
  241. 176 EXIT ;
  242. 177 END ;
  243. 178 END ;
  244. 179 IF c = CHAR(1AH) THEN EXIT END;
  245. 180
  246. 181 ovln := 0;
  247. 182
  248. 183 WHILE ( c >= '0' ) AND ( c <= '9' ) DO
  249. 184 ovln := ovln*10 + ORD(c) - ORD('0');
  250. 185 nextc;
  251. 186 END;
  252. 187
  253. 188 WHILE c = ' ' DO nextc END;
  254. 189
  255. 190 i := 0;
  256. 191 WHILE ( c > ' ' ) DO
  257. 192 name[i] := c;
  258. 193 INC(i);
  259. 194 nextc;
  260. 195 END;
  261. 196 name[i] := CHAR(0);
  262. 197
  263. 198 (* search table *)
  264. 199 i := 0;
  265. 200 LOOP
  266. 201 INC(i);
  267. 202 IF i > nmap THEN
  268. 203 IO.WrStr('Segment/group name ');
  269. 204 IO.WrStr(name);
  270. 205 IO.WrStr(' not found');
  271. 206 IO.WrLn;
  272. 207 EXIT;
  273. 208 END;
  274. 209 WITH map[i] DO
  275. 210 IF Str.Compare( Name, name ) = 0 THEN
  276. 211 Overlay := ovln;
  277. 212 EXIT;
  278. 213 END;
  279. 214 END;
  280. 215 END;
  281. 216 END;
  282. 217 END ReadOvl;
  283. 218
  284. 219 VAR newseg_in_exe:BOOLEAN;
  285. 220
  286. 221 PROCEDURE newseg( seg,off:CARDINAL ):CARDINAL;
  287. 222 VAR loc:LONGCARD;
  288. 223 k:CARDINAL;
  289. 224 BEGIN
  290. 225 loc := 16*VAL(LONGCARD,seg) + VAL(LONGCARD,off);
  291. 226 k := 1;
  292. 227 (* search for location segment = k *)
  293. 228 WHILE ( k <= nmap ) AND ( loc >= map[k].Start ) DO INC(k) END;
  294. 229 DEC(k);
  295. 230 newseg_in_exe := ( map[k].Overlay = 0 );
  296. 231 RETURN seg - map[k].Diff;
  297. 232 END newseg;
  298. 233
  299. 234 PROCEDURE hex(n:CARDINAL):CHAR;
  300. 235 BEGIN
  301. 236 n := n MOD 16;
  302. 237 IF n > 9 THEN
  303. 238 RETURN CHAR( n + ORD('A') - 10 )
  304. 239 ELSE
  305. 240 RETURN CHAR( n + ORD('0') );
  306. 241 END;
  307. 242 END hex;
  308. 243
  309. 244 PROCEDURE EditMap;
  310. 245 VAR line:String;
  311. 246 i:CARDINAL;
  312. 247 seg,off:CARDINAL;
  313. 248 addr:LONGCARD;
  314. 249 BEGIN
  315. 250 FIO.Seek(mapfile,0);
  316. 251 LOOP
  317. 252 FIO.RdStr(mapfile,line);
  318. 253 newseg_in_exe := TRUE;
  319. 254 IF FIO.EOF THEN EXIT END;
  320. 255 IF ( line[0] = ' ' ) AND ( line[5] = ':' ) THEN
  321. 256 seg := CARDINAL(ReadHex(line,1));
  322. 257 off := CARDINAL(ReadHex(line,6));
  323. 258 seg := newseg( seg, off );
  324. 259 line[4] := hex(seg); seg := seg DIV 16;
  325. 260 line[3] := hex(seg); seg := seg DIV 16;
  326. 261 line[2] := hex(seg); seg := seg DIV 16;
  327. 262 line[1] := hex(seg); seg := seg DIV 16;
  328. 263 ELSIF ( line[0] = ' ' ) AND ( line[6] = 'H' ) THEN
  329. 264 addr := ReadHex(line,1);
  330. 265 seg := CARDINAL(addr DIV 16);
  331. 266 off := CARDINAL(addr) MOD 16;
  332. 267 seg := newseg( seg, off );
  333. 268 addr := LONGCARD(seg)*16 + LONGCARD(off) + ReadHex(line,15);
  334. 269 line[4] := hex(seg); seg := seg DIV 16;
  335. 270 line[3] := hex(seg); seg := seg DIV 16;
  336. 271 line[2] := hex(seg); seg := seg DIV 16;
  337. 272 line[1] := hex(seg); seg := seg DIV 16;
  338. 273 seg := CARDINAL(addr DIV 16);
  339. 274 line[11] := hex(seg); seg := seg DIV 16;
  340. 275 line[10] := hex(seg); seg := seg DIV 16;
  341. 276 line[9] := hex(seg); seg := seg DIV 16;
  342. 277 line[8] := hex(seg); seg := seg DIV 16;
  343. 278 END;
  344. 279 (* IF NOT newseg_in_exe THEN
  345. 280 IO.WrStr(line);
  346. 281 IO.WrLn;
  347. 282 END;
  348. 283 *)
  349. 284 IF newseg_in_exe THEN
  350. 285 IF line[0] <> CHAR(0) THEN
  351. 286 FIO.WrStr(newmapfile,line);
  352. 287 END;
  353. 288 FIO.WrLn(newmapfile);
  354. 289 END;
  355. 290 END;
  356. 291 END EditMap;
  357. 292
  358. 293 PROCEDURE PrintMap;
  359. 294 VAR i:CARDINAL;
  360. 295 BEGIN
  361. 296 FOR i := 1 TO nmap DO
  362. 297 WITH map[i] DO
  363. 298 IO.WrStr(' Start='); IO.WrLngCard(Start,6);
  364. 299 IO.WrStr(' Diff='); IO.WrCard(Diff,5);
  365. 300 IO.WrCard(Overlay,3);
  366. 301 IO.WrStr(' ');
  367. 302 IO.WrStr(Name);
  368. 303 IO.WrLn;
  369. 304 END;
  370. 305 END;
  371. 306 END PrintMap;
  372. 307
  373. 308 PROCEDURE ChkRead( VAR buf:ARRAY OF BYTE; count:CARDINAL );
  374. 309 BEGIN
  375. 310 IF FIO.RdBin( exefile, buf, count ) <> count THEN
  376. 311 IO.WrStr('?? on read');
  377. 312 HALT;
  378. 313 END;
  379. 314 END ChkRead;
  380. 315
  381. 316 PROCEDURE ChkRead1( VAR buf:ARRAY OF BYTE; count:CARDINAL );
  382. 317 BEGIN
  383. 318 IF FIO.RdBin( exefile1, buf, count ) <> count THEN
  384. 319 IO.WrStr('?? on read');
  385. 320 HALT;
  386. 321 END;
  387. 322 END ChkRead1;
  388. 323
  389. 324 PROCEDURE Copy(src,dst:CARDINAL; count:CARDINAL):CARDINAL;
  390. 325 VAR amount:CARDINAL; actual:CARDINAL;
  391. 326 buf:ARRAY [0..0FFFH] OF SHORTCARD;
  392. 327 res:CARDINAL;
  393. 328 BEGIN
  394. 329 res := 0;
  395. 330 WHILE count > 0 DO
  396. 331 amount := count;
  397. 332 IF amount > SIZE(buf) THEN
  398. 333 amount := SIZE(buf);
  399. 334 END;
  400. 335 actual := FIO.RdBin( src, buf, amount );
  401. 336 IF actual <> 0 THEN
  402. 337 FIO.WrBin( dst, buf, actual );
  403. 338 END;
  404. 339 DEC(count,amount);
  405. 340 INC(res,actual);
  406. 341 END;
  407. 342 RETURN res;
  408. 343 END Copy;
  409. 344
  410. 345 PROCEDURE LongCopy(src,dst:CARDINAL; count:LONGCARD);
  411. 346 VAR junk:CARDINAL;
  412. 347 BEGIN
  413. 348 WHILE count > 8000H DO
  414. 349 junk := Copy(src,dst,8000H);
  415. 350 DEC(count,8000H);
  416. 351 END;
  417. 352 junk := Copy( src,dst,CARDINAL(count) );
  418. 353 END LongCopy;
  419. 354
  420. 355
  421. 356 PROCEDURE resetexe;
  422. 357 VAR filename:ARRAY[0..255] OF CHAR;
  423. 358 BEGIN
  424. 359 Str.Concat( filename, Lib.CommandLine^, '.exe');
  425. 360 exefile := FIO.Create(filename);
  426. 361 END resetexe;
  427. 362
  428. 363 PROCEDURE MakeFix( k:CARDINAL; loc:LONGCARD; j:CARDINAL; target:CARDINAL; internalfix:BOOLEAN );
  429. 364 VAR
  430. 365 tmp:CARDINAL;
  431. 366 fix:tfix;
  432. 367 BEGIN
  433. 368 (*
  434. 369 IO.WrStr('k='); IO.WrCard(k,1);
  435. 370 IO.WrStr('j='); IO.WrCard(j,1);
  436. 371
  437. 372 IO.WrStr( ' map[k].Overlay=' ); IO.WrCard( ORD(map[k].Overlay),1 );
  438. 373 IO.WrStr( ' map[j].Overlay=' ); IO.WrCard( ORD(map[j].Overlay),1 );
  439. 374 IO.WrStr( ' loc=' ); IO.WrLngCard( loc, 1 );
  440. 375 IO.WrStr( ' target=' ); IO.WrCard( target, 1 );
  441. 376 IO.WrLn;
  442. 377 *)
  443. 378 IF internalfix THEN
  444. 379 IF map[k].Overlay = 0 THEN
  445. 380 IF map[j].Overlay <> 0 THEN
  446. 381 RETURN; (* overlay 0 requires only internal fixups to itself *)
  447. 382 END;
  448. 383 END;
  449. 384 INC( ovlheaders[map[k].Overlay].nifix );
  450. 385 tmp := j; j := k; k := tmp;
  451. 386 ELSE
  452. 387 IF map[j].Overlay = 0 THEN RETURN END;
  453. 388 IF map[j].Overlay = map[k].Overlay THEN RETURN END;
  454. 389 INC( ovlheaders[map[j].Overlay].nefix );
  455. 390 END;
  456. 391
  457. 392 fix.locoff := ( SHORTCARD(loc) MOD 16 ) + 16*SHORTCARD( map[k].Overlay );
  458. 393 fix.locseg := CARDINAL(loc DIV 16);
  459. 394 fix.target := target;
  460. 395 FIO.WrBin( ovlfiles[map[j].Overlay], fix, SIZE(fix) );
  461. 396
  462. 397 END MakeFix;
  463. 398
  464. 399 PROCEDURE Main;
  465. 400 VAR
  466. 401 exe:texeheader;
  467. 402 dummy:CARDINAL;
  468. 403 i,j,k:CARDINAL;
  469. 404 hsize:LONGCARD;
  470. 405 filename:String;
  471. 406 ext:ARRAY[0..3] OF CHAR;
  472. 407 pad:ARRAY[0..15] OF SHORTCARD;
  473. 408 padsize:CARDINAL;
  474. 409 copysize:CARDINAL;
  475. 410 target:CARDINAL;
  476. 411 internalfix:BOOLEAN;
  477. 412 fixlocabs:LONGCARD;
  478. 413 fsize:LONGCARD;
  479. 414 hpage:CARDINAL;
  480. 415 fix:tfix;
  481. 416 exefix:RECORD off,seg:CARDINAL END;
  482. 417 file:CARDINAL;
  483. 418
  484. 419 BEGIN
  485. 420 ChkRead( exe, SIZE(exe) );
  486. 421 hsize := VAL(LONGCARD,exe.headerparas)*16;
  487. 422
  488. 423 FOR i := 0 TO MaxOverlay DO
  489. 424 ovlfiles[i] := CARDINAL(-1);
  490. 425 WITH ovlheaders[i] DO
  491. 426 Alloc := 0;
  492. 427 Init := 0;
  493. 428 nifix := 0;
  494. 429 nefix := 0;
  495. 430 copyr := 'JPI' ;
  496. 431 END;
  497. 432 END;
  498. 433
  499. 434 FOR i := 0 TO 15 DO pad[i] := 0 END;
  500. 435
  501. 436 (* Now read through exe file redistributing segments *)
  502. 437 FIO.Seek( exefile, hsize );
  503. 438 FOR i := 1 TO nmap DO
  504. 439 WITH map[i] DO
  505. 440 WITH ovlheaders[Overlay] DO
  506. 441 file := ovlfiles[Overlay];
  507. 442 IF file = CARDINAL(-1) THEN
  508. 443 ext := '.ov ';
  509. 444 ext[3] := CHAR( Overlay+ORD('0') );
  510. 445 Str.Concat( filename, Lib.CommandLine^, ext );
  511. 446 file := FIO.Create( filename );
  512. 447 ovlfiles[Overlay] := file;
  513. 448 FIO.WrBin( file, pad, 16 );
  514. 449 END;
  515. 450 padsize := ( CARDINAL(Start) - CARDINAL(Alloc) ) MOD 16;
  516. 451 FIO.WrBin( file, pad, padsize );
  517. 452 INC( Init, VAL(LONGCARD, padsize) );
  518. 453 INC( Alloc, VAL(LONGCARD,padsize) );
  519. 454 Diff := CARDINAL(Start DIV 16) - CARDINAL(Alloc DIV 16);
  520. 455 copysize := CARDINAL(map[i+1].Start-Start);
  521. 456 INC( Init, VAL(LONGCARD, Copy( exefile, file, copysize ) ) );
  522. 457 INC( Alloc , VAL(LONGCARD,copysize) ) ;
  523. 458 END;
  524. 459 END;
  525. 460 END;
  526. 461
  527. 462 (* OK. We now have the overlay files, so work out the fixups *)
  528. 463
  529. 464
  530. 465 (* First allocate buffers for overlays *)
  531. 466 FOR i := 0 TO MaxOverlay DO
  532. 467 IF ovlfiles[i] <> CARDINAL(-1) THEN
  533. 468 GiveBuf( ovlfiles[i] );
  534. 469 END;
  535. 470 END;
  536. 471
  537. 472 FOR internalfix := FALSE TO TRUE DO
  538. 473 FIO.Seek( exefile1, VAL(LONGCARD,exe.relocations) );
  539. 474 FOR i := 1 TO exe.numrelocitem DO
  540. 475 ChkRead1( exefix, SIZE(exefix) );
  541. 476 fixlocabs := VAL(LONGCARD,exefix.off)+16*VAL(LONGCARD,exefix.seg);
  542. 477 FIO.Seek( exefile, hsize+fixlocabs);
  543. 478 ChkRead( target, SIZE(target) );
  544. 479
  545. 480 k := 1;
  546. 481 (* search for location segment = k *)
  547. 482 WHILE ( k <= nmap ) AND ( fixlocabs >= map[k].Start ) DO INC(k) END;
  548. 483 DEC(k);
  549. 484
  550. 485 (*
  551. 486 IO.WrCard(target,1);
  552. 487 IO.WrStr(' at ');
  553. 488 IO.WrLngCard(fixlocabs,1);
  554. 489 IO.WrLn;
  555. 490 *)
  556. 491
  557. 492 j := 0;
  558. 493 LOOP (* search for target segment = j *)
  559. 494 INC(j);
  560. 495 IF ( j > nmap ) OR ( target < map[j].StartSeg ) THEN
  561. 496 DEC(j);
  562. 497 MakeFix( k, fixlocabs - VAL(LONGCARD,map[k].Diff)*16,
  563. 498 j, target - map[j].Diff, internalfix );
  564. 499 EXIT;
  565. 500 END;
  566. 501 END;
  567. 502 END;
  568. 503 END;
  569. 504
  570. 505 (* Phew ! *)
  571. 506 (* Now save the headers *)
  572. 507
  573. 508 FOR i := 0 TO MaxOverlay DO
  574. 509 WITH ovlheaders[i] DO
  575. 510 file := ovlfiles[i];
  576. 511 IF file <> CARDINAL(-1) THEN
  577. 512 FIO.Seek( file, 0 );
  578. 513 FIO.WrBin( file, ovlheaders[i], 16 );
  579. 514 END;
  580. 515 END;
  581. 516 END;
  582. 517
  583. 518
  584. 519 (* Now rewrite exe file *)
  585. 520
  586. 521 resetexe;
  587. 522 hpage := ( 4*ovlheaders[0].nifix + SIZE(texeheader) + 511 ) DIV 512;
  588. 523 hsize := VAL(LONGCARD,hpage * 512);
  589. 524
  590. 525 FIO.Seek( exefile, VAL(LONGCARD,512*hpage) );
  591. 526 file := ovlfiles[0];
  592. 527 FIO.Seek( file, 16 );
  593. 528 LongCopy( file, exefile, ovlheaders[0].Init );
  594. 529
  595. 530 FIO.Seek( exefile, 0 );
  596. 531
  597. 532 exe.numrelocitem := ovlheaders[0].nifix;
  598. 533 exe.headerparas := hpage*32;
  599. 534 exe.relocations := SIZE(texeheader);
  600. 535 exe.initialcs := newseg(exe.initialcs,exe.initialip);
  601. 536 exe.initialss := newseg(exe.initialss,16);
  602. 537 fsize := FIO.Size(exefile);
  603. 538 exe.sizemod512 := CARDINAL(fsize) MOD 512;
  604. 539 exe.sizediv512 := CARDINAL((fsize+511) DIV 512);
  605. 540
  606. 541 FIO.WrBin( exefile, exe, SIZE(texeheader) );
  607. 542 FOR i := 1 TO ovlheaders[0].nifix DO
  608. 543 dummy := FIO.RdBin( file, fix, SIZE(fix) );
  609. 544 fixlocabs := VAL(LONGCARD,fix.locoff)+16*VAL(LONGCARD,fix.locseg);
  610. 545
  611. 546
  612. 547 FIO.Seek( exefile, hsize+fixlocabs);
  613. 548 FIO.WrBin( exefile, fix.target, 2 );
  614. 549 (*
  615. 550 IO.WrStr('Repatch at');
  616. 551 IO.WrLngCard( hsize+fixlocabs,1 );
  617. 552 IO.WrStr(' value ');
  618. 553 IO.WrCard( fix.target, 1 );
  619. 554 IO.WrLn;
  620. 555 *)
  621. 556 FIO.Seek( exefile, VAL(LONGCARD, SIZE(texeheader) + (i-1)*4 ) );
  622. 557 exefix.off := VAL(CARDINAL,fix.locoff);
  623. 558 exefix.seg := fix.locseg;
  624. 559 FIO.WrBin( exefile, exefix, SIZE(exefix) );
  625. 560 END;
  626. 561
  627. 562 (* close buffered ovl files *)
  628. 563 FOR i := 0 TO MaxOverlay DO
  629. 564 IF ovlfiles[i] <> CARDINAL(-1) THEN
  630. 565 FIO.Close( ovlfiles[i] );
  631. 566 END;
  632. 567 END;
  633. 568
  634. 569 END Main;
  635. 570
  636. 571 VAR filename:ARRAY[0..255] OF CHAR;
  637. 572
  638. 573 PROCEDURE init;
  639. 574 VAR
  640. 575 renname : FIO.PathStr ;
  641. 576 BEGIN
  642. 577 Str.Concat( filename, Lib.CommandLine^, '.exe');
  643. 578 exefile := FIO.Open(filename); (* no buffering because random access *)
  644. 579 exefile1 := FIO.Open(filename); GiveBuf(exefile1);
  645. 580 Str.Concat( filename, Lib.CommandLine^, '.ovl');
  646. 581 ovlfile := FIO.Open(filename); GiveBuf(ovlfile);
  647. 582 Str.Concat( filename, Lib.CommandLine^, '.map');
  648. 583 Str.Concat( renname, Lib.CommandLine^, '.omp');
  649. 584 Erase(renname) ;
  650. 585 FIO.Rename(filename,renname);
  651. 586 mapfile := FIO.Open(renname); GiveBuf(mapfile);
  652. 587 newmapfile := FIO.Create(filename); GiveBuf(newmapfile);
  653. 588 END init;
  654. 589
  655. 590 BEGIN
  656. 591 init;
  657. 592 ReadMap;
  658. 593 ReadOvl;
  659. 594 too_small_check;
  660. 595 Main;
  661. 596 (* PrintMap; *)
  662. 597 EditMap;
  663. 598 Str.Concat( filename, Lib.CommandLine^, '.ov0');
  664. 599 Erase(filename) ;
  665. 600 FIO.Close(newmapfile) ;
  666. 601 END ovl.
  667. 602
  668. 603
  669. 64 errors