home *** CD-ROM | disk | FTP | other *** search
/ Oakland CPM Archive / oakcpm.iso / cpmug / cpmug014.ark / REL1.ASM < prev    next >
Encoding:
Assembly Source File  |  1984-04-29  |  9.5 KB  |  448 lines

  1. ; REL1.ASM
  2. ;
  3. ;
  4. ; THIS IS A MODIFIED SOURCE TEXT OF THE PROGRAM PORTION OF
  5. ; RELOC.COM. THE COM FILE ALSO CONTAINS A COPY OF CP/M,
  6. ; BEGINNING AT 900H, AND A RELOCATION TABLE, PRESENTLY
  7. ; BEGINNING AT 2100H.
  8. ;
  9. ; THIS VERSION OF RELOC DIFFERS FROM THE STANDARD VERSION IN
  10. ; THAT THE SERIAL-NUMBER CHECKS HAVE BEEN REMOVED. IT COPIES THE
  11. ; SERIAL NUMBER FROM THE USER'S BDOS INTO THE RELOCATED SYSTEM, THUS
  12. ; INSURING COMPATIBILITY.  IN ADDITION, THIS VERSION CAN BE RUN UNDER
  13. ; DDT WITHOUT CAUSING A "SYNCRONIZATION" ERROR.
  14. ;
  15. ;
  16.     ORG    100H
  17. ;
  18. ; LOCATIONS OF INFORMATION FROM COMMAND LINE, PUT IN DEFAULT BUFFERS
  19. ; BY CCP:
  20. ;
  21. NAME1    EQU    5DH    ;FIRST "FILENAME" (NO. OF K)
  22. NAME2    EQU    6DH    ;2ND "FILENAME" (BLANK OR *)
  23. ;
  24. ENTRY    EQU    5    ;LOCATION OF JUMP TO BDOS
  25. REBOOT    EQU    0    ;LOCATION TO JUMP TO FOR REBOOT
  26. SYSTEM    EQU    900H    ;WHERE RELOC'S COPY OF SYSTEM RESIDES
  27. SERIALB    EQU    1300H    ;START OF BDOS SERIAL NUMBER IN THAT SYSTEM
  28. SERIALC    EQU    0CA0H    ;START OF CCP SERIAL NUMBER IN THAT SYSTEM
  29. SIZE    EQU    801H    ;WHERE LENGTH OF SYSTEM IS STORED
  30. ;
  31. ;
  32. CR    EQU    0DH
  33. LF    EQU    0AH
  34. ;
  35. ;
  36. ;
  37. ;
  38. FIRST:    JMP    START
  39. ;
  40. ;
  41. ;
  42. ;
  43.     ORG    012CH
  44. ;
  45. START:    LXI    SP,800H
  46. ;
  47. ;
  48.     LXI    D,NAME1
  49.     LDAX    D    ;GET FIRST CHAR. OF WHAT IS ASSUMED TO BE NO. OF K
  50.     CPI    ' '
  51.     JZ    UNSPEC    ;JUMP IF NO NUMBER TYPED IN COMMAND
  52.     CPI    '?'
  53.     JZ    UNSPEC    ;RECOGNIZE BLANK OR QUESTION MARK AS NO-NUMBER
  54. ;
  55. ;
  56. ; IF WE ARE HERE, THERE IS A DECIMAL NUMBER AT 5DH WAITING TO BE READ
  57. ;
  58.     LXI    H,0    ;H WILL CONTAIN THE VALUE OF THE NUMBER
  59. DIGIT:    LDAX    D    ;GET NEXT DIGIT (ASCII)
  60.     INX    D    ;INCREMENT DIGIT POINTER
  61.     CPI    ' '
  62.     JZ    TESTNO    ;FINISHED GETTING NUMBER IF BLANK OR NULL
  63.     ORA    A    ;TEST FOR NULL (0)
  64.     JZ    TESTNO
  65.     SUI    '0'    ;SUBTRACT ASCII 0; THIS CONVERTS DIGIT TO NUMBER
  66.     CPI    10    ;MAKE SURE IT WAS REALLY A DIGIT (0-9)
  67.     JNC    INVAL    ;JUMP IF NOT
  68.     DAD    H    ;DOUBLE ACCUMULATED VALUE
  69.     PUSH    H    ;SAVE RESULT
  70.     DAD    H    ;DOUBLE IT AGAIN
  71.     DAD    H    ;AND AGAIN
  72.     POP    B    ;NOW GET RESULT SAVE ABOVE AND ADD TO VALUE
  73.     DAD    B    ;WE HAVE NOW MULTIPLIED VALUE BY 10
  74.     MOV    C,A    ;NOW ADD TO IT THE VALUE OF THE NEW DIGIT
  75.     MVI    B,0
  76.     DAD    B
  77.     JMP    DIGIT    ;AND GO BACK FOR NEXT DIGIT
  78. ;
  79. ;
  80. TESTNO:    MOV    A,H    ;GET HIGH BYTE OF NUMBER OF K SPECIFIED
  81.     ORA    A    ;IF IT'S NOT ZERO, NUMBER WAS 256 OR BIGGER
  82.     JNZ    INVAL    ; AND THEREFORE NOT A VALID MEMORY SIZE
  83.     MOV    A,L    ;GET LOW BYTE
  84.     CPI    16    ;SYSTEM MUST BE AT LEAST 16K
  85.     JC    INVAL ; SO ERROR IF <16.
  86. ;
  87. ;
  88. ; NOW MULTIPY NO. OF K BY 1024 TO GET SPECIFIED MEMORY SIZE
  89. ;
  90.     MVI    L,0    ;L WAS SAVED IN A ABOVE
  91.     MOV    H,A    ;THIS MULTIPLIES BY 256
  92.     DAD    H    ;MULTIPLY BY 2
  93.     DAD    H    ;MULTIPLY BY 2 AGAIN
  94.     JMP    PUTK    ;GO TO NEXT SECTION WITH H=MEMORY SIZE IN BYTES
  95. ;
  96. ;
  97. INVAL:    LXI    D,INVMSG
  98.     CALL    MSG    ;OUTPUT "INVALID MEMORY SIZE" MESAGE TO CONSOLE
  99.     JMP    REBOOT    ;REBOOT SYSTEM
  100. ;
  101. ;
  102. INVMSG:    DB  CR,LF,'INVALID MEMORY SIZE$'
  103. ;
  104. ;
  105. ; COME HERE IF MEMORY SIZE WAS NOT SPECIFIED IN COMMAND LINE
  106. ;
  107. UNSPEC:    LXI    H,0    ;SET UP TO FIND MEMORY SIZE
  108. PAGE:    INR    H    ;POINT TO 1ST LOCATION OF NEXT PAGE
  109.     JZ    FOUND    ;GET OUT OF LOOP IF WE FOUND 256 PAGES OF MEMORY (WHY?)
  110.     MOV    A,M    ;GET 1ST BYTE OF PAGE POINTED TO BY H
  111.     CMA        ;COMPLEMENT IT
  112.     MOV    M,A    ; AND PUT IT BACK
  113.     CMP    M    ;NOW READ BACK AND COMPARE
  114.     CMA        ;RESTORE MEMORY BEFORE JUMPING
  115.     MOV    M,A
  116.     JZ    PAGE    ;KEEP LOOPING IF MEMORY VALID
  117. FOUND:    MOV    A,H    ;L IS STILL ZERO, SO HL IS NUMBER OF BYTES OF MEMORY,
  118.     ANI    0FCH    ; TRUNCATED TO NEAREST 256. NOW ZERO BITS 0,1 OF H TO
  119.     MOV    H,A    ; TRUNCATE TO A MULTIPLE OF 1024
  120. PUTK:    PUSH    H    ;SAVE TRUNCATED MEMORY SIZE ON STACK
  121. ;
  122.     LHLD    ENTRY+1    ;GET STARTING ADDRESS OF PRESENT BDOS FROM THE JUMP AT LOC. 5
  123.     MOV    A,L    ;SEE IF WE'RE IN DDT
  124.     CPI    6
  125.     JZ    NOTDDT    ;DDT CHANGES LOW BYTE
  126.     INX    H    ;POINT TO ADDRESS OF BDOS IN DDT
  127.     MOV    A,M
  128.     INX    H
  129.     MOV    H,M
  130.     MOV    L,A
  131. NOTDDT:    SHLD    BDOS    ;SAVE IT FOR LATER USE
  132. ;
  133.     POP    H    ;GET MEMORY SIZE AGAIN
  134.     PUSH    H    ; BUT LEAVE IT ON STACK TOP
  135.     MOV    A,H    ;TAKE NUMBER OF PAGES AND DIVIDE BY 4 (INTEGER)
  136.     RRC        ;TO GET NUMBER OF K.
  137.     RRC
  138.     ANI    3FH
  139.     MOV    B,A    ;SAVE NUMBER OF K IN B
  140.     LXI    H,CPMMSG+15 ;POINT TO OF NUMBER OF K (ASCII) IN "CONSTRUCTING" MESSAGE TEXT
  141.     MVI    A,'0'    ;SET IT TO ASCII 00
  142.     MOV    M,A
  143.     INX    H
  144.     MOV    M,A
  145. CNVRT1:    LXI    H,CPMMSG+16 ;LOOP TO CONVERT NO. OF K TO DECIMAL ASCII (2 DIGITS)
  146.     INR    M    ;INCREMENT LOW DIGIT
  147.     MOV    A,M    ;GET ITS NEW VALUE
  148.     CPI    '9'+1
  149.     JC    CNV1A    ;CONTINUE LOOP IF STILL IN THE RANGE '0' TO '9'
  150.     MVI    M,'0'    ;ELSE SET IT TO ASCII 0 AND INCREMENT HIGH DIGIT.
  151.     DCX    H
  152.     INR    M
  153. CNV1A:    DCR    B    ;DECREMENT REMAINDER OF NUMBER BEING CONVERTED
  154.     JNZ    CNVRT1    ; AND CONTINUE IN LOOP IF NOT YET ZERO
  155. ;
  156. ;
  157.     LXI    D,CPMMSG 
  158.     CALL    MSG    ;OUTPUT "CONSTRUCTING . . ." MESSAGE TO CONSOLE
  159. ;
  160. ;
  161.     LXI    H,SIZE    ;GET LENGTH OF SYSTEM IN BYTES
  162.     MOV    C,M
  163.     INX    H
  164.     MOV    B,M
  165.     PUSH    B    ;SAVE LENGTH IN B AND ON STACK
  166. ;
  167. ;
  168. ; SEARCH RELOC'S COPY OF THE SYSTEM FOR THE STRING "K CP/M VERS 1.3". THE
  169. ; SEARCH PRESENTLY BEGINS AT 900H AND CONTINUES THROUGH 900+LENGTH
  170. ;
  171. ;
  172.     LXI    H,SYSTEM
  173. SEARCH:    LXI    D,CPMMSG+17
  174.     MOV    A,B
  175.     ORA    C
  176.     JZ    NOFIND    ;EXIT IF SEARCH COMPLETED WITHOUT FINDING STRING
  177.     DCX    B    ;DECREMENT SEARCH COUNT AND SAVE ON STACK
  178.     PUSH    B
  179.     ;
  180.     MVI    C,15    ;SET STRING LENGTH FOR COMPARE LOOP
  181.     PUSH    H    ;SAVE CURRENTLY SEARCH ADDRESS ON STACK
  182. COMPR:    LDAX    D    ;LOOP TO COMPARE STRINGS- D POINTS TO ONE, H TO THE OTHER
  183.     CMP    M
  184.     JNZ    NEWLOC    ;GO TRY NEXT MEMORY POSITION IF COMPARISON FAILED
  185.     INX    D
  186.     INX    H
  187.     DCR    C
  188.     JZ    GOTIT
  189.     JMP    COMPR
  190. ;
  191. ;
  192. ;
  193. ;
  194. ;
  195. ;
  196. ;
  197. ;
  198. ;
  199. NEWLOC: POP    H    ;GET SEARCH POINTER AGAIN
  200.     INX    H    ;INCREMENT IT
  201.     POP    B    ;RESTORE  REMAINING SEARCH COUNT
  202.     JMP    SEARCH    ;GO BACK TO LOOK FOR STRING AGAIN
  203. ;
  204. ;
  205. GOTIT:    POP    H    ;STRING FOUND- GET ITS LOCATION
  206.     POP    B    ;CLEAN UP STACK
  207.     DCX    H    ;POINT TO 2ND DIGIT OF NUMBER OF K IN STRING
  208.     LXI    D,CPMMSG+16
  209.     LDAX    D    ;GET ASCII NUMBER OF K FROM STRING, AND PUT IT INTO STRING JUST FOUND
  210.     MOV    M,A
  211.     DCX    H
  212.     DCX    D
  213.     LDAX    D
  214.     MOV    M,A
  215. ;
  216. ;
  217. ;
  218. ;
  219. NOFIND:    LXI    B,BDOS    ;GET LOW BYTE OF CURRENT BDOS ADDRESS
  220.     MVI    A,0
  221.     STAX    B    ;SET LOW BYTE OF BDOS ADDRESS TO ZERO, SO ADDRESS IS THAT OF SERIAL NUMBER
  222. ;
  223. ;
  224. ;
  225. ;
  226.     POP    B    ;GET SYSTEM LENGTH
  227.     POP    H    ;GET MEMORY SIZE IN BYTES
  228.     MOV    A,L    ;SUBTRACT B FROM H TO GET MSIZE-LENGTH
  229.     SUB    C    ; THIS IS ADDRESS NEW SYSTEM WILL RUN FROM
  230.     MOV    L,A
  231.     MOV    A,H
  232.     SBB    B
  233.     MOV    H,A
  234.     SHLD    NEWSYS    ;SAVE THIS ADDRESS AT NEWSYS AND IN D
  235.     XCHG
  236. ;
  237. ;
  238. ;
  239. ;
  240.     LXI    H,SYSTEM    ;POINT TO BEGINNING OF SYSTEM LOADED WITH RELOC.COM
  241.     PUSH    B    ;SAVE LENGTH
  242. ;
  243.     LDA    NAME2    ;GET 2ND ITEM IN COMMAND LINE
  244.     CPI    ' '    ;IF BLANK, SYSTEM IS TO BE PLACED AT ITS EXECUTION ADDRESS
  245.     JZ    EXEC
  246.     DAD    B    ;SET H TO POINT TO FIRST LOC. AFTER SYSTEM (START OF RELOCATION TABLE)
  247.     JMP    REL1
  248. ;
  249. ;
  250. ;
  251. ;
  252. ;
  253. ;
  254. ;
  255. ;
  256. ; IF 2ND ITEM IN COMMAND WAS BLANK, THEN COME HERE TO MOVE A COPY
  257. ; OF THE SYSTEM FROM 900 TO ITS EVENTUAL EXECUTION ADDRESS.
  258. ;
  259. ;
  260. EXEC:    MOV    A,B
  261.     ORA    C
  262.     JZ    REL1
  263.     DCX    B
  264.     MOV    A,M
  265.     STAX    D
  266.     INX    D
  267.     INX    H
  268.     JMP    EXEC
  269. ;
  270. ;
  271. ;
  272. ;
  273. ; LOOP TO PERFORM THE RELOCATION.
  274. ; MSIZE-LENGTH+100H IS ADDED TO EACH ADDRESS 
  275. ; MARKED BY A '1' IN THE RELOCATION BIT TABLE.
  276. ;
  277. ;
  278. REL1:    POP    B    ;GET LENGTH
  279.     PUSH    H    ;SAVE TABLE ADDRESS
  280.     LHLD    NEWSYS
  281.     XCHG        ;ADDRESS OF NEW SYSTEM IN D
  282.     LXI    H,100H
  283.     DAD    D    ;H IS NOW NEWSYS+100H
  284. ;
  285. ;
  286.     LDA    NAME2    ;GET 2ND COMMAND ITEM AGAIN
  287.     CPI    ' '
  288.     JZ    REL2
  289.     LXI    D,SYSTEM    ;IF NOT A SPACE, SET D TO PUT NEW SYSTEM IN PLACE FOR SYSGEN
  290. REL2:    MOV    A,B
  291.     ORA    C
  292.     JZ    FINISH    ;JUMP IF COUNT HAS REACHED ZERO
  293.     JMP    REL3
  294. ;
  295. ;
  296. ;
  297. ;
  298. REL3:    DCX    B    ;DECREMENT BYTE COUNT
  299.     MOV    A,E    ;GET LOW BYTE OF CURRENT ADDRESS IN NEW SYSTEM
  300.     ANI    7    ;IF IT IS A MULTIPLE OF 8, WE NEED TO GET ANOTHER
  301.     JNZ    REL4    ; BYTE OF THE RELOCATION TABLE
  302.     XTHL        ;GET H=CURRENT ADDRESS IN TABLE
  303.     MOV    A,M    ;GET THE BYTE THERE
  304.     INX    H    ;INCREMENT TABLE ADDRESS
  305.     XTHL        ;PUT IT BACK ON STACK
  306.     MOV    L,A
  307. REL4:    MOV    A,L    ;TEST NEXT BIT OF CURRENT TABLE BYTE
  308.     RAL
  309.     MOV    L,A
  310.     JNC    REL5    ;IF NOT SET, CONTINUE IN LOOP
  311.     LDAX    D    ;GET HIGH BYTE OF ADDRESS AT CURRENT LOCATION IN NEW SYSTEM
  312.     ADD    H    ;ADD HIGH BYTE OF  100H+EXECUTION ADDRESS
  313.     STAX    D    ; AND PUT BACK IN NEW SYSTEM
  314.     JMP    REL5
  315. REL5:    INX    D    ;POINT TO NEXT BYTE OF NEW SYSTEM
  316.     JMP    REL2
  317. ;
  318. ;
  319. ;
  320. ;
  321. FINISH: POP    D    ;CLEAN UP STACK
  322. ;
  323. ;
  324. ; COPY SERIAL NUMBER FROM SYSTEM CURRENTLY IN USE (INTO NEW SYSTEM)
  325. ;
  326. ;
  327.     LXI    D,SERIALB  ;ADDR OF BDOS SERIAL IN RELOC.COM
  328.     CALL    SERPUT
  329.     LXI    D,SERIALC  ;ADDR OF CCP SERIAL IN RELOC.COM
  330.     CALL    SERPUT
  331.     JMP    SER2
  332. ;
  333. SERPUT:    LHLD    BDOS    ;ADDRESS OF SERIAL NO. IN CURRENT SYSTEM
  334.     MVI    C,6    ;LOOP COUNT
  335. SERLP:    MOV    A,M
  336.     STAX    D
  337.     INX    H
  338.     INX    D
  339.     DCR    C
  340.     JNZ    SERLP
  341.     RET
  342. SER2:
  343. ;
  344. ;
  345. ; IF SYSTEM WAS PUT AT EXECUTION ADDRESS, GO THERE
  346. ;
  347.     LDA    NAME2
  348.     CPI    ' '
  349.     JZ    SYSGO
  350. ;
  351. ;
  352. ; IF 900-97F IS ALL ZEROES, THEN MOVE THE WHOLE SYSTEM DOWN 80H BYTES
  353. ; FROM 980 TO 900
  354. ;
  355. ;
  356.     MVI    B,80H
  357.     LXI    H,SYSTEM
  358. TEST1:    MOV    A,M
  359.     ORA    A
  360.     JNZ    NOMOVE
  361.     INX    H
  362.     DCR    B
  363.     JNZ    TEST1
  364. ;
  365.     XCHG        ;D IS 980H
  366.     LHLD    SIZE    ;GET SYSTEM LENGTH
  367.     LXI    B,-80H
  368.     DAD    B
  369.     MOV    B,H
  370.     MOV    C,L    ;BC = LENGTH-128
  371.     LXI    H,900H
  372. MOVE:    MOV    A,B
  373.     ORA    C
  374.     JZ    NOMOVE
  375.     DCX    B
  376.     LDAX    D
  377.     MOV    M,A
  378.     INX    D
  379.     INX    H
  380.     JMP    MOVE
  381. ;
  382. ;
  383. ;
  384. ;
  385. NOMOVE: LXI    H,SIZE
  386.     MOV    C,M
  387.     INX    H
  388.     MOV    B,M    ;B = LENGTH
  389.     LXI    H,900H
  390.     DAD    B
  391.     MOV    B,H    ;C IS ALREADY ZERO- NOW B IS NUMBER OF PAGES IN NEW SYSTEM
  392. ;
  393. ;
  394. ; PUT NUMBER OF PAGES IN THE NEW SYSTEM INTO THE "SAVE NN . . ." MESSAGE TEXT
  395. ;
  396.     LXI    H,ENDMSG+31
  397.     MVI    A,30H
  398.     MOV    M,A
  399.     INX    H
  400.     MOV    M,A
  401. PUTN:    DCR    B
  402.     JZ    PUTK2
  403.     LXI    H,ENDMSG+32
  404.     INR    M
  405.     MOV    A,M
  406.     CPI    '9'+1
  407.     JC    PUTN
  408.     MVI    M,30H
  409.     DCX    H
  410.     INR    M
  411.     JMP    PUTN
  412. ;
  413. ;
  414. PUTK2:    LHLD    CPMMSG+15
  415.     SHLD    ENDMSG+37    ;PUT NO. OF K IN MESSAGE
  416.     LXI    D,ENDMSG
  417.     CALL    MSG    ;OUTPUT MESSAGE TO CONSOLE
  418.     JMP    REBOOT    ;RETURN TO CP/M
  419. ;
  420. ;
  421. ;
  422. ;
  423. ENDMSG:    DB  CR,LF,'READY FOR "SYSGEN" OR',CR,LF
  424.     DB  '"SAVE 00 CPM00.COM"$'
  425. ;
  426. ;
  427. ;
  428. ;
  429. SYSGO:    LXI    D,1600H
  430.     LHLD    NEWSYS
  431.     DAD    D
  432.     PCHL        ;JUMP TO NEW SYSTEM
  433. ;
  434. ;
  435. ;
  436. ;
  437. MSG:    MVI    C,9
  438. SYSCAL:    JMP    ENTRY
  439. BDOS    DW    0
  440. NEWSYS    DW    0
  441. ;
  442. CPMMSG:    DB  CR,LF,'CONSTRUCTING 00K CP/M VERS 1.3$'
  443. ;
  444. ;
  445. ;
  446. ;
  447.     END
  448.