diff options
| author | 2024-04-25 21:24:10 +0100 | |
|---|---|---|
| committer | 2024-04-25 22:32:27 +0000 | |
| commit | 2d04cacc5322951f187bb17e017c12920ac8ebe2 (patch) | |
| tree | 80ee017efa878dfd5344b44249e6a241f2a7f6e2 /v4.0/src/CMD/COMMAND/INIT.ASM | |
| parent | Merge pull request #430 from jpbaltazar/typoptbr (diff) | |
| download | ms-dos-main.tar.gz ms-dos-main.tar.xz ms-dos-main.zip | |
Diffstat (limited to 'v4.0/src/CMD/COMMAND/INIT.ASM')
| -rw-r--r-- | v4.0/src/CMD/COMMAND/INIT.ASM | 1685 |
1 files changed, 1685 insertions, 0 deletions
diff --git a/v4.0/src/CMD/COMMAND/INIT.ASM b/v4.0/src/CMD/COMMAND/INIT.ASM new file mode 100644 index 0000000..3ac84b6 --- /dev/null +++ b/v4.0/src/CMD/COMMAND/INIT.ASM | |||
| @@ -0,0 +1,1685 @@ | |||
| 1 | page 80,132 | ||
| 2 | ; SCCSID = @(#)init.asm 4.13 85/11/03 | ||
| 3 | ; SCCSID = @(#)init.asm 4.13 85/11/03 | ||
| 4 | TITLE COMMAND Initialization | ||
| 5 | |||
| 6 | INCLUDE comsw.asm | ||
| 7 | |||
| 8 | .xlist | ||
| 9 | .xcref | ||
| 10 | INCLUDE DOSSYM.INC | ||
| 11 | include doscntry.inc ;AC000; | ||
| 12 | INCLUDE comseg.asm | ||
| 13 | INCLUDE comequ.asm | ||
| 14 | include resmsg.equ ;AN000; | ||
| 15 | .list | ||
| 16 | .cref | ||
| 17 | |||
| 18 | |||
| 19 | ENVIRONSIZ EQU 0A0H ;Must agree with values in EVIRONMENT segment | ||
| 20 | ENVIRONSIZ2 EQU 092H | ||
| 21 | |||
| 22 | ENVBIG EQU 32768 | ||
| 23 | ENVSML EQU 160 | ||
| 24 | KOREA_COUNTRY_CODE EQU 82 | ||
| 25 | |||
| 26 | CODERES SEGMENT PUBLIC BYTE ;AC000; | ||
| 27 | EXTRN CONTC:NEAR | ||
| 28 | EXTRN DskErr:NEAR | ||
| 29 | EXTRN endinit:near | ||
| 30 | EXTRN INT_2E:NEAR | ||
| 31 | EXTRN LODCOM:NEAR | ||
| 32 | EXTRN RSTACK:WORD | ||
| 33 | CODERES ENDS | ||
| 34 | |||
| 35 | DATARES SEGMENT PUBLIC BYTE ;AC000; | ||
| 36 | EXTRN abort_char:byte ;AN000; | ||
| 37 | EXTRN append_state:word ;AN042; | ||
| 38 | EXTRN BADFAT_OP_SEG:WORD ;AN000; | ||
| 39 | EXTRN BATCH:WORD | ||
| 40 | EXTRN COM_FCB1:DWORD | ||
| 41 | EXTRN COM_FCB2:DWORD | ||
| 42 | EXTRN COM_PTR:DWORD | ||
| 43 | EXTRN com_xlat_addr:word | ||
| 44 | EXTRN COMDRV:BYTE | ||
| 45 | EXTRN COMPRMT1_SEG:WORD ;AN000; | ||
| 46 | EXTRN COMPRMT1_SEG2:WORD ;AN000; | ||
| 47 | EXTRN COMSPEC:BYTE | ||
| 48 | EXTRN comspec_print:word | ||
| 49 | EXTRN comspec_end:word | ||
| 50 | EXTRN cpdrv:byte | ||
| 51 | EXTRN crit_msg_off:word ;AN000; | ||
| 52 | EXTRN crit_msg_seg:word ;AN000; | ||
| 53 | EXTRN critical_msg_start:byte ;AN000; | ||
| 54 | EXTRN DATARESEND:BYTE ;AC000; | ||
| 55 | EXTRN dbcs_vector_addr:word ;AN000; | ||
| 56 | EXTRN DEVE_OP_SEG:WORD ;AN000; | ||
| 57 | EXTRN DEVE_OP_SEG2:WORD ;AN000; | ||
| 58 | EXTRN disp_class:byte ;AN000; | ||
| 59 | EXTRN DRVNUM_OP_SEG:WORD ;AN000; | ||
| 60 | EXTRN DRVNUM_OP_SEG2:WORD ;AN000; | ||
| 61 | EXTRN EchoFlag:BYTE | ||
| 62 | EXTRN ENVIRSEG:WORD | ||
| 63 | EXTRN ERR15_OP_SEG:WORD ;AN000; | ||
| 64 | EXTRN ERR15_OP_SEG2:WORD ;AN000; | ||
| 65 | EXTRN ERR15_OP_SEG3:WORD ;AN000; | ||
| 66 | EXTRN extended_msg_start:byte ;AN000; | ||
| 67 | EXTRN extmsgend:byte ;AN000; | ||
| 68 | EXTRN fFail:BYTE | ||
| 69 | EXTRN fucase_addr:word ;AN000; | ||
| 70 | EXTRN InitFlag:BYTE | ||
| 71 | EXTRN IO_SAVE:WORD | ||
| 72 | EXTRN LTPA:WORD ;AC000; | ||
| 73 | EXTRN MEMSIZ:WORD | ||
| 74 | EXTRN MYSEG:WORD ;AC000; | ||
| 75 | EXTRN MYSEG1:WORD | ||
| 76 | EXTRN MYSEG2:WORD | ||
| 77 | EXTRN nest:word | ||
| 78 | EXTRN number_subst:byte ;AN000; | ||
| 79 | EXTRN OldTerm:DWORD | ||
| 80 | EXTRN PARENT:WORD | ||
| 81 | ;AD060; EXTRN pars_msg_off:word ;AN000; | ||
| 82 | ;AD060; EXTRN pars_msg_seg:word ;AN000; | ||
| 83 | EXTRN parse_msg_start:byte ;AN000; | ||
| 84 | EXTRN parsemes_ptr:word ;AN000; | ||
| 85 | EXTRN PERMCOM:BYTE | ||
| 86 | EXTRN RES_TPA:WORD | ||
| 87 | EXTRN resmsgend:word ;AN000; | ||
| 88 | EXTRN RSWITCHAR:BYTE | ||
| 89 | EXTRN SINGLECOM:WORD | ||
| 90 | EXTRN SUM:WORD | ||
| 91 | EXTRN TRNSEG:WORD | ||
| 92 | EXTRN TrnMvFlg:BYTE | ||
| 93 | DATARES ENDS | ||
| 94 | |||
| 95 | BATARENA SEGMENT PUBLIC PARA ;AC000; | ||
| 96 | BATARENA ENDS | ||
| 97 | |||
| 98 | BATSEG SEGMENT PUBLIC PARA ;AC000; | ||
| 99 | BATSEG ENDS | ||
| 100 | |||
| 101 | ENVARENA SEGMENT PUBLIC PARA ;AC000; | ||
| 102 | ENVARENA ENDS | ||
| 103 | |||
| 104 | ENVIRONMENT SEGMENT PUBLIC PARA ; Default COMMAND environment | ||
| 105 | EXTRN ECOMSPEC:BYTE | ||
| 106 | EXTRN ENVIREND:BYTE | ||
| 107 | EXTRN PATHSTRING:BYTE | ||
| 108 | ENVIRONMENT ENDS | ||
| 109 | |||
| 110 | TAIL SEGMENT PUBLIC PARA | ||
| 111 | EXTRN TRANSTART:WORD | ||
| 112 | TAIL ENDS | ||
| 113 | |||
| 114 | TRANCODE SEGMENT PUBLIC BYTE ;AC000; | ||
| 115 | EXTRN DATINIT:FAR | ||
| 116 | EXTRN printf_init:far | ||
| 117 | TRANCODE ENDS | ||
| 118 | |||
| 119 | TRANSPACE SEGMENT PUBLIC BYTE ;AC000; | ||
| 120 | EXTRN TRANSPACEEND:BYTE | ||
| 121 | TRANSPACE ENDS | ||
| 122 | |||
| 123 | ; This is the area used for the autoexec.bat file. BATARENA is a pad for the | ||
| 124 | ; the address mark placed by DOS. | ||
| 125 | |||
| 126 | BATARENA SEGMENT PUBLIC PARA | ||
| 127 | |||
| 128 | ORG 0 | ||
| 129 | DB 10h DUP (?) ;Pad for memory allocation addr mark | ||
| 130 | |||
| 131 | BATARENA ENDS | ||
| 132 | |||
| 133 | BATSEG SEGMENT PUBLIC PARA ;Autoexec.bat segment | ||
| 134 | |||
| 135 | ORG 0 | ||
| 136 | initbat batchsegment <> ;batch segment | ||
| 137 | DB 31 DUP (0) ;reserve area for batch file name & pad | ||
| 138 | |||
| 139 | BATSEG ENDS | ||
| 140 | |||
| 141 | ; ******************************************************************* | ||
| 142 | ; START OF INIT PORTION | ||
| 143 | ; This code is overlayed the first time the TPA is used. | ||
| 144 | |||
| 145 | INIT SEGMENT PUBLIC PARA | ||
| 146 | |||
| 147 | EXTRN AUTOBAT:byte | ||
| 148 | EXTRN BADCSPFL:byte | ||
| 149 | EXTRN bslash:byte | ||
| 150 | EXTRN CHUCKENV:byte | ||
| 151 | EXTRN command_c_syn:byte ;AN000; | ||
| 152 | EXTRN command_d_syn:byte ;AN000; | ||
| 153 | EXTRN command_e_syn:byte ;AN000; | ||
| 154 | EXTRN command_f_syn:byte ;AN000; | ||
| 155 | EXTRN command_m_syn:byte ;AN000; | ||
| 156 | EXTRN command_p_syn:byte ;AN000; | ||
| 157 | EXTRN comnd1_syn:word ;AN000; | ||
| 158 | EXTRN comnd1_addr:dword ;AN000; | ||
| 159 | EXTRN COMSPECT:byte | ||
| 160 | EXTRN comspstring:byte | ||
| 161 | EXTRN dswitch:byte ;AN018; | ||
| 162 | EXTRN ECOMLOC:word | ||
| 163 | EXTRN EnvMax:WORD | ||
| 164 | EXTRN EnvSiz:WORD | ||
| 165 | EXTRN equalsign:byte | ||
| 166 | EXTRN eswitch:byte ;AN018; | ||
| 167 | EXTRN ext_msg:byte ;AN000; | ||
| 168 | EXTRN fslash:byte | ||
| 169 | EXTRN INITADD:dword | ||
| 170 | EXTRN initend:word | ||
| 171 | EXTRN init_parse:dword ;AN054; | ||
| 172 | EXTRN INTERNAT_INFO:BYTE ;AN000; 3/3/KK | ||
| 173 | EXTRN KAUTOBAT:byte ;AN000; 3/3/KK | ||
| 174 | EXTRN lcasea:byte | ||
| 175 | EXTRN lcasez:byte | ||
| 176 | EXTRN num_positionals:word ;AN000; | ||
| 177 | EXTRN oldenv:word | ||
| 178 | EXTRN old_parse_ptr:word ;AN057; | ||
| 179 | EXTRN parse_command:byte ;AN000; | ||
| 180 | EXTRN pars_msg_off:word ;AN060; | ||
| 181 | EXTRN pars_msg_seg:word ;AN060; | ||
| 182 | EXTRN PRDATTM:byte | ||
| 183 | EXTRN resetenv:word ;AC000; | ||
| 184 | EXTRN scswitch:byte | ||
| 185 | EXTRN space:byte | ||
| 186 | EXTRN triage_add:dword ;AC000; | ||
| 187 | EXTRN trnsize:word | ||
| 188 | EXTRN ucasea:byte | ||
| 189 | EXTRN usedenv:word | ||
| 190 | |||
| 191 | |||
| 192 | ;AD054; EXTRN SYSPARSE:NEAR | ||
| 193 | |||
| 194 | PUBLIC CONPROC | ||
| 195 | PUBLIC init_contc_specialcase | ||
| 196 | |||
| 197 | ASSUME CS:RESGROUP,DS:RESGROUP,ES:RESGROUP,SS:RESGROUP | ||
| 198 | |||
| 199 | ORG 0 | ||
| 200 | ZERO = $ | ||
| 201 | |||
| 202 | |||
| 203 | CONPROC: | ||
| 204 | MOV SP,OFFSET RESGROUP:RSTACK ; MUST be first instruction | ||
| 205 | |||
| 206 | CALL SYSLOADMSG ;AN000; check dos version | ||
| 207 | JNC OKDOS ;AN000; if no problem - continue | ||
| 208 | |||
| 209 | mov ax,badver ;AN000; set DOS version | ||
| 210 | invoke sysdispmsg ;AN000; must be incorrect version | ||
| 211 | mov ax,es | ||
| 212 | cmp es:[PDB_Parent_PID],AX ; If command is its own parent, | ||
| 213 | here: ; loop forever. | ||
| 214 | Jz here | ||
| 215 | int 20h ; Otherwise, exit. | ||
| 216 | |||
| 217 | ; | ||
| 218 | ; Turn APPEND off during initialization processing | ||
| 219 | ; | ||
| 220 | okdos: | ||
| 221 | mov ax,AppendInstall ;AN042; see if append installed | ||
| 222 | int 2fh ;AN042; | ||
| 223 | cmp al,0 ;AN042; append installed? | ||
| 224 | je set_msg_addr ;AN042; no - continue | ||
| 225 | mov ax,AppendDOS ;AN042; see if append DOS version right | ||
| 226 | int 2fh ;AN042; | ||
| 227 | cmp ax,-1 ;AN042; append version correct? | ||
| 228 | jne set_msg_addr ;AN042; no - continue | ||
| 229 | mov ax,AppendGetState ;AN042; Get the state of Append | ||
| 230 | int 2fh ;AN042; | ||
| 231 | mov append_state,bx ;AN042; save append state | ||
| 232 | xor bx,bx ;AN042; clear out state | ||
| 233 | mov ax,AppendSetState ;AN042; Set the state of Append | ||
| 234 | int 2fh ;AN042; set everything off | ||
| 235 | |||
| 236 | set_msg_addr: | ||
| 237 | ; | ||
| 238 | ; Get addresses of old critical and parse errors and save so they can | ||
| 239 | ; be reset if COMMAND needs to exit | ||
| 240 | ; | ||
| 241 | |||
| 242 | push es ;AN000; SAVE ES DESTROYED BY INT 2FH | ||
| 243 | ;AD060; mov ah,multdos ;AN000; set up to call DOS through int 2fh | ||
| 244 | ;AD060; mov al,message_2f ;AN000; call for message retriever | ||
| 245 | mov ax,(multdos shl 8 or message_2f);AN060; set up to call DOS through int 2fh | ||
| 246 | mov dl,get_parse_msg ;AN000; get parse message address | ||
| 247 | int 2fh ;AN000; | ||
| 248 | mov cs:pars_msg_seg,es ;AN000; save returned segment | ||
| 249 | mov cs:pars_msg_off,di ;AN000; save returned offset | ||
| 250 | |||
| 251 | ;AD060; mov ah,multdos ;AN000; set up to call DOS through int 2fh | ||
| 252 | ;AD060; mov al,message_2f ;AN000; call for message retriever | ||
| 253 | mov ax,(multdos shl 8 or message_2f);AN060; set up to call DOS through int 2fh | ||
| 254 | mov dl,get_critical_msg ;AN000; get critical error message address | ||
| 255 | int 2fh ;AN000; | ||
| 256 | mov cs:crit_msg_seg,es ;AN000; save returned segment | ||
| 257 | mov cs:crit_msg_off,di ;AN000; save returned offset | ||
| 258 | pop es ;AN000; RESTORE ES DESTROYED BY INT 2FH | ||
| 259 | |||
| 260 | ; | ||
| 261 | ; Set addresses of critical and parse errors in this level of COMMAND | ||
| 262 | ; | ||
| 263 | |||
| 264 | ;AD060; mov ah,multdos ;AN000; set up to call DOS through int 2fh | ||
| 265 | ;AD060; mov al,message_2f ;AN000; call for message retriever | ||
| 266 | ;AD060; mov dl,set_parse_msg ;AN000; set up parse message address | ||
| 267 | mov di,offset resgroup:parse_msg_start ;AN000; start address | ||
| 268 | ;AD060; int 2fh ;AN000; | ||
| 269 | call set_parse_2f ;AN060; set parse error address | ||
| 270 | |||
| 271 | |||
| 272 | ;AD060; mov ah,multdos ;AN000; set up to call DOS through int 2fh | ||
| 273 | ;AD060; mov al,message_2f ;AN000; call for message retriever | ||
| 274 | mov ax,(multdos shl 8 or message_2f);AN060; set up to call DOS through int 2fh | ||
| 275 | mov dl,set_critical_msg ;AN000; set up critical error message address | ||
| 276 | mov di,offset resgroup:critical_msg_start ;AN000; start address | ||
| 277 | int 2fh ;AN000; | ||
| 278 | |||
| 279 | mov di,offset resgroup:dataresend+15 ;AN000; get address of resident end | ||
| 280 | mov [resmsgend],di ;AN000; save it | ||
| 281 | call sysloadmsg ;AN000; load message addresses | ||
| 282 | call get_msg_ptr ;AN000; set up pointers to some translated chars | ||
| 283 | mov ah,GetExtCntry ;g get extended country information | ||
| 284 | mov al,2 ;g minor function - ucase table | ||
| 285 | mov dx,-1 ;g | ||
| 286 | mov bx,-1 ;g | ||
| 287 | mov cx,5 ;g number of bytes we want | ||
| 288 | mov di,offset resgroup:com_xlat_addr ;g buffer to put address in | ||
| 289 | int int_command ;g | ||
| 290 | |||
| 291 | mov ah,GetExtCntry ;AN000; get extended country info | ||
| 292 | mov al,4 ;AN000; get file ucase table | ||
| 293 | mov dx,-1 ;AN000; | ||
| 294 | mov bx,-1 ;AN000; | ||
| 295 | mov cx,5 ;AN000; number of bytes we want | ||
| 296 | mov di,offset resgroup:fucase_addr ;AN000; buffer for address | ||
| 297 | int int_command ;AN000; | ||
| 298 | |||
| 299 | mov dx,offset resgroup:transtart+15 ;eg get end of init code | ||
| 300 | mov cl,4 ;eg change to paragraphs | ||
| 301 | shr dx,cl ;eg | ||
| 302 | mov ax,cs ;eg get current segment | ||
| 303 | add ax,dx ;eg calculate segment of end of init | ||
| 304 | mov [initend],ax ;eg save this | ||
| 305 | |||
| 306 | push ds ;AN000; | ||
| 307 | mov ax, (ECS_call SHL 8) OR GetLeadBTbl ;AN000; get dbcs vector | ||
| 308 | int int_command ;AN000; | ||
| 309 | mov bx,ds ;AN000; get segment to bx | ||
| 310 | pop ds ;AN000; | ||
| 311 | mov dbcs_vector_addr,si ;AN000; save address of | ||
| 312 | mov dbcs_vector_addr+2,bx ;AN000; dbcs vector | ||
| 313 | |||
| 314 | |||
| 315 | mov ax,word ptr ds:[PDB_Parent_PID] ; Init PARENT so we can exit | ||
| 316 | mov [PARENT],ax ; correctly. | ||
| 317 | MOV AX,WORD PTR DS:[PDB_Exit] | ||
| 318 | MOV WORD PTR OldTerm,AX | ||
| 319 | MOV AX,WORD PTR DS:[PDB_Exit+2] | ||
| 320 | MOV WORD PTR OldTerm+2,AX | ||
| 321 | |||
| 322 | MOV AX,OFFSET RESGROUP:ENVIREND + 15 | ||
| 323 | MOV CL,4 ; ax = size of resident part of | ||
| 324 | SHR AX,CL ; command in paragraphs. Add | ||
| 325 | MOV CX,CS ; this to CS and you get the | ||
| 326 | ADD AX,CX ; segment of the TPA. | ||
| 327 | |||
| 328 | MOV [RES_TPA], AX ; Temporarily save the TPA segment | ||
| 329 | AND AX, 0F000H | ||
| 330 | ADD AX, 01000H ; Round up to next 64K boundary | ||
| 331 | JNC TPASET ; Memory wrap if carry set | ||
| 332 | MOV AX, [RES_TPA] | ||
| 333 | TPASET: | ||
| 334 | MOV [LTPA],AX ; Good enough for the moment | ||
| 335 | MOV AX,WORD PTR DS:[PDB_block_len] ; ax = # of paras given to command | ||
| 336 | |||
| 337 | MOV [MYSEG1],DS ; These 3 variables are used as part of | ||
| 338 | MOV [MYSEG2],DS ; 3 long ptrs that the transient will | ||
| 339 | MOV [MYSEG],DS ; use to call resident routines. | ||
| 340 | MOV [MEMSIZ],AX ; Needed for execing other programs | ||
| 341 | ; | ||
| 342 | ; Compute maximum size of environment | ||
| 343 | ; | ||
| 344 | MOV EnvMax,(Environsiz + 15) / 16 + (EnvMaximum-zero + 15)/16 - 1 | ||
| 345 | ; | ||
| 346 | ; Compute minimum size of environment | ||
| 347 | ; | ||
| 348 | |||
| 349 | MOV EnvSiz, ENVSML / 16 | ||
| 350 | |||
| 351 | MOV DX,OFFSET TRANGROUP:TRANSPACEEND + 15 ; dx = size of transient | ||
| 352 | MOV CL,4 ; in paragraphs. | ||
| 353 | SHR DX,CL | ||
| 354 | mov [trnsize],dx ;eg save size of transient in paragraphs | ||
| 355 | |||
| 356 | SUB AX,DX ; max seg addr - # para's needed for transient | ||
| 357 | MOV [TRNSEG],AX ; = seg addr to load the transient at. | ||
| 358 | MOV AX,DS:[PDB_environ] ; ax = environment segment | ||
| 359 | OR AX,AX ; If there is no environment segment, | ||
| 360 | JZ BUILDENV ; go compute one. | ||
| 361 | INC BYTE PTR [CHUCKENV] ; Flag no new ENVIRONSEG to set up | ||
| 362 | JMP SHORT ENVIRONPASSED ; Otherwise one was passed to us. | ||
| 363 | |||
| 364 | BUILDENV: ; (this label isn't very accurate) | ||
| 365 | MOV AX,OFFSET RESGROUP:PATHSTRING ; Compute the segment of the | ||
| 366 | MOV CL,4 ; environment and put it in | ||
| 367 | SHR AX,CL ; ax. | ||
| 368 | MOV DX,DS | ||
| 369 | ADD AX,DX | ||
| 370 | |||
| 371 | ENVIRONPASSED: | ||
| 372 | MOV [ENVIRSEG],AX ; Save the environment's segment and | ||
| 373 | MOV ES,AX ; load into es. | ||
| 374 | ASSUME ES:ENVIRONMENT | ||
| 375 | |||
| 376 | GOTTHEENVIR: | ||
| 377 | MOV AX,CHAR_OPER SHL 8 ; Get the switch character and store it | ||
| 378 | INT int_command ; in RSWITCHAR. | ||
| 379 | MOV [RSWITCHAR],DL | ||
| 380 | |||
| 381 | CMP DL,fslash ; If backslashes are being used as the | ||
| 382 | JNZ IUSESLASH ; path separator, change the forward | ||
| 383 | mov al,bslash ; slash in COMSPECT and ECOMSPEC (if | ||
| 384 | MOV [COMSPECT],al ; there is a new ENVIRONSEG) to | ||
| 385 | CMP BYTE PTR [CHUCKENV],0 ; backslash. | ||
| 386 | JNZ IUSESLASH | ||
| 387 | MOV ES:[ECOMSPEC],al ;eg | ||
| 388 | |||
| 389 | IUSESLASH: | ||
| 390 | ; | ||
| 391 | ; Initialize the command drive | ||
| 392 | ; | ||
| 393 | MOV AH,Get_Default_Drive | ||
| 394 | INT 21h | ||
| 395 | INC AL | ||
| 396 | MOV ComDrv,AL | ||
| 397 | |||
| 398 | MOV AL,BYTE PTR DS:[FCB] ; al = default drive number for command | ||
| 399 | OR AL,AL | ||
| 400 | JZ NoComDrv ; no drive specified | ||
| 401 | |||
| 402 | MOV AH,':' | ||
| 403 | MOV [COMDRV],AL | ||
| 404 | ADD AL,40H ; Convert number to uppercase character | ||
| 405 | |||
| 406 | STD | ||
| 407 | CMP BYTE PTR [CHUCKENV],0 ; If a new environment is being built, | ||
| 408 | JNZ NOTWIDENV ; move the default comspec string in it | ||
| 409 | PUSH DS ; 2 bytes to make room for a drivespec. | ||
| 410 | PUSH ES ; The drivespec is in ax and is copied | ||
| 411 | POP DS ; on to the front of the string. | ||
| 412 | MOV DI,OFFSET ENVIRONMENT:ECOMSPEC + ENVIRONSIZ2 - 1 ;eg | ||
| 413 | MOV SI,OFFSET ENVIRONMENT:ECOMSPEC + ENVIRONSIZ2 - 3 ;eg | ||
| 414 | |||
| 415 | MOV CX,ENVIRONSIZ2 - 2 | ||
| 416 | REP MOVSB | ||
| 417 | POP DS | ||
| 418 | MOV WORD PTR ES:[ECOMSPEC],AX | ||
| 419 | |||
| 420 | NOTWIDENV: | ||
| 421 | CLD ; Add the drivespec to the string | ||
| 422 | MOV WORD PTR [AUTOBAT],AX ; used to reference autoexec.bat | ||
| 423 | MOV WORD PTR [KAUTOBAT],AX ;AN000; used to reference kautoexe.bat 3/3/KK | ||
| 424 | |||
| 425 | NOCOMDRV: | ||
| 426 | INVOKE SETVECT ; Set interrupt vectors 22h, 23h, & 24h | ||
| 427 | |||
| 428 | ;********************************* | ||
| 429 | ; PARSING STARTS HERE | ||
| 430 | ;********************************* | ||
| 431 | |||
| 432 | push cs ;AN000; get local segment | ||
| 433 | push cs ;AN000; into DS,ES | ||
| 434 | pop ds ;AN000; | ||
| 435 | pop es ;AN000; | ||
| 436 | |||
| 437 | ASSUME DS:RESGROUP,ES:RESGROUP ;AN000; | ||
| 438 | |||
| 439 | MOV SI,80H ;AC000; get command line | ||
| 440 | LODSB ;AC000; get length of line | ||
| 441 | MOV DI,SI ;AN000; get line position in DI | ||
| 442 | XOR AH,AH ;AC000; ax = length of command line | ||
| 443 | ; | ||
| 444 | ; Insure that the command line correctly ends with a CR | ||
| 445 | ; | ||
| 446 | ADD DI,AX ;AC000; go to end of command line | ||
| 447 | MOV BYTE PTR [DI],0Dh ;AC000; insert a carriage return | ||
| 448 | xor cx,cx ;AC000; clear cx | ||
| 449 | mov num_positionals,cx ;AC000; initialize positionals | ||
| 450 | ; | ||
| 451 | ; Scan the command line looking for the parameters | ||
| 452 | ; | ||
| 453 | |||
| 454 | parse_command_line: | ||
| 455 | mov di,offset resgroup:parse_command;AN000; Get address of parse_command | ||
| 456 | mov cx,num_positionals ;AN000; Get number of positionals | ||
| 457 | xor dx,dx ;AN000; clear dx | ||
| 458 | mov old_parse_ptr,si ;AN057; save position before calling parser | ||
| 459 | call init_parse ;AN054; call parser | ||
| 460 | mov num_positionals,cx ;AN000; Save number of positionals | ||
| 461 | cmp ax,end_of_line ;AC000; are we at end of line? | ||
| 462 | jz ArgsDoneJ3 ;AC000; yes - exit | ||
| 463 | cmp ax,result_no_error ;AN000; did an error occur | ||
| 464 | jz parse_cont ;AN000; no - continue | ||
| 465 | |||
| 466 | ; | ||
| 467 | ; Before issuing error message - make sure switch is not /C | ||
| 468 | ; | ||
| 469 | |||
| 470 | parse_line_error: | ||
| 471 | push si ;AN057; save line position | ||
| 472 | push ax ;AN057; save error number | ||
| 473 | cmp ax,BadSwt_Ptr ;AN057; Was error invalid switch? | ||
| 474 | jnz parse_line_error_disp ;AN057; No - just issue message | ||
| 475 | mov di,si ;AN057; Get terminating pointer in DI | ||
| 476 | mov si,old_parse_ptr ;AN057; Get starting pointer in SI | ||
| 477 | |||
| 478 | init_chk_delim: | ||
| 479 | cmp si,di ;AN057; at end of parsed parameter? | ||
| 480 | jz parse_line_error_disp ;AN057; Yes - just display message | ||
| 481 | lodsb ;AN057; | ||
| 482 | cmp al,space ;AN057; Skip blank spaces | ||
| 483 | jz init_chk_delim ;AN057; | ||
| 484 | cmp al,tab_chr ;AN057; Skip tab characters | ||
| 485 | jz init_chk_delim ;AN057; | ||
| 486 | |||
| 487 | cmp al,[rswitchar] ;AN057; Switch? | ||
| 488 | jnz parse_line_error_disp ;AN057; No - just issue message | ||
| 489 | lodsb ;AN057; Get the char after the switch | ||
| 490 | invoke itestkanj ;AN057; Is it DBCS? | ||
| 491 | jnz parse_line_error_disp ;AN057; Yes - can't be /C | ||
| 492 | invoke iupconv ;AN057; upper case it | ||
| 493 | cmp al,scswitch ;AN057; it is /C? | ||
| 494 | jnz parse_line_error_disp ;AN057; | ||
| 495 | pop dx ;AN057; even up stack | ||
| 496 | pop dx ;AN057; even up stack | ||
| 497 | jmp setSSwitch ;AN057; Yes - go set COMMAND /C | ||
| 498 | |||
| 499 | parse_line_error_disp: | ||
| 500 | pop ax ;AN057; restore error number | ||
| 501 | pop si ;AN057; restore line position | ||
| 502 | mov disp_class,parse_msg_class ;AN000; set up parse error msg class | ||
| 503 | mov dx,ax ;AN000; get message number | ||
| 504 | call print_message ;AN000; issue error message | ||
| 505 | jmp short parse_command_line ;AN000; continue parsing | ||
| 506 | |||
| 507 | parse_cont: | ||
| 508 | ; | ||
| 509 | ; See if a switch was entered | ||
| 510 | ; | ||
| 511 | |||
| 512 | cmp comnd1_syn,offset resgroup:command_f_syn ;AC000; was /F entered? | ||
| 513 | jz SetFSwitch ;AC000; yes go set fail switch | ||
| 514 | cmp comnd1_syn,offset resgroup:command_p_syn ;AC000; was /P entered? | ||
| 515 | Jz SetPSwitch ;AC000; yes go set up PERMCOM | ||
| 516 | cmp comnd1_syn,offset resgroup:command_d_syn ;AC000; was /D entered? | ||
| 517 | jz SetDSwitch ;AC000; yes go set date switch | ||
| 518 | cmp comnd1_syn,offset resgroup:command_c_syn ;AC000; was /C entered? | ||
| 519 | jz SetSSwitch ;AC000; yes go set up SINGLECOM | ||
| 520 | cmp comnd1_syn,offset resgroup:command_e_syn ;AC000; was /E entered? | ||
| 521 | jz SetESwitch ;AC000; yes go set up environment | ||
| 522 | cmp comnd1_syn,offset resgroup:command_m_syn ;AN000; was /MSG entered? | ||
| 523 | jz SetMSwitchjmp ;AN000; yes go set up message flag | ||
| 524 | jmp chkotherargs ;AC000; Must be something else | ||
| 525 | |||
| 526 | SetMSwitchjmp: ;AN018; long jump needed | ||
| 527 | jmp SetMswitch ;AN018; | ||
| 528 | |||
| 529 | ArgsdoneJ3: ;AN018; long jump needed | ||
| 530 | jmp ArgsDone ;AN018; | ||
| 531 | |||
| 532 | SetFSwitch: | ||
| 533 | cmp fFail,-1 ;AN018; has fail switch been set? | ||
| 534 | jnz failok ;AN018; no - set it | ||
| 535 | mov ax,moreargs_ptr ;AN018; set up too many arguments | ||
| 536 | jmp parse_line_error ;AN018; go issue error message | ||
| 537 | |||
| 538 | failok: | ||
| 539 | MOV fFail,-1 ;AC000; fail all INT 24s. | ||
| 540 | JMP parse_command_line ;AC000; | ||
| 541 | |||
| 542 | SetPSwitch: | ||
| 543 | ; | ||
| 544 | ; We have a permanent COMMAND switch /P. Flag this and stash the | ||
| 545 | ; termination address. | ||
| 546 | ; | ||
| 547 | cmp [permcom],0 ;AN018; has /p switch been set? | ||
| 548 | jz permcomok ;AN018; no - set it | ||
| 549 | mov ax,moreargs_ptr ;AN018; set up too many arguments | ||
| 550 | jmp parse_line_error ;AN018; go issue error message | ||
| 551 | |||
| 552 | permcomok: | ||
| 553 | INC [PERMCOM] | ||
| 554 | MOV WORD PTR [oldTerm],OFFSET RESGROUP:LODCOM | ||
| 555 | MOV WORD PTR [oldTerm+2],DS | ||
| 556 | ; | ||
| 557 | ; Make sure that we display the date and time. If the flag was not | ||
| 558 | ; initialized, set it to indicate yes, do prompt. | ||
| 559 | ; | ||
| 560 | CMP BYTE PTR [PRDATTM],-1 | ||
| 561 | JNZ parse_command_line_jmp ;AC018; keep parsing | ||
| 562 | MOV BYTE PTR [PRDATTM],0 ; If not set explicit, set to prompt | ||
| 563 | |||
| 564 | Parse_command_line_jmp: ;AN018; | ||
| 565 | JMP parse_command_line ;AC000; keep parsing | ||
| 566 | |||
| 567 | ArgsDoneJump: | ||
| 568 | JMP ArgsDone | ||
| 569 | |||
| 570 | SetDSwitch: | ||
| 571 | ; | ||
| 572 | ; Flag no date/time prompting. | ||
| 573 | ; | ||
| 574 | cmp dswitch,0 ;AN018; has /D switch been set? | ||
| 575 | jz setdateok ;AN018; no - set it | ||
| 576 | mov ax,moreargs_ptr ;AN018; set up too many arguments | ||
| 577 | jmp parse_line_error ;AN018; go issue error message | ||
| 578 | |||
| 579 | setdateok: | ||
| 580 | inc dswitch ;AN018; indicate /D entered | ||
| 581 | MOV BYTE PTR [PRDATTM],1 ; User explicitly says no date time | ||
| 582 | JMP parse_command_line ;AC000; continue parsing | ||
| 583 | |||
| 584 | SetSSwitch: | ||
| 585 | ; | ||
| 586 | ; Set up pointer to command line, flag no date/time and turn off singlecom. | ||
| 587 | ; | ||
| 588 | MOV [SINGLECOM],SI ; Point to the rest of the command line | ||
| 589 | MOV [PERMCOM],0 ; A SINGLECOM must not be a PERMCOM | ||
| 590 | MOV BYTE PTR [PRDATTM],1 ; No date or time either, explicit | ||
| 591 | JMP ArgsDone | ||
| 592 | ; | ||
| 593 | ; Look for environment-size setting switch | ||
| 594 | ; | ||
| 595 | ; The environment size is represented in decimal bytes and is | ||
| 596 | ; converted into pargraphs (rounded up to the next paragraph). | ||
| 597 | ; | ||
| 598 | |||
| 599 | SetESwitch: | ||
| 600 | cmp eswitch,0 ;AN018; has fail switch been set? | ||
| 601 | jz eswitchok ;AN018; no - set it | ||
| 602 | mov ax,moreargs_ptr ;AN018; set up too many arguments | ||
| 603 | jmp parse_line_error ;AN018; go issue error message | ||
| 604 | |||
| 605 | eswitchok: | ||
| 606 | inc eswitch ;AN018; indicate /E entered | ||
| 607 | mov di,offset resgroup:comnd1_addr ;AN000; get number returned | ||
| 608 | mov bx,word ptr [di] ;AN000; into bx | ||
| 609 | |||
| 610 | ADD BX, 0FH ; Round up to next paragraph | ||
| 611 | mov cl,4 ;AC000; convert to pargraphs | ||
| 612 | SHR BX, cl ;AC000; by right 4 | ||
| 613 | |||
| 614 | MOV EnvSiz,BX ; EnvSiz is in paragraphs | ||
| 615 | JMP parse_command_line ;AC000; continue parsing command line | ||
| 616 | |||
| 617 | SetMSwitch: | ||
| 618 | cmp ext_msg,set_extended_msg ;AN018; has /MSG switch been set? | ||
| 619 | jnz setMswitchok ;AN018; no - set it | ||
| 620 | mov ax,moreargs_ptr ;AN018; set up too many arguments | ||
| 621 | jmp parse_line_error ;AN018; go issue error message | ||
| 622 | setMswitchok: | ||
| 623 | MOV Ext_msg,set_extended_msg ;AN000; set /MSG switch | ||
| 624 | JMP parse_command_line ;AN000; keep parsing | ||
| 625 | |||
| 626 | ARGSDONEJ: | ||
| 627 | JMP ARGSDONE | ||
| 628 | |||
| 629 | ; | ||
| 630 | ; We have a non-switch character here. | ||
| 631 | ; | ||
| 632 | CHKOTHERARGS: | ||
| 633 | push ds ;AN054; | ||
| 634 | push si ;AC000; save place in command line | ||
| 635 | lds si,comnd1_addr ;AN000; get address of filespec | ||
| 636 | assume ds:nothing ;AN054; | ||
| 637 | |||
| 638 | mov dx,si ;AN000; put in dx also | ||
| 639 | MOV AX,(OPEN SHL 8) OR 2 ; Read and write | ||
| 640 | INT int_command | ||
| 641 | JC CHKSRCHSPEC ; Wasn't a file | ||
| 642 | MOV BX,AX | ||
| 643 | MOV AX,IOCTL SHL 8 | ||
| 644 | INT int_command | ||
| 645 | TEST DL,80H | ||
| 646 | JNZ ISADEVICE | ||
| 647 | |||
| 648 | BADSETCON: ;AN022; | ||
| 649 | MOV AH,CLOSE ; Close initial handle, wasn't a device | ||
| 650 | INT int_command | ||
| 651 | JMP CHKSRCHSPEC | ||
| 652 | |||
| 653 | ISADEVICE: | ||
| 654 | XOR DH,DH | ||
| 655 | OR DL,3 ; Make sure has CON attributes | ||
| 656 | MOV AX,(IOCTL SHL 8) OR 1 | ||
| 657 | INT int_command | ||
| 658 | JC BADSETCON ;AN022; Can't set attributes - quit | ||
| 659 | MOV DX,BX ; Save new handle | ||
| 660 | ;eg POP BX ; Throw away saved SI | ||
| 661 | ;eg POP BX ; Throw away saved CX | ||
| 662 | PUSH CX | ||
| 663 | MOV CX,3 | ||
| 664 | XOR BX,BX | ||
| 665 | |||
| 666 | RCCLLOOP: ; Close 0,1 and 2 | ||
| 667 | MOV AH,CLOSE | ||
| 668 | INT int_command | ||
| 669 | INC BX | ||
| 670 | LOOP RCCLLOOP | ||
| 671 | MOV BX,DX ; New device handle | ||
| 672 | MOV AH,XDUP | ||
| 673 | INT int_command ; Dup to 0 | ||
| 674 | MOV AH,XDUP | ||
| 675 | INT int_command ; Dup to 1 | ||
| 676 | MOV AH,XDUP | ||
| 677 | INT int_command ; Dup to 2 | ||
| 678 | MOV AH,CLOSE | ||
| 679 | INT int_command ; Close initial handle | ||
| 680 | POP CX | ||
| 681 | pop si ;AN000; restore position of command line | ||
| 682 | pop ds ;AN054; | ||
| 683 | JMP parse_command_line ;AC000; continue parsing | ||
| 684 | |||
| 685 | CHKSRCHSPEC: ; Not a device, so must be directory spec | ||
| 686 | |||
| 687 | MOV BYTE PTR [CHUCKENV],0 ; If search specified -- no inheritance | ||
| 688 | MOV AX,OFFSET RESGROUP:PATHSTRING ; Figure environment pointer | ||
| 689 | MOV CL,4 | ||
| 690 | SHR AX,CL | ||
| 691 | ;AD054; MOV DX,DS | ||
| 692 | MOV DX,CS ;AC054; | ||
| 693 | ADD AX,DX | ||
| 694 | MOV [ENVIRSEG],AX | ||
| 695 | |||
| 696 | MOV ES,AX | ||
| 697 | push si ;AN000; remember location of file | ||
| 698 | xor cx,cx ;AN000; clear cx for counting | ||
| 699 | |||
| 700 | countloop: | ||
| 701 | lodsb ;AN000; get a character | ||
| 702 | inc cx ;AN000; increment counter | ||
| 703 | cmp al,end_of_line_out ;AN000; are we at end of line? | ||
| 704 | jnz countloop ;AN000; no - keep counting | ||
| 705 | |||
| 706 | mov al,space | ||
| 707 | dec si ;AN000; move back one | ||
| 708 | MOV BYTE PTR [SI],al ;AN000; put a space at end of line | ||
| 709 | pop si ;AC000; get location back | ||
| 710 | |||
| 711 | MOV DI,[ECOMLOC] | ||
| 712 | |||
| 713 | COMTRLOOP: | ||
| 714 | LODSB | ||
| 715 | DEC CX | ||
| 716 | CMP AL,space | ||
| 717 | JZ SETCOMSR | ||
| 718 | STOSB | ||
| 719 | |||
| 720 | ;;; IF KANJI 3/3/KK | ||
| 721 | XOR AH,AH | ||
| 722 | ;;; ENDIF 3/3/KK | ||
| 723 | |||
| 724 | JCXZ SETCOMSR | ||
| 725 | |||
| 726 | ;;;; IF KANJI 3/3/KK | ||
| 727 | PUSH DS ;AN054; Make sure we have | ||
| 728 | PUSH CS ;AN054; local DS for | ||
| 729 | POP DS ;AN054; ITESTKANJ | ||
| 730 | INVOKE ITESTKANJ | ||
| 731 | POP DS ;AN054; restore PARSER DS | ||
| 732 | JZ COMTRLOOP | ||
| 733 | DEC CX | ||
| 734 | MOVSB | ||
| 735 | INC AH | ||
| 736 | JCXZ SETCOMSR | ||
| 737 | ;;;; ENDIF 3/3/KK | ||
| 738 | |||
| 739 | JMP SHORT COMTRLOOP | ||
| 740 | |||
| 741 | SETCOMSR: | ||
| 742 | PUSH CX | ||
| 743 | |||
| 744 | PUSH CS ;AN054; Get local segment | ||
| 745 | POP DS ;AN054; | ||
| 746 | assume ds:resgroup ;AN054; | ||
| 747 | |||
| 748 | PUSH DS | ||
| 749 | MOV SI,OFFSET RESGROUP:COMSPECT | ||
| 750 | MOV CX,14 | ||
| 751 | |||
| 752 | MOV AL,ES:[DI-1] | ||
| 753 | |||
| 754 | ;;;; IF KANJI 3/3/KK | ||
| 755 | OR AH,AH | ||
| 756 | JNZ INOTROOT ; Last char was KANJI second byte, might be '\' | ||
| 757 | ;;;; ENDIF 3/3/KK | ||
| 758 | |||
| 759 | CALL PATHCHRCMPR | ||
| 760 | JNZ INOTROOT | ||
| 761 | INC SI ; Don't make a double / | ||
| 762 | DEC CX | ||
| 763 | |||
| 764 | INOTROOT: | ||
| 765 | REP MOVSB | ||
| 766 | |||
| 767 | MOV DX,[ECOMLOC] ; Now lets make sure its good! | ||
| 768 | PUSH ES | ||
| 769 | POP DS | ||
| 770 | |||
| 771 | MOV AX,OPEN SHL 8 | ||
| 772 | INT int_command ; Open COMMAND.COM | ||
| 773 | POP DS | ||
| 774 | JC SETCOMSRBAD ; No COMMAND.COM here | ||
| 775 | MOV BX,AX ; Handle | ||
| 776 | MOV AH,CLOSE | ||
| 777 | INT int_command ; Close COMMAND.COM | ||
| 778 | |||
| 779 | SETCOMSRRET: | ||
| 780 | POP CX | ||
| 781 | POP SI | ||
| 782 | POP DS ;AN054; | ||
| 783 | assume ds:resgroup ;AN054; | ||
| 784 | |||
| 785 | ARGSDONEJ2: | ||
| 786 | PUSH CS ;AN000; Make sure local ES is | ||
| 787 | POP ES ;AN000; restored | ||
| 788 | JMP parse_command_line ;AC000; continue parsing command line | ||
| 789 | |||
| 790 | SETCOMSRBAD: | ||
| 791 | MOV DX,BADCOMLKMES_ptr ;AC000; get message number | ||
| 792 | invoke triageError | ||
| 793 | cmp ax, 65 | ||
| 794 | jnz doprt | ||
| 795 | mov dx,BADCOMACCMES_ptr ;AC000; get error message number | ||
| 796 | doprt: | ||
| 797 | call print_message | ||
| 798 | MOV SI,OFFSET RESGROUP:COMSPECT | ||
| 799 | MOV DI,[ECOMLOC] | ||
| 800 | MOV CX,14 | ||
| 801 | REP MOVSB ; Get my default back | ||
| 802 | |||
| 803 | JMP SHORT SETCOMSRRET | ||
| 804 | |||
| 805 | ;********************************* | ||
| 806 | ; PARSING ENDS HERE | ||
| 807 | ;********************************* | ||
| 808 | |||
| 809 | ARGSDONE: | ||
| 810 | mov es,[envirseg] ;AC000; get environment back | ||
| 811 | ASSUME ES:ENVIRONMENT ;AN000; | ||
| 812 | ;AD060; cmp ext_msg,set_extended_msg ;AN000; was /msg specified? | ||
| 813 | ;AD060; jnz check_permcom ;AN000; No, go check permcom | ||
| 814 | ;AD060; cmp [permcom],0 ;AN000; Yes - was permcom set? | ||
| 815 | ;AD060; jz permcom_error ;AN000; No - error cannot have /MSG without /P | ||
| 816 | |||
| 817 | ;AD060; mov ah,multdos ;AN000; set up to call DOS through int 2fh | ||
| 818 | ;AD060; mov al,message_2f ;AN000; call for message retriever | ||
| 819 | ;AD060; mov dl,set_extended_msg ;AN000; set up extended error message address | ||
| 820 | ;AD060; push es ;AN016; save environment segment | ||
| 821 | ;AD060; push cs ;AN016; get local segment to ES | ||
| 822 | ;AD060; pop es ;AN016; | ||
| 823 | ;AD060; mov di,offset resgroup:extended_msg_start ;AN000; start address | ||
| 824 | ;AD060; int 2fh ;AN000; | ||
| 825 | ;AD060; pop es ;AN016; restore environment segment | ||
| 826 | ;AD060; mov di,offset resgroup:extmsgend+15 ;AN000; get address of resident end | ||
| 827 | ;AD060; mov [resmsgend],di ;AN000; save it | ||
| 828 | ;AD060; call sysloadmsg ;AN000; load message addresses | ||
| 829 | ;AD060; jmp short process_permcom ;AN000; now go process /P switch | ||
| 830 | |||
| 831 | ;AD060;permcom_error: | ||
| 832 | ;AD060; mov disp_class,parse_msg_class ;AN000; set up parse error msg class | ||
| 833 | ;AD060; mov dx,LessArgs_Ptr ;AN000; get message number for "Required parameter missing" | ||
| 834 | ;AD060; call print_message ;AN000; issue error message | ||
| 835 | ;AD060; jmp short comreturns ;AN000; we already know /P wasn't entered | ||
| 836 | |||
| 837 | ;AD060;check_permcom: | ||
| 838 | CMP [PERMCOM],0 | ||
| 839 | JZ COMRETURNS | ||
| 840 | |||
| 841 | ;AD060;process_permcom: | ||
| 842 | PUSH ES ; Save environment pointer | ||
| 843 | MOV AH,SET_CURRENT_PDB | ||
| 844 | MOV BX,DS | ||
| 845 | MOV ES,BX | ||
| 846 | INT int_command ; Current process is me | ||
| 847 | MOV DI,PDB_Exit ; Diddle the addresses in my header | ||
| 848 | MOV AX,OFFSET RESGROUP:LODCOM | ||
| 849 | STOSW | ||
| 850 | MOV AX,DS | ||
| 851 | STOSW | ||
| 852 | MOV AX,OFFSET RESGROUP:CONTC | ||
| 853 | STOSW | ||
| 854 | MOV AX,DS | ||
| 855 | STOSW | ||
| 856 | MOV AX,OFFSET RESGROUP:DskErr | ||
| 857 | STOSW | ||
| 858 | MOV AX,DS | ||
| 859 | STOSW | ||
| 860 | MOV WORD PTR DS:[PDB_Parent_PID],DS ; Parent is me forever | ||
| 861 | |||
| 862 | MOV DX,OFFSET RESGROUP:INT_2E | ||
| 863 | MOV AX,(SET_INTERRUPT_VECTOR SHL 8) OR 02EH | ||
| 864 | INT int_command ;Set magic interrupt | ||
| 865 | POP ES ;Remember environment | ||
| 866 | |||
| 867 | COMRETURNS: | ||
| 868 | MOV AX,WORD PTR DS:[PDB_Parent_PID] | ||
| 869 | MOV [PARENT],AX ; Save parent | ||
| 870 | MOV WORD PTR DS:[PDB_Parent_PID],DS ; Parent is me | ||
| 871 | MOV AX,WORD PTR DS:[PDB_JFN_Table] | ||
| 872 | MOV [IO_SAVE],AX ; Get the default stdin and out | ||
| 873 | MOV WORD PTR [COM_PTR+2],DS ; Set all these to resident | ||
| 874 | MOV WORD PTR [COM_FCB1+2],DS | ||
| 875 | MOV WORD PTR [COM_FCB2+2],DS | ||
| 876 | MOV DI,OFFSET RESGROUP:COMSPEC | ||
| 877 | |||
| 878 | MOV SI,[ECOMLOC] | ||
| 879 | CMP BYTE PTR [CHUCKENV],0 | ||
| 880 | |||
| 881 | MOV AX,DS ; XCHG ES,DS | ||
| 882 | PUSH ES | ||
| 883 | POP DS | ||
| 884 | MOV ES,AX | ||
| 885 | |||
| 886 | JZ COPYCOMSP ; All set up for copy | ||
| 887 | |||
| 888 | PUSH CS | ||
| 889 | POP DS | ||
| 890 | |||
| 891 | MOV SI,OFFSET RESGROUP:COMSPSTRING | ||
| 892 | PUSH ES | ||
| 893 | PUSH DI | ||
| 894 | CALL IFINDE | ||
| 895 | MOV SI,DI | ||
| 896 | PUSH ES | ||
| 897 | POP DS | ||
| 898 | POP DI | ||
| 899 | POP ES | ||
| 900 | JNC COPYCOMSP | ||
| 901 | |||
| 902 | COMSPECNOFND: | ||
| 903 | MOV SI,CS:[ECOMLOC] ;AC062 | ||
| 904 | ADD SI,OFFSET RESGROUP:PATHSTRING | ||
| 905 | PUSH CS | ||
| 906 | POP DS | ||
| 907 | |||
| 908 | assume es:resgroup | ||
| 909 | COPYCOMSP: | ||
| 910 | mov es:comspec_print,di ; Save ptr to beginning of comspec path | ||
| 911 | cmp byte ptr [si+1],':' ; Is there a drive specifier in comspec | ||
| 912 | jnz COPYCOMSPLOOP ; If not, do not skip over first 2 bytes | ||
| 913 | add es:comspec_print,2 | ||
| 914 | |||
| 915 | COPYCOMSPLOOP: | ||
| 916 | LODSB | ||
| 917 | STOSB | ||
| 918 | OR AL,AL | ||
| 919 | JNZ COPYCOMSPLOOP | ||
| 920 | mov es:comspec_end,di ; Save ptr to end of comspec path | ||
| 921 | dec es:comspec_end | ||
| 922 | mov ah,es:comdrv | ||
| 923 | add ah,'A'-1 | ||
| 924 | mov es:cpdrv,ah ; Load drive letter in comprmt2 | ||
| 925 | assume es:environment | ||
| 926 | |||
| 927 | call setup_for_messages ;AN060; set up parse and extended error messages | ||
| 928 | PUSH CS | ||
| 929 | POP DS | ||
| 930 | MOV BX,[RESMSGEND] ;AC000; get end of resident | ||
| 931 | MOV CL,4 | ||
| 932 | SHR BX,CL | ||
| 933 | Public EnvMaximum | ||
| 934 | EnvMaximum: | ||
| 935 | ; | ||
| 936 | ; NOTE: The transient has to loaded directly after shrinking to the | ||
| 937 | ; resident size. | ||
| 938 | ; There is an assumption made when loading the transient that it | ||
| 939 | ; still intact after the resident portion. | ||
| 940 | ; If any other ALLOC/DEALLOC/SETBLOCK operations are performed | ||
| 941 | ; inbetween, then there is a real good chance that the non-resident | ||
| 942 | ; portion will be overwritten by arena information. | ||
| 943 | ; | ||
| 944 | MOV AH,SETBLOCK | ||
| 945 | INT int_command ; Shrink me to the resident only | ||
| 946 | ; | ||
| 947 | ; Load in the transient and compute the checksum. We may do this in one of | ||
| 948 | ; two ways: First, cheat and use the transient loading code that exists in | ||
| 949 | ; the resident piece. This may be OK except that it will hit the disk. | ||
| 950 | ; | ||
| 951 | ; But we do not need to hit the disk! The transient is already loaded but is | ||
| 952 | ; in the wrong place. We need to block transfer it up to the correct spot. | ||
| 953 | ; | ||
| 954 | GOTENVIR: | ||
| 955 | MOV TrnMvFlg, 1 ; Indicate that transient has been moved | ||
| 956 | PUSH ES | ||
| 957 | MOV SI,OFFSET RESGroup:TranStart | ||
| 958 | MOV DI,0 | ||
| 959 | mov ES,Trnseg | ||
| 960 | MOV CX,OFFSET TRANGROUP:TRANSPACEEND | ||
| 961 | ; | ||
| 962 | ; We need to ensure that we do not have the potential of overwriting our | ||
| 963 | ; existing code in this move | ||
| 964 | ; It is OK to move if (SI+CX+Segment of Transient < TrnSeg). | ||
| 965 | ; | ||
| 966 | push cx | ||
| 967 | mov ax,cx ; Get size of transient in bytes | ||
| 968 | add ax,si ; Calculate end of transient section | ||
| 969 | mov cl,4 | ||
| 970 | shr ax,cl ; Convert to paragraphs | ||
| 971 | inc ax ; Round up (for partial paragraph) | ||
| 972 | mov cx,ds | ||
| 973 | add ax,cx ; Add in current segment | ||
| 974 | cmp ax,Trnseg ; See if there is overlap | ||
| 975 | pop cx | ||
| 976 | ; If we are too close to be safe, call LOADCOM instead of moving the code. | ||
| 977 | jb Ok_To_Move | ||
| 978 | invoke LOADCOM | ||
| 979 | jmp short Trans_Loaded | ||
| 980 | Ok_To_Move: | ||
| 981 | ; | ||
| 982 | ; Everything is set for an upward move. WRONG! We must move downward. | ||
| 983 | ; | ||
| 984 | ADD SI,CX | ||
| 985 | DEC SI | ||
| 986 | ADD DI,CX | ||
| 987 | DEC DI | ||
| 988 | STD | ||
| 989 | REP MOVSB | ||
| 990 | CLD | ||
| 991 | |||
| 992 | Trans_Loaded: | ||
| 993 | POP ES | ||
| 994 | |||
| 995 | INVOKE CHKSUM ; Compute the checksum | ||
| 996 | MOV [SUM],DX ; Save it | ||
| 997 | |||
| 998 | CMP BYTE PTR [PRDATTM],0 ;eg | ||
| 999 | JNZ NOBATCHSEG ;eg Don't do AUTOEXEC or date time | ||
| 1000 | ; | ||
| 1001 | ; Allocate batch segment for D:/autoexec.bat + no arguments | ||
| 1002 | ; | ||
| 1003 | MOV BX,((SIZE BatchSegment) + 15 + 1 + 0Fh)/16 ;eg | ||
| 1004 | MOV AH,ALLOC ;eg | ||
| 1005 | INT int_command ;eg | ||
| 1006 | JC NOBATCHSEG ;eg didn't allocate - pretend no batch | ||
| 1007 | MOV BATCH,AX ;eg save batch segment | ||
| 1008 | |||
| 1009 | NOBATCHSEG: | ||
| 1010 | MOV BX, 0FFFFH ; Get size of largest block for env | ||
| 1011 | MOV AH, ALLOC | ||
| 1012 | INT int_command | ||
| 1013 | |||
| 1014 | ; Only allocate maximum 64K worth of environment | ||
| 1015 | |||
| 1016 | SUB BX,TRNSIZE ;eg subtract # of transient paragraphs | ||
| 1017 | SUB BX,128 ;eg make sure we have 2K left | ||
| 1018 | MOV EnvMax, BX | ||
| 1019 | CMP BX, 4096 ; 64K = 4096 paragraphs | ||
| 1020 | JB MAXOK | ||
| 1021 | MOV BX, 4096-1 | ||
| 1022 | MOV EnvMax, BX | ||
| 1023 | MAXOK: | ||
| 1024 | |||
| 1025 | MOV AH, ALLOC ; Get max size | ||
| 1026 | INT int_command | ||
| 1027 | |||
| 1028 | mov bx,[envirseg] ;g get old environment segment | ||
| 1029 | mov oldenv,bx ;g save it | ||
| 1030 | mov usedenv,0 ;g initialize env size counter | ||
| 1031 | MOV DS,bx | ||
| 1032 | ASSUME DS:NOTHING | ||
| 1033 | MOV [ENVIRSEG],AX | ||
| 1034 | MOV ES,AX | ||
| 1035 | XOR SI,SI | ||
| 1036 | MOV DI,SI | ||
| 1037 | MOV BX,EnvMax ; Copy over as much of the environment | ||
| 1038 | ; as possible | ||
| 1039 | SHL BX,1 | ||
| 1040 | SHL BX,1 | ||
| 1041 | SHL BX,1 | ||
| 1042 | SHL BX,1 | ||
| 1043 | MOV EnvMax, BX ; Convert EnvMax to bytes | ||
| 1044 | DEC BX ; Dec by one to leave room for double 0 | ||
| 1045 | XOR DX,DX ; Use DX to indicate that there was | ||
| 1046 | ; no environment size error. | ||
| 1047 | Public Nxtstr | ||
| 1048 | Nxtstr: | ||
| 1049 | CALL GetStrLen ; Get the size of the current env string | ||
| 1050 | push ds ;g get addressability to environment | ||
| 1051 | push cs ;g counter | ||
| 1052 | pop ds ;g | ||
| 1053 | ASSUME DS:RESGROUP | ||
| 1054 | add usedenv,cx ;g add the string length to env size | ||
| 1055 | pop ds ;g | ||
| 1056 | ASSUME DS:NOTHING | ||
| 1057 | CMP CX,1 ; End of environment was encountered. | ||
| 1058 | JZ EnvExit | ||
| 1059 | SUB BX,CX | ||
| 1060 | JAE OKCpyStr ; Can't fit in all of enviroment. | ||
| 1061 | INC DX ; Out of env space msg must be displayed | ||
| 1062 | JMP EnvExit | ||
| 1063 | OKCpyStr: | ||
| 1064 | JMP Nxtstr | ||
| 1065 | EnvExit: | ||
| 1066 | |||
| 1067 | PUSH CS | ||
| 1068 | POP DS | ||
| 1069 | ASSUME DS:RESGroup | ||
| 1070 | OR DX,DX ; DX will be non-zero if error | ||
| 1071 | JZ EnvNoErr | ||
| 1072 | MOV DX,OUTENVERR_ptr ;AC000; get message number | ||
| 1073 | call print_message | ||
| 1074 | |||
| 1075 | EnvNoErr: | ||
| 1076 | ; BX now has the left over size of the maximum environment | ||
| 1077 | ; We want to shrink the environment down to the minimum size | ||
| 1078 | ; Set the environment size to max(Envsiz,Env used) | ||
| 1079 | |||
| 1080 | MOV CX, EnvMax | ||
| 1081 | SUB CX, BX ; CX now has the environment used | ||
| 1082 | ADD CX, 16 ; Round up to next paragraph | ||
| 1083 | SHR CX, 1 | ||
| 1084 | SHR CX, 1 | ||
| 1085 | SHR CX, 1 | ||
| 1086 | SHR CX, 1 | ||
| 1087 | CMP CX, Envsiz ; Is environment used > Envsiz | ||
| 1088 | JB EnvSet | ||
| 1089 | MOV Envsiz, CX | ||
| 1090 | EnvSet: | ||
| 1091 | MOV BX, Envsiz ; Set environment to size needed | ||
| 1092 | mov ax,es ;eg get environment segment | ||
| 1093 | add ax,bx ;eg add number of environment paragraphs | ||
| 1094 | cmp ax,initend ;eg does this go past end of init? | ||
| 1095 | ja envsetok ;eg yes - do the setblock | ||
| 1096 | mov ax,es ;eg no - get back the environment segment | ||
| 1097 | mov bx,initend ;eg get the segment at end of init | ||
| 1098 | sub bx,ax ;eg setblock envir segment to end of init code | ||
| 1099 | mov resetenv,1 ;eg set flag so we know to set envir later | ||
| 1100 | |||
| 1101 | envsetok: | ||
| 1102 | MOV AH, SETBLOCK | ||
| 1103 | INT int_command | ||
| 1104 | |||
| 1105 | IF MSVER | ||
| 1106 | CMP [SINGLECOM],0 | ||
| 1107 | JNZ NOPHEAD ; Don't print header if SINGLECOM | ||
| 1108 | MOV DX,HEADER_ptr ;AC000; get message number | ||
| 1109 | call print_message | ||
| 1110 | NOPHEAD: | ||
| 1111 | ENDIF | ||
| 1112 | |||
| 1113 | CMP [BATCH],0 ;eg did we set up a batch segment? | ||
| 1114 | JNZ dodate ;eg yes - go initialize it | ||
| 1115 | JMP NODTTM ; Don't do AUTOEXEC or date time | ||
| 1116 | ; | ||
| 1117 | ; Allocate batch segment for D:/autoexec.bat + no arguments | ||
| 1118 | ; | ||
| 1119 | dodate: | ||
| 1120 | MOV AX,BATCH ;eg get batch segment | ||
| 1121 | MOV EchoFlag,3 ; set batch echo | ||
| 1122 | MOV NEST,1 ; g set nest flag to 1 batch | ||
| 1123 | MOV ES,AX | ||
| 1124 | ; | ||
| 1125 | ; Initialize the segment | ||
| 1126 | ; | ||
| 1127 | XOR DI,DI | ||
| 1128 | MOV AL,BatchType | ||
| 1129 | STOSB | ||
| 1130 | MOV AL,1 ; G initialize echo for batch exit | ||
| 1131 | STOSB ; G | ||
| 1132 | XOR AX,AX ; initialize to zero | ||
| 1133 | STOSW ; G batch segment of last job - batlast | ||
| 1134 | STOSW ; G segment for FOR | ||
| 1135 | STOSB ; G FOR flag | ||
| 1136 | STOSW ; position in file - batseek | ||
| 1137 | STOSW | ||
| 1138 | ; | ||
| 1139 | ; Clean out the parameters | ||
| 1140 | ; | ||
| 1141 | MOV AX,-1 ; initialize to no parameters | ||
| 1142 | MOV CX,10 | ||
| 1143 | REP STOSW | ||
| 1144 | ; | ||
| 1145 | ; Decide whether we should grab the default drive | ||
| 1146 | ; | ||
| 1147 | CMP BYTE PTR [AUTOBAT],0 | ||
| 1148 | |||
| 1149 | JNZ NOAUTSET | ||
| 1150 | MOV AH,GET_DEFAULT_DRIVE | ||
| 1151 | INT int_command | ||
| 1152 | ADD AL,ucasea | ||
| 1153 | |||
| 1154 | MOV [AUTOBAT],AL | ||
| 1155 | MOV [KAUTOBAT],AL ;AN000; 3/3/KK | ||
| 1156 | |||
| 1157 | NOAUTSET: | ||
| 1158 | ; | ||
| 1159 | ; Copy in the batch file name (including NUL) | ||
| 1160 | ; | ||
| 1161 | MOV SI,OFFSET RESGROUP:AUTOBAT | ||
| 1162 | MOV CX,8 | ||
| 1163 | REP MOVSW | ||
| 1164 | MOVSB ;AN027; move in carraige return to terminate string | ||
| 1165 | |||
| 1166 | MOV DX,OFFSET RESGROUP:AUTOBAT | ||
| 1167 | MOV AX,OPEN SHL 8 | ||
| 1168 | INT int_command ; See if AUTOEXEC.BAT exists | ||
| 1169 | JC NOABAT | ||
| 1170 | MOV BX,AX | ||
| 1171 | MOV AH,CLOSE | ||
| 1172 | INT int_command | ||
| 1173 | JMP DRV0 ;AC000; go process autoexec | ||
| 1174 | |||
| 1175 | NOABAT: | ||
| 1176 | push ax | ||
| 1177 | call setup_seg | ||
| 1178 | mov word ptr [triage_add+2],ax | ||
| 1179 | pop ax | ||
| 1180 | call triage_add | ||
| 1181 | cmp ax, 65 | ||
| 1182 | jz AccDenErr ;AN000; was network access denied | ||
| 1183 | |||
| 1184 | |||
| 1185 | ; If AUTOEXEC.BAT is not found, then check for KAUTOEXE.BAT. Changed | ||
| 1186 | ; by Ellen to check only when in Korea. The country information | ||
| 1187 | ; returned will overlay the old parse data area, but we don't care | ||
| 1188 | ; since we won't need the parse information or country information. | ||
| 1189 | ; We only care about the country code returned in BX. | ||
| 1190 | |||
| 1191 | MOV DX,OFFSET RESGROUP:INTERNAT_INFO ;AN000; Set up internat vars | ||
| 1192 | MOV AX,INTERNATIONAL SHL 8 ;AN000; get country dependent info | ||
| 1193 | INT 21H ;AN000; | ||
| 1194 | JC NOKABAT ;AN000; Error - don't bother with it | ||
| 1195 | CMP BX,KOREA_COUNTRY_CODE ;AN000; Are we speaking Korean? | ||
| 1196 | JNZ OPENERR ;AN000; No, don't check for KAUTOEXE | ||
| 1197 | |||
| 1198 | MOV DI, OFFSET BatFile ;AN000; 3/3/KK | ||
| 1199 | MOV SI,OFFSET RESGROUP:KAUTOBAT ;AN000; Another trial to do 3/3/KK | ||
| 1200 | MOV CX,8 ;AN000; auto execution for the 3/3/KK | ||
| 1201 | REP MOVSW ;AN000; non-English country 3/3/KK | ||
| 1202 | MOVSB ;AN027; move in carraige return to terminate string | ||
| 1203 | MOV DX,OFFSET RESGROUP:KAUTOBAT ;AN000; 3/3/KK | ||
| 1204 | MOV AX,OPEN SHL 8 ;AN000; 3/3/KK | ||
| 1205 | INT int_command ;AN000; See if KAUTOEXE.BAT exists 3/3/KK | ||
| 1206 | JC NOKABAT ;AN000; 3/3/KK | ||
| 1207 | MOV BX,AX ;AN000; 3/3/KK | ||
| 1208 | MOV AH,CLOSE ;AN000; 3/3/KK | ||
| 1209 | INT int_command ;AN000; 3/3/KK | ||
| 1210 | JMP SHORT DRV0 ;AN000; 3/3/KK | ||
| 1211 | |||
| 1212 | NOKABAT: ;AN000; 3/3/KK | ||
| 1213 | call triage_add ;AN000; get extended error | ||
| 1214 | cmp ax, 65 ;AN000; network access denied? | ||
| 1215 | jnz openerr ;AN000; no - go deallocate batch | ||
| 1216 | |||
| 1217 | AccDenErr: ;AN000; yes - put out message | ||
| 1218 | mov DX,ACCDEN ;AC000; get message number | ||
| 1219 | call print_message | ||
| 1220 | |||
| 1221 | openerr: | ||
| 1222 | MOV ES,[BATCH] ; Not found--turn off batch job | ||
| 1223 | MOV AH,DEALLOC | ||
| 1224 | INT int_command | ||
| 1225 | MOV [BATCH],0 ; AFTER DEALLOC in case of ^C | ||
| 1226 | MOV EchoFlag,1 | ||
| 1227 | mov nest,0 ;g indicate no batch in progress | ||
| 1228 | |||
| 1229 | DODTTM: | ||
| 1230 | MOV AX,OFFSET TRANGROUP:DATINIT | ||
| 1231 | MOV WORD PTR[INITADD],AX | ||
| 1232 | MOV AX,[TRNSEG] | ||
| 1233 | MOV WORD PTR[INITADD+2],AX | ||
| 1234 | CALL DWORD PTR [INITADD] | ||
| 1235 | |||
| 1236 | NODTTM: | ||
| 1237 | |||
| 1238 | IF IBMVER | ||
| 1239 | CMP [SINGLECOM],0 | ||
| 1240 | JNZ DRV0 ; Don't print header if SINGLECOM | ||
| 1241 | MOV DX,HEADER_ptr ;AC000; get message number | ||
| 1242 | call print_message | ||
| 1243 | ENDIF | ||
| 1244 | |||
| 1245 | DRV0: ; Reset APPEND state | ||
| 1246 | push ds ;AN042; save data segment | ||
| 1247 | push cs ;AN042; Get local segment into DS | ||
| 1248 | pop ds ;AN042; | ||
| 1249 | mov ax,AppendSetState ;AN042; Set the state of Append | ||
| 1250 | mov bx,Append_state ;AN042; back to the original state | ||
| 1251 | int 2fh ;AN042; | ||
| 1252 | pop ds ;AN042; get data segment back | ||
| 1253 | JMP ENDINIT ;G Finish initializing | ||
| 1254 | |||
| 1255 | ; | ||
| 1256 | ; Get length of string pointed to by DS:SI. Length includes NULL. | ||
| 1257 | ; Length is returned in CX | ||
| 1258 | ; | ||
| 1259 | GetStrLen: | ||
| 1260 | xor cx,cx | ||
| 1261 | NxtChar: | ||
| 1262 | lodsb | ||
| 1263 | inc cx | ||
| 1264 | or al,al | ||
| 1265 | jnz NxtChar | ||
| 1266 | ret | ||
| 1267 | ; | ||
| 1268 | ; If the transient has been loaded in TranSeg, then we need to use that | ||
| 1269 | ; segment for calls to routines in the transient area. Otherwise, the current | ||
| 1270 | ; code segment is used | ||
| 1271 | ; Segment returned in AX. | ||
| 1272 | ; | ||
| 1273 | setup_seg: | ||
| 1274 | mov ax,[trnseg] | ||
| 1275 | cmp TrnMvFlg, 1 ; Has transient portion been moved | ||
| 1276 | jz setup_end | ||
| 1277 | push bx | ||
| 1278 | mov bx,cs | ||
| 1279 | mov ax,OFFSET RESGroup:TranStart | ||
| 1280 | shr ax,1 | ||
| 1281 | shr ax,1 | ||
| 1282 | shr ax,1 | ||
| 1283 | shr ax,1 | ||
| 1284 | add ax,bx | ||
| 1285 | pop bx | ||
| 1286 | setup_end: | ||
| 1287 | ret | ||
| 1288 | |||
| 1289 | print_message: | ||
| 1290 | push ax | ||
| 1291 | PUSH DS ;AN000; save data and extra segment | ||
| 1292 | PUSH ES ;AN000; registers | ||
| 1293 | MOV AX,CS ;AN000; get local segment | ||
| 1294 | MOV ES,AX ;AN000; set ES and DS to point to it | ||
| 1295 | MOV DS,AX ;AN000; | ||
| 1296 | ;AD054; PUSH BX ;AC000; save BX register | ||
| 1297 | ;AD054; PUSH CX ;AC000; save CX register | ||
| 1298 | ;AD054; PUSH DX ;AC000; save DX register | ||
| 1299 | ;AD054; MOV AX,DX ;AC000; get message number | ||
| 1300 | ;AD054; MOV DH,DISP_CLASS ;AC000; get display class | ||
| 1301 | ;AD054; MOV DL,NO_CONT_FLAG ;AN000; set control flags off | ||
| 1302 | ;AD054; MOV BX,NO_HANDLE_OUT ;AC000; set message handler to use function 1-12 | ||
| 1303 | ;AD054; XOR CH,CH ;AC000; clear upper part of cx | ||
| 1304 | ;AD054; MOV CL,NUMBER_SUBST ;AC000; set number of substitutions | ||
| 1305 | ;AD054; invoke SYSDISPMSG ;AC000; display the message | ||
| 1306 | ;AD054; MOV DISP_CLASS,UTIL_MSG_CLASS ;AC000; reset display class | ||
| 1307 | ;AD054; MOV NUMBER_SUBST,NO_SUBST ;AC000; reset number of substitutions | ||
| 1308 | ;AD054; POP DX ;AC000; restore registers | ||
| 1309 | ;AD054; POP CX ;AC000; | ||
| 1310 | ;AD054; POP BX ;AC000; | ||
| 1311 | invoke rprint ;AC054; | ||
| 1312 | |||
| 1313 | POP ES ;AN000; | ||
| 1314 | POP DS ;AN000; | ||
| 1315 | pop ax | ||
| 1316 | ret | ||
| 1317 | |||
| 1318 | PATHCHRCMPR: | ||
| 1319 | push dx | ||
| 1320 | mov dl,fslash | ||
| 1321 | CMP [RSWITCHAR],dl | ||
| 1322 | JZ RNOSLASHT | ||
| 1323 | CMP AL,dl | ||
| 1324 | JZ RET41 | ||
| 1325 | RNOSLASHT: | ||
| 1326 | CMP AL,bslash | ||
| 1327 | RET41: | ||
| 1328 | pop dx | ||
| 1329 | RET | ||
| 1330 | |||
| 1331 | |||
| 1332 | IFINDE: | ||
| 1333 | CALL IFIND ; FIND THE NAME | ||
| 1334 | JC IFIND2 ; CARRY MEANS NOT FOUND | ||
| 1335 | JMP ISCASB1 ; SCAN FOR = SIGN | ||
| 1336 | ; | ||
| 1337 | ; On return of FIND1, ES:DI points to beginning of name | ||
| 1338 | ; | ||
| 1339 | IFIND: | ||
| 1340 | CLD | ||
| 1341 | CALL ICOUNT0 ; CX = LENGTH OF NAME | ||
| 1342 | MOV ES,[ENVIRSEG] | ||
| 1343 | XOR DI,DI | ||
| 1344 | |||
| 1345 | IFIND1: | ||
| 1346 | PUSH CX | ||
| 1347 | PUSH SI | ||
| 1348 | PUSH DI | ||
| 1349 | |||
| 1350 | IFIND11: | ||
| 1351 | LODSB | ||
| 1352 | |||
| 1353 | ;;;; IF KANJI 3/3/KK | ||
| 1354 | INVOKE ITESTKANJ | ||
| 1355 | JZ NOTKANJ4 | ||
| 1356 | DEC SI | ||
| 1357 | LODSW | ||
| 1358 | INC DI | ||
| 1359 | INC DI | ||
| 1360 | CMP AX,ES:[DI-2] | ||
| 1361 | JNZ IFIND12 | ||
| 1362 | DEC CX | ||
| 1363 | LOOP IFIND11 | ||
| 1364 | JMP SHORT IFIND12 | ||
| 1365 | |||
| 1366 | NOTKANJ4: | ||
| 1367 | ;;;; ENDIF 3/3/KK | ||
| 1368 | |||
| 1369 | CALL IUPCONV | ||
| 1370 | INC DI | ||
| 1371 | CMP AL,ES:[DI-1] | ||
| 1372 | JNZ IFIND12 | ||
| 1373 | LOOP IFIND11 | ||
| 1374 | |||
| 1375 | IFIND12: | ||
| 1376 | POP DI | ||
| 1377 | POP SI | ||
| 1378 | POP CX | ||
| 1379 | JZ IFIND2 | ||
| 1380 | PUSH CX | ||
| 1381 | CALL ISCASB2 ; SCAN FOR A NUL | ||
| 1382 | POP CX | ||
| 1383 | CMP BYTE PTR ES:[DI],0 | ||
| 1384 | JNZ IFIND1 | ||
| 1385 | STC ; INDICATE NOT FOUND | ||
| 1386 | |||
| 1387 | IFIND2: | ||
| 1388 | RET | ||
| 1389 | |||
| 1390 | ICOUNT0: | ||
| 1391 | PUSH DS | ||
| 1392 | POP ES | ||
| 1393 | MOV DI,SI | ||
| 1394 | |||
| 1395 | PUSH DI ; COUNT NUMBER OF CHARS UNTIL "=" | ||
| 1396 | CALL ISCASB1 | ||
| 1397 | JMP SHORT ICOUNTX | ||
| 1398 | PUSH DI ; COUNT NUMBER OF CHARS UNTIL NUL | ||
| 1399 | CALL ISCASB2 | ||
| 1400 | |||
| 1401 | ICOUNTX: | ||
| 1402 | POP CX | ||
| 1403 | SUB DI,CX | ||
| 1404 | XCHG DI,CX | ||
| 1405 | RET | ||
| 1406 | |||
| 1407 | ISCASB1: | ||
| 1408 | MOV AL,equalsign ; SCAN FOR AN = | ||
| 1409 | JMP SHORT ISCASBX | ||
| 1410 | |||
| 1411 | ISCASB2: | ||
| 1412 | XOR AL,AL ; SCAN FOR A NUL | ||
| 1413 | |||
| 1414 | ISCASBX: | ||
| 1415 | MOV CX,100H | ||
| 1416 | REPNZ SCASB | ||
| 1417 | RET | ||
| 1418 | |||
| 1419 | |||
| 1420 | ; **************************************************************** | ||
| 1421 | ; * | ||
| 1422 | ; * ROUTINE: IUPCONV (ADDED BY EMG 4.00) | ||
| 1423 | ; * | ||
| 1424 | ; * FUNCTION: This routine returns the upper case equivalent of | ||
| 1425 | ; * the character in AL from the file upper case table | ||
| 1426 | ; * in DOS if character if above ascii 128, else | ||
| 1427 | ; * subtracts 20H if between "a" and "z". | ||
| 1428 | ; * | ||
| 1429 | ; * INPUT: DS set to resident | ||
| 1430 | ; * AL char to be upper cased | ||
| 1431 | ; * FUCASE_ADDR set to the file upper case table | ||
| 1432 | ; * | ||
| 1433 | ; * OUTPUT: AL upper cased character | ||
| 1434 | ; * | ||
| 1435 | ; **************************************************************** | ||
| 1436 | |||
| 1437 | assume ds:resgroup ;AN000; | ||
| 1438 | |||
| 1439 | iupconv proc near ;AN000; | ||
| 1440 | |||
| 1441 | cmp al,80h ;AN000; see if char is > ascii 128 | ||
| 1442 | jb other_fucase ;AN000; no - upper case math | ||
| 1443 | sub al,80h ;AN000; only upper 128 chars in table | ||
| 1444 | push ds ;AN000; | ||
| 1445 | push bx ;AN000; | ||
| 1446 | lds bx,dword ptr fucase_addr+1 ;AN000; get table address | ||
| 1447 | add bx,2 ;AN000; skip over first word | ||
| 1448 | xlat ds:byte ptr [bx] ;AN000; convert to upper case | ||
| 1449 | pop bx ;AN000; | ||
| 1450 | pop ds ;AN000; | ||
| 1451 | jmp short iupconv_end ;AN000; we finished - exit | ||
| 1452 | |||
| 1453 | other_fucase: ;AN000; | ||
| 1454 | cmp al,lcasea ;AC000; if between "a" and "z", | ||
| 1455 | jb iupconv_end ;AC000; subtract 20h to get | ||
| 1456 | cmp al,lcasez ;AC000; upper case equivalent. | ||
| 1457 | ja iupconv_end ;AC000; | ||
| 1458 | sub al,20h ;AC000; Change lower-case to upper | ||
| 1459 | |||
| 1460 | iupconv_end: ;AN000; | ||
| 1461 | ret | ||
| 1462 | |||
| 1463 | iupconv endp ;AN000; | ||
| 1464 | |||
| 1465 | init_contc_specialcase: | ||
| 1466 | ; This routine is called if control-C | ||
| 1467 | add sp,6 ; is type during the date/time prompt | ||
| 1468 | push si ; at initialization time. The desired | ||
| 1469 | mov si,dx ; response is to make it look like the | ||
| 1470 | mov word ptr [si+1],0d00h ; user typed <CR> by "popping" the | ||
| 1471 | pop si ; INT 21h stuff off the stack, putting | ||
| 1472 | iret ; a <CR> in the user's buffer, and | ||
| 1473 | ; returning directly to the user. | ||
| 1474 | ; In this case the user is TCODE. | ||
| 1475 | |||
| 1476 | ; **************************************************************** | ||
| 1477 | ; * | ||
| 1478 | ; * ROUTINE: GET_MSG_PTR | ||
| 1479 | ; * | ||
| 1480 | ; * FUNCTION: Fill in translatable char table starting at | ||
| 1481 | ; * at Abort_char with translated characters. | ||
| 1482 | ; Set segments of resident messages. | ||
| 1483 | ; * | ||
| 1484 | ; * INPUT: none | ||
| 1485 | ; * | ||
| 1486 | ; * OUTPUT: none | ||
| 1487 | ; * | ||
| 1488 | ; **************************************************************** | ||
| 1489 | |||
| 1490 | CHAR_START EQU 201 ;AN000; first character translate is 1 | ||
| 1491 | CHAR_END EQU 207 ;AN000; last is 6 | ||
| 1492 | |||
| 1493 | GET_MSG_PTR PROC NEAR ;AN000; | ||
| 1494 | |||
| 1495 | MOV AX,CHAR_START ;AN000; get first char translation | ||
| 1496 | MOV BX,OFFSET RESGROUP:ABORT_CHAR ;AN000; get first char offset | ||
| 1497 | MOVEMES: ;AN000; | ||
| 1498 | MOV DH,-1 ;AN000; utility message | ||
| 1499 | INVOKE SYSGETMSG ;AN000; get the offset of the char | ||
| 1500 | MOV CL,BYTE PTR [SI] ;AN000; get the character in CL | ||
| 1501 | MOV BYTE PTR [BX],CL ;AN000; put the character in the table | ||
| 1502 | INC BX ;AN000; point to next position in table | ||
| 1503 | INC AX ;AN000; increment message number | ||
| 1504 | CMP AX,CHAR_END ;AN000; are we at the end? | ||
| 1505 | JNZ MOVEMES ;AN000; no - keep loading | ||
| 1506 | |||
| 1507 | MOV AX,DS ;AN000; get data segment | ||
| 1508 | MOV DRVNUM_OP_SEG,AX ;AN000; set up segments for | ||
| 1509 | MOV DRVNUM_OP_SEG2,AX ;AN000; message substitutions | ||
| 1510 | MOV DEVE_OP_SEG,AX ;AN000; used in the resident | ||
| 1511 | MOV DEVE_OP_SEG2,AX ;AN000; portion of command | ||
| 1512 | MOV ERR15_OP_SEG,AX ;AN000; during initialization | ||
| 1513 | MOV ERR15_OP_SEG2,AX ;AN000; to save resident | ||
| 1514 | MOV ERR15_OP_SEG3,AX ;AN000; space. | ||
| 1515 | MOV BADFAT_OP_SEG,AX ;AN000; | ||
| 1516 | MOV COMPRMT1_SEG,AX ;AN000; | ||
| 1517 | MOV COMPRMT1_SEG2,AX ;AN000; | ||
| 1518 | |||
| 1519 | RET ;AN000; | ||
| 1520 | |||
| 1521 | GET_MSG_PTR ENDP ;AN000; | ||
| 1522 | |||
| 1523 | |||
| 1524 | ; **************************************************************** | ||
| 1525 | ; * | ||
| 1526 | ; * ROUTINE: Setup_for_messages | ||
| 1527 | ; * | ||
| 1528 | ; * FUNCTION: Sets up system for PARSE and EXTENDED ERROR | ||
| 1529 | ; * messages as follows: | ||
| 1530 | ; * | ||
| 1531 | ; * IF /P and /MSG are entered | ||
| 1532 | ; * keep PARSE and EXTENDED ERRORS in memory | ||
| 1533 | ; * ELSE IF /P is entered | ||
| 1534 | ; * use PARSE and EXTENDED ERRORS on disk | ||
| 1535 | ; * remove PARSE ERRORS from memory | ||
| 1536 | ; * ELSE | ||
| 1537 | ; * remove PARSE ERRORS from memory | ||
| 1538 | ; * ENDIF | ||
| 1539 | ; * | ||
| 1540 | ; * INPUT: PERMCOM Set up with user input | ||
| 1541 | ; * EXT_MSG Set up with user input | ||
| 1542 | ; * System set up to retain PARSE ERRORS | ||
| 1543 | ; * | ||
| 1544 | ; * OUTPUT: registers unchanged | ||
| 1545 | ; * | ||
| 1546 | ; **************************************************************** | ||
| 1547 | |||
| 1548 | |||
| 1549 | setup_for_messages proc near ;AN060; | ||
| 1550 | |||
| 1551 | push ds ;AN060; save data segment | ||
| 1552 | push es ;AN060; save environment segment | ||
| 1553 | push ax ;AN060; | ||
| 1554 | push dx ;AN060; | ||
| 1555 | push di ;AN060; | ||
| 1556 | mov ax,cs ;AN060; get local segment to ES and DS | ||
| 1557 | mov ds,ax ;AN060; | ||
| 1558 | mov es,ax ;AN060; | ||
| 1559 | |||
| 1560 | cmp [permcom],0 ;AN060; was permcom set? | ||
| 1561 | jz no_permcom ;AN060; No - don't worry about messages | ||
| 1562 | cmp ext_msg,set_extended_msg ;AN060; was /msg specified? | ||
| 1563 | jz permcom_slash_msg ;AN060; Yes - go process it | ||
| 1564 | push es ;AN060; | ||
| 1565 | mov ax,1 ;AN060; Set ES to 1 as a flag to the message | ||
| 1566 | mov es,ax ;AN060; services that messages are on disk | ||
| 1567 | mov di,offset resgroup:extended_msg_start-100h ;AN060; start address | ||
| 1568 | call set_ext_2f ;AN060; set extended error address | ||
| 1569 | mov di,offset resgroup:parse_msg_start-0100h ;AN060; start address | ||
| 1570 | call set_parse_2f ;AN060; set parse error address | ||
| 1571 | pop es ;AN060; | ||
| 1572 | IF2 ;AN060;; | ||
| 1573 | IFNDEF READ_DISK_INFO ;AN060;; | ||
| 1574 | Extrn READ_DISK_PROC:Far ;AN060;; | ||
| 1575 | ENDIF ;AN060;; | ||
| 1576 | ENDIF ;AN060;; | ||
| 1577 | MOV AX,DOS_GET_EXT_PARSE_ADD ;AN060;; 2FH Interface | ||
| 1578 | MOV DL,DOS_SET_ADDR ;AN060;; Set the READ_DISK_PROC address | ||
| 1579 | LEA DI,READ_DISK_PROC ;AN060;; | ||
| 1580 | INT 2FH ;AN060;; Private interface | ||
| 1581 | jmp short permcom_end ;AN060; and exit | ||
| 1582 | |||
| 1583 | permcom_slash_msg: ;AN060; Keep messages in memory | ||
| 1584 | mov di,offset resgroup:extended_msg_start ;AN060; start address | ||
| 1585 | call set_ext_2f ;AN060; set the extended message address | ||
| 1586 | mov di,offset resgroup:extmsgend+15 ;AN060; get address of resident end | ||
| 1587 | mov [resmsgend],di ;AN060; save it | ||
| 1588 | jmp short permcom_end ;AN060; exit | ||
| 1589 | |||
| 1590 | no_permcom: ;AN060; | ||
| 1591 | cmp ext_msg,set_extended_msg ;AN060; was /msg specified? | ||
| 1592 | jnz no_slash_msg ;AN060; no - no error | ||
| 1593 | mov disp_class,parse_msg_class ;AN060; set up parse error msg class | ||
| 1594 | mov dx,LessArgs_Ptr ;AN060; get message number for "Required parameter missing" | ||
| 1595 | call print_message ;AN060; issue error message | ||
| 1596 | |||
| 1597 | no_slash_msg: | ||
| 1598 | mov ax,(multdos shl 8 or message_2f);AN060; reset parse message pointers | ||
| 1599 | mov dl,set_parse_msg ;AN060; set up parse message address | ||
| 1600 | mov di,pars_msg_off ;AN060; old offset of parse messages | ||
| 1601 | mov es,pars_msg_seg ;AN060; old segment of parse messages | ||
| 1602 | int 2fh ;AN060; go set it | ||
| 1603 | |||
| 1604 | permcom_end: | ||
| 1605 | call sysloadmsg ;AN060; load message addresses | ||
| 1606 | pop di ;AN060; | ||
| 1607 | pop dx ;AN060; | ||
| 1608 | pop ax ;AN060; | ||
| 1609 | pop es ;AN060; get environment back | ||
| 1610 | pop ds ;AN060; | ||
| 1611 | |||
| 1612 | ret ;AN060; | ||
| 1613 | |||
| 1614 | setup_for_messages endp ;AN060; | ||
| 1615 | |||
| 1616 | ; **************************************************************** | ||
| 1617 | ; * | ||
| 1618 | ; * ROUTINE: Set_parse_2f | ||
| 1619 | ; * | ||
| 1620 | ; * FUNCTION: Does the INT 2Fh to DOS to set the PARSE | ||
| 1621 | ; * message address that will later be retrieved | ||
| 1622 | ; * by the message services. | ||
| 1623 | ; * | ||
| 1624 | ; * INPUT: ES set to segment of messages | ||
| 1625 | ; * DI points to offset of messages | ||
| 1626 | ; * | ||
| 1627 | ; * OUTPUT: none | ||
| 1628 | ; * | ||
| 1629 | ; **************************************************************** | ||
| 1630 | |||
| 1631 | Set_parse_2f proc near ;AN060; | ||
| 1632 | |||
| 1633 | mov ax,(multdos shl 8 or message_2f);AN060; set up to call DOS through int 2fh | ||
| 1634 | mov dl,set_parse_msg ;AN060; set up parse message address | ||
| 1635 | int 2fh ;AN060; | ||
| 1636 | |||
| 1637 | ret ;AN060; | ||
| 1638 | |||
| 1639 | Set_parse_2f endp ;AN060; | ||
| 1640 | |||
| 1641 | ; **************************************************************** | ||
| 1642 | ; * | ||
| 1643 | ; * ROUTINE: Set_ext_2f | ||
| 1644 | ; * | ||
| 1645 | ; * FUNCTION: Does the INT 2Fh to DOS to set the EXTENDED | ||
| 1646 | ; * message address that will later be retrieved | ||
| 1647 | ; * by the message services. | ||
| 1648 | ; * | ||
| 1649 | ; * INPUT: ES set to segment of messages | ||
| 1650 | ; * DI points to offset of messages | ||
| 1651 | ; * | ||
| 1652 | ; * OUTPUT: none | ||
| 1653 | ; * | ||
| 1654 | ; **************************************************************** | ||
| 1655 | |||
| 1656 | Set_ext_2f proc near ;AN060; | ||
| 1657 | |||
| 1658 | mov ax,(multdos shl 8 or message_2f);AN060; set up to call DOS through int 2fh | ||
| 1659 | mov dl,set_extended_msg ;AN060; set up extended error message address | ||
| 1660 | int 2fh ;AN060; | ||
| 1661 | |||
| 1662 | ret ;AN060; | ||
| 1663 | |||
| 1664 | Set_ext_2f endp ;AN060; | ||
| 1665 | |||
| 1666 | |||
| 1667 | ASSUME DS:RESGROUP, ES:RESGROUP | ||
| 1668 | |||
| 1669 | .xlist | ||
| 1670 | .xcref | ||
| 1671 | |||
| 1672 | INCLUDE SYSMSG.INC ;AN000; include message services | ||
| 1673 | |||
| 1674 | .list | ||
| 1675 | .cref | ||
| 1676 | |||
| 1677 | MSG_UTILNAME <COMMAND> ;AN000; define utility name | ||
| 1678 | |||
| 1679 | MSG_SERVICES <COMR,NEARmsg,LOADmsg,NOCHECKSTDIN,NOCHECKSTDOUT> ;AC026; include message services macro | ||
| 1680 | |||
| 1681 | include msgdcl.inc | ||
| 1682 | |||
| 1683 | INIT ENDS | ||
| 1684 | |||
| 1685 | END | ||