summaryrefslogtreecommitdiff
path: root/v4.0/src/CMD/COMMAND/CPARSE.ASM
diff options
context:
space:
mode:
authorGravatar Mark Zbikowski2024-04-25 21:24:10 +0100
committerGravatar Microsoft Open Source2024-04-25 22:32:27 +0000
commit2d04cacc5322951f187bb17e017c12920ac8ebe2 (patch)
tree80ee017efa878dfd5344b44249e6a241f2a7f6e2 /v4.0/src/CMD/COMMAND/CPARSE.ASM
parentMerge pull request #430 from jpbaltazar/typoptbr (diff)
downloadms-dos-main.tar.gz
ms-dos-main.tar.xz
ms-dos-main.zip
MZ is back!HEADmain
Diffstat (limited to 'v4.0/src/CMD/COMMAND/CPARSE.ASM')
-rw-r--r--v4.0/src/CMD/COMMAND/CPARSE.ASM417
1 files changed, 417 insertions, 0 deletions
diff --git a/v4.0/src/CMD/COMMAND/CPARSE.ASM b/v4.0/src/CMD/COMMAND/CPARSE.ASM
new file mode 100644
index 0000000..f751086
--- /dev/null
+++ b/v4.0/src/CMD/COMMAND/CPARSE.ASM
@@ -0,0 +1,417 @@
1 page 80,132
2; SCCSID = @(#)cparse.asm 1.1 85/05/14
3; SCCSID = @(#)cparse.asm 1.1 85/05/14
4 INCLUDE comsw.asm
5
6.xlist
7.xcref
8 INCLUDE DOSSYM.INC
9 INCLUDE DEVSYM.INC
10 INCLUDE comseg.asm
11 INCLUDE comequ.asm
12.list
13.cref
14
15
16TRANDATA SEGMENT PUBLIC BYTE ;AC000;
17 EXTRN BADCD_PTR:WORD ;AC022;
18 EXTRN BADCPMES_ptr:word ;AC000;
19TRANDATA ENDS
20
21TRANSPACE SEGMENT PUBLIC BYTE ;AC000;
22 EXTRN comma:byte
23 EXTRN cpyflag:byte
24 EXTRN CURDRV:BYTE
25 EXTRN ELCNT:BYTE
26 EXTRN ELPOS:BYTE
27 EXTRN EXPAND_STAR:BYTE
28 EXTRN SKPDEL:BYTE
29 EXTRN STARTEL:WORD
30 EXTRN SWITCHAR:BYTE
31 EXTRN switch_list:byte
32 EXTRN TPA:WORD
33TRANSPACE ENDS
34
35TRANCODE SEGMENT PUBLIC BYTE
36
37ASSUME CS:TRANGROUP,DS:TRANGROUP,ES:TRANGROUP,SS:NOTHING
38
39 EXTRN CERROR:NEAR
40
41 PUBLIC BADCDERR ;AC022;
42 PUBLIC CPARSE
43
44SWCOUNT EQU 5 ; Must agree with length of switch_list
45
46;-----------------------------------------------------------------------;
47; ENTRY: ;
48; DS:SI Points input buffer ;
49; ES:DI Points to the token buffer ;
50; BL Special delimiter for this call ;
51; Always checked last ;
52; set it to space if there is no special delimiter ;
53; EXIT: ;
54; DS:SI Points to next char in the input buffer ;
55; ES:DI Points to the token buffer ;
56; [STARTEL] Points to start of last element of path in token ;
57; points to a NUL for no element strings 'd:' 'd:/' ;
58; CX Character count ;
59; BH Condition Code ;
60; Bit 1H of BH set if switch character ;
61; Token buffer contains char after ;
62; switch character ;
63; BP has switch bits set (ORing only) ;
64; Bit 2H of BH set if ? or * in token ;
65; if * found element ? filled ;
66; Bit 4H of BH set if path sep in token ;
67; Bit 80H of BH set if the special delimiter ;
68; was skipped at the start of this token ;
69; Token buffer always starts d: for non switch tokens ;
70; CARRY SET ;
71; if CR on input ;
72; token buffer not altered ;
73; ;
74; DOES NOT RETURN ON BAD PATH, OR TRAILING SWITCH CHAR ERROR ;
75; MODIFIES: ;
76; CX, SI, AX, BH, DX and the Carry Flag ; ;
77; ;
78; -----------------------------------------------------------------------;
79;---------------
80; Modifications to cparse: recognition of right and left parentheses
81; as integral tokens, and removal of automatic upper-case conversion code.
82;
83; Both modifications were installed in the course of adding a coherent
84; command-line parser to COMMAND.COM which builds a UNIX-style argv[]/argc
85; structure for command-line arguments. This parser relies on cparse to
86; recognize individual tokens.
87;
88; To process for-loops correctly, parentheses must therefore be
89; recognized as tokens. The upper-case conversion code was removed so
90; that commands (such as for and echo) would be able to use the "original"
91; text of the command line.
92;
93; Note also the modification to prevent the automatic conversion of colons
94; into spaces WITHIN THE SOURCE TEXT!
95;
96; Also note that BP is also clobbered if cparse recognizes any switches
97; on the command line.
98;
99; Alan L, OS/MSDOS 14 August 1983
100;---------------
101
102CPARSE:
103ASSUME DS:TRANGROUP,ES:TRANGROUP
104
105 xor ax,ax
106 mov [STARTEL],DI ; No path element (Is DI correct?)
107 mov [ELPOS],al ; Start in 8 char prefix
108 mov [SKPDEL],al ; No skip delimiter yet
109 mov bh,al ; Init nothing
110 pushf ; save flags
111 push di ; save the token buffer addrss
112 xor cx,cx ; no chars in token buffer
113 mov comma,cl ;g reset comma flag
114moredelim:
115 LODSB
116 INVOKE DELIM
117 JNZ SCANCDONE
118 CMP AL,' '
119 JZ moredelim
120 CMP AL,9
121 JZ moredelim
122 xchg al,[SKPDEL]
123 or al,al
124 jz moredelim ; One non space/tab delimiter allowed
125 test bh,080h ;g has a special char been found?
126 jz no_comma ;g no - just exit
127 mov comma,1 ;g set comma flag
128no_comma:
129 JMP x_done ; Nul argument
130
131SCANCDONE:
132
133;;;; IF NOT KANJI 3/3/KK
134;---------------
135; Mod to avoid upper-case conversion.
136; cmp cpyflag,1 3/3/KK
137; jnz cpcont1 3/3/KK
138; invoke UPCONV 3/3/KK
139cpcont1:
140;---------------
141;;;; ENDIF 3/3/KK
142
143 cmp al,bl ; Special delimiter?
144 jnz nospec
145 or bh,80H
146 jmp short moredelim
147
148nospec:
149 cmp al,0DH ; a CR?
150 jne ncperror
151 jmp cperror
152
153ncperror:
154 cmp al,[SWITCHAR] ; is the char the switch char?
155 jne na_switch ; yes, process...
156 jmp a_switch
157
158na_switch:
159 mov dl,':'
160 cmp byte ptr [si],dl
161 jne anum_chard ; Drive not specified
162
163;;;; IF KANJI 3/3/KK
164;---------------
165; Mod to avoid upper-case conversion.
166 cmp cpyflag,1
167 jnz cpcont2
168 invoke UPCONV
169cpcont2:
170;---------------
171;;;; ENDIF 3/3/KK
172
173 call move_char
174 lodsb ; Get the ':'
175 call move_char
176 mov [STARTEL],di
177 mov [ELCNT],0
178 jmp anum_test
179
180anum_chard:
181 mov [STARTEL],di
182 mov [ELCNT],0 ; Store of this char sets it to one
183 cmp cpyflag,1 ; Was CPARSE called from COPY?
184 jnz anum_char ; No, don't add drive spec.
185 invoke PATHCHRCMP ; Starts with a pathchar?
186 jnz anum_char ; no
187 push ax
188 mov al,[CURDRV] ; Insert drive spec
189 add al,capital_A
190 call move_char
191 mov al,':'
192 call move_char
193 pop ax
194 mov [STARTEL],di
195 mov [ELCNT],0
196
197anum_char:
198
199;;;; IF KANJI 3/3/KK
200 invoke TESTKANJ
201 jz NOTKANJ ;AC048;
202 call move_char
203 lodsb
204 jmp short notspecial
205
206NOTKANJ: ;AN048; If not kanji
207 cmp cpyflag,1 ;AN048; and if we're in COPY
208 jnz testdot ;AN048;
209 invoke upconv ;AN048; upper case the char
210
211TESTDOT:
212;;;; ENDIF 3/3/KK
213
214 cmp al,dot_chr
215 jnz testquest
216 inc [ELPOS] ; flag in extension
217 mov [ELCNT],0FFH ; Store of the '.' resets it to 0
218
219testquest:
220 cmp al,'?'
221 jnz testsplat
222 or bh,2
223
224testsplat:
225 cmp al,star
226 jnz testpath
227 or bh,2
228 cmp byte ptr [expand_star],0
229 jnz expand_filename
230 jmp SHORT testpath
231
232badperr2j:
233 jmp badperr2
234
235expand_filename:
236 mov ah,7
237 cmp [ELPOS],0
238 jz gotelcnt
239 mov ah,2
240
241gotelcnt:
242 mov al,'?'
243 sub ah,[ELCNT]
244 jc badperr2j
245 xchg ah,cl
246 jcxz testpathx
247
248qmove:
249 xchg ah,cl
250 call move_char
251 xchg ah,cl
252 loop qmove
253
254testpathx:
255 xchg ah,cl
256
257testpath:
258 invoke PATHCHRCMP
259 jnz notspecial
260 or bh,4
261 cmp byte ptr [expand_star],0
262 jz no_err_check
263 test bh,2 ; If just hit a '/', cannot have ? or * yet
264 jnz badperr
265
266no_err_check:
267 mov [STARTEL],di ; New element
268 INC [STARTEL] ; Point to char after /
269 mov [ELCNT],0FFH ; Store of '/' sets it to 0
270 mov [ELPOS],0
271
272notspecial:
273 call move_char ; just an alphanum string
274anum_test:
275
276 lodsb
277
278;;;; IF NOT KANJI 3/3/KK
279;---------------
280; Mod to avoid upper-case conversion.
281; cmp cpyflag,1 3/3/KK
282; jnz cpcont3 3/3/KK
283; invoke UPCONV 3/3/KK
284cpcont3:
285;---------------
286;;;; ENDIF 3/3/KK
287
288 INVOKE DELIM
289 je x_done
290
291 cmp al,0DH
292 je x_done
293 cmp al,[SWITCHAR]
294 je x_done
295 cmp al,bl
296 je x_done
297 cmp al,':' ; ':' allowed as trailer because
298 ; of devices
299;;;; IF KANJI 3/3/KK
300 je FOO15
301 jmp anum_char
302FOO15:
303;;; ELSE 3/3/KK
304;;; jne anum_charj 3/3/KK
305;;; ENDIF 3/3/KK
306
307;---------------
308; Modification made for parseline.
309; Why would it be necessary to change colons to spaces? In this
310; case, EVERY colon is changed to a space; e.g., 'f:' yields 'f ',
311; but so does 'echo foo:bar' yield 'echo foo bar'.
312;---------------
313 cmp cpyflag,2 ; Is CPARSE parsing the 1st token from
314 ; from PARSELINE?
315 jnz cpcont4 ; No, continue
316 call move_char ; Yes, save the ':' and go get another
317 jmp anum_test ; character.
318
319cpcont4:
320 inc si ;Skip the ':'
321 jmp short x_done
322
323anum_charj:
324 jmp anum_char
325
326badperr2:
327 mov dx,offset trangroup:BADCPMES_ptr
328 jmp CERROR
329
330badperr:
331BADCDERR: ;AC022; Issue "Invalid Directory"
332 MOV DX,OFFSET TRANGROUP:BADCD_ptr ;AC022; message
333 JMP CERROR ;AC022;
334
335cperror:
336 dec si ; adjust the pointer
337 pop di ; retrive token buffer address
338 popf ; restore flags
339 stc ; set the carry bit
340 return
341
342x_done:
343 dec si ; adjust for next round
344;---------------
345; Mod to recognize right and left parens as integral tokens.
346x_done2:
347;---------------
348 jmp short out_token
349
350a_switch:
351 OR BH,1 ; Indicate switch
352 OR BP,fSwitch
353 INVOKE SCANOFF
354 INC SI
355 invoke testkanj ;AN057; See if DBCS lead byte
356 jz a_switch_notkanj ;AN057; no - continue processing
357 call move_char ;AN057; DBCS - store first byte
358 lodsb ;AN057; get second byte
359 call move_char ;AN057; store second byte
360 or bp,fBadSwitch ;AN057; DBCS switch is invalid
361 jmp short out_token ;AN057; don't bother checking switch
362a_switch_notkanj: ;AN057;
363 cmp al,0DH
364 jne Store_swt
365 mov al,0
366 stosb ; null at the end
367 OR BP,fBadSwitch
368 jmp cperror ; Trailing switch character error
369 ; BP = fSwitch but no switch
370 ; bit is set (unknown switch)
371Store_swt:
372 call move_char ; store the character
373;
374;---------------
375; This upconv call must stay. It is used to identify copy-switches
376; on the command line, and won't store anything into the output buffer.
377 invoke UPCONV
378;---------------
379;
380 PUSH ES
381 PUSH DI
382 PUSH CX
383 PUSH CS
384 POP ES
385ASSUME ES:TRANGROUP
386 MOV DI,OFFSET TRANGROUP:switch_list
387 MOV CX,SWCOUNT
388 OR BP,fBadSwitch
389 REPNE SCASB
390 JNZ out_tokenp
391 AND BP,NOT fBadSwitch
392 MOV AX,1
393 SHL AX,CL
394 OR BP,AX
395
396out_tokenp:
397 POP CX
398 POP DI
399 POP ES
400
401ASSUME ES:NOTHING
402out_token:
403 mov al,0
404 stosb ; null at the end
405 pop di ; restore token buffer pointer
406 popf
407 clc ; clear carry flag
408 return
409
410move_char:
411 stosb ; store char in token buffer
412 inc cx ; increment char count
413 inc [ELCNT] ; increment element count for * substi
414 return
415
416TRANCODE ENDS
417 END