rev |
line source |
pascal@19515
|
1 ;***************************************************************
|
pascal@19515
|
2 ;****** This file is distributed under GPL
|
pascal@19515
|
3 ;***************************************************************
|
pascal@19515
|
4 ideal
|
pascal@19515
|
5 %crefref
|
pascal@19515
|
6 %noincl
|
pascal@19515
|
7 %nomacs
|
pascal@19636
|
8 p8086
|
pascal@19515
|
9
|
pascal@19515
|
10 group DGROUP _TEXT,_DATA,_BSS
|
pascal@19515
|
11 assume cs:DGROUP,ds:DGROUP
|
pascal@19515
|
12
|
pascal@19515
|
13 segment _TEXT byte public use16 'CODE'
|
pascal@20451
|
14 ends _TEXT
|
pascal@20451
|
15
|
pascal@20451
|
16 segment _DATA byte public use16 'DATA'
|
pascal@20451
|
17 global _data_start:byte
|
pascal@20451
|
18 label _data_start byte
|
pascal@20451
|
19 ifndef NO386
|
pascal@20451
|
20 msg_badcpu db "I need 386+ CPU in real mode or under VCPI manager"
|
pascal@20451
|
21 endif
|
pascal@20451
|
22 global _vcpi:byte
|
pascal@20451
|
23 _vcpi db 0
|
pascal@20528
|
24 msg_badmapping db "VCPI: low 640k need 1:1 mapping",0
|
pascal@20451
|
25
|
pascal@20451
|
26 ends _DATA
|
pascal@20451
|
27
|
pascal@20451
|
28 segment _BSS byte public use16 'BSS'
|
pascal@21757
|
29
|
pascal@21757
|
30 STACK_SIZE = 1024
|
pascal@21757
|
31
|
pascal@20451
|
32 global _bss_start:byte
|
pascal@20451
|
33 label _bss_start byte
|
pascal@21757
|
34 db STACK_SIZE-2 dup(?)
|
pascal@21757
|
35 stktop dw ?
|
pascal@20451
|
36 ifdef EXTRA
|
pascal@20451
|
37 global _cpu_features:dword
|
pascal@20451
|
38 _cpu_features dd ?
|
pascal@20451
|
39 endif
|
pascal@20451
|
40 ends _BSS
|
pascal@20451
|
41
|
pascal@20451
|
42 segment _TEXT byte public use16 'CODE'
|
pascal@19515
|
43
|
pascal@19825
|
44 macro cpuid
|
pascal@19825
|
45 db 0fh,0A2h
|
pascal@19825
|
46 endm
|
pascal@19825
|
47
|
pascal@19515
|
48 org 100h
|
pascal@19515
|
49 global _text_start:byte
|
pascal@19515
|
50 label _text_start byte
|
pascal@19546
|
51
|
pascal@19515
|
52 ;***************************************************************
|
pascal@19515
|
53 ; clear bss
|
pascal@19515
|
54 ;***************************************************************
|
pascal@21757
|
55 mov sp,offset stktop
|
pascal@21757
|
56 mov si,sp
|
pascal@20457
|
57 mov bx, 0F000h ; cld ; cli & empty string
|
pascal@19515
|
58 clearbss:
|
pascal@20451
|
59 mov [si],bl ; clear bss + heap + sp
|
pascal@20426
|
60 inc si
|
pascal@19546
|
61 jne clearbss
|
pascal@19546
|
62
|
pascal@19546
|
63 ;***************************************************************
|
pascal@19546
|
64 ; check CPU
|
pascal@19546
|
65 ;***************************************************************
|
pascal@19546
|
66
|
pascal@19546
|
67 ; Check for oldies
|
pascal@19873
|
68 push bx ; < 286 : flags[12..15] are forced 1
|
pascal@19873
|
69 popf ; = 286 : flags[12..15] are forced 0
|
pascal@19873
|
70 pushf ; > 286 : only flags[15] is forced 0
|
pascal@19873
|
71 pop dx
|
pascal@20451
|
72 add dh,bh ; NS=386+, S+NC=286, S+C=86/186
|
pascal@20451
|
73 ifndef NO386
|
pascal@19873
|
74 mov bx,offset msg_badcpu
|
pascal@20457
|
75 js godie ;it is not a 386+
|
pascal@20451
|
76 else
|
pascal@20457
|
77 js endcpu86 ;it is not a 386+
|
pascal@19546
|
78 endif
|
pascal@19636
|
79 p386
|
pascal@19546
|
80 ; Check for vm
|
pascal@19546
|
81 smsw ax ;SMSW cannot be trapped! :-)
|
pascal@19571
|
82 and al,1 ;MSW_PE
|
pascal@19546
|
83 ; We're in vm
|
pascal@20457
|
84 jnz check_vcpi
|
pascal@20457
|
85
|
pascal@20457
|
86 check_rm_paging:
|
pascal@20457
|
87 ; It's a 386 in real mode, chk for paging (crazy but possible)
|
pascal@20457
|
88 mov eax,cr0
|
pascal@20457
|
89 inc eax ;CR0_PG to S
|
pascal@20457
|
90 jns endcpu386
|
pascal@20457
|
91 no_vcpi:
|
pascal@20457
|
92 p8086
|
pascal@20457
|
93 extrn die:near
|
pascal@20457
|
94 godie:
|
pascal@20457
|
95 call near die
|
pascal@19546
|
96
|
pascal@19546
|
97 ;***************************************************************
|
pascal@19546
|
98 ; checks for vcpi
|
pascal@19546
|
99 ;***************************************************************
|
pascal@19546
|
100 label check_vcpi near
|
pascal@20457
|
101 p386
|
pascal@19546
|
102 push ds
|
pascal@19546
|
103 ; Check whether it is safe to call 67h (we trust only known EMM managers)
|
pascal@20426
|
104 push si
|
pascal@19546
|
105 pop ds
|
pascal@19546
|
106 mov ds,[word 67h*4+2]
|
pascal@20426
|
107 cmp [dword si+10+4],'0XXX'
|
pascal@19546
|
108 jne skip
|
pascal@19825
|
109 ;mov eax,'XMME'
|
pascal@20426
|
110 ;xor eax,[dword si+10]
|
pascal@19546
|
111 ; QMME also works (as told by <J.S.Peatfield@damtp.cambridge.ac.uk>)
|
pascal@19825
|
112 ;shl eax,8
|
pascal@19825
|
113 mov ax,'ME'
|
pascal@20426
|
114 xor ax,[word si+10]
|
pascal@19546
|
115 skip:
|
pascal@19546
|
116 pop ds
|
pascal@19546
|
117 jne no_vcpi
|
pascal@19546
|
118
|
pascal@19546
|
119 ; Check emm manager status and version
|
pascal@19571
|
120 ;mov ah,40h ; get status
|
pascal@19571
|
121 ;int 67h
|
pascal@19571
|
122 ;test ah,ah
|
pascal@19571
|
123 ;jnz no_vcpi
|
pascal@19546
|
124 mov ah,46h ; get version
|
pascal@19546
|
125 int 67h
|
pascal@19546
|
126 test ah,ah
|
pascal@19546
|
127 jnz no_vcpi
|
pascal@19546
|
128 cmp al,40h ; version must be >= 4.0
|
pascal@19546
|
129 jb no_vcpi
|
pascal@19546
|
130 ; Check vcpi manager status
|
pascal@19546
|
131 ;;mov ax,5A01h ; ALLOCATE RAW PAGES
|
pascal@19546
|
132 ;;mov bx,4
|
pascal@19546
|
133 ;;int 67h
|
pascal@19546
|
134 ;;test ah,ah
|
pascal@19546
|
135 ;;jnz no_vcpi
|
pascal@19546
|
136 ;;push dx ;$ save handle
|
pascal@19546
|
137 mov ax,0DE00h ; check for vcpi present
|
pascal@19546
|
138 int 67h
|
pascal@19546
|
139 test ah,ah
|
pascal@19571
|
140 jnz no_vcpi
|
pascal@19546
|
141 is386vcpi:
|
pascal@19546
|
142 extrn prepare_vcpi:near
|
pascal@19546
|
143 call prepare_vcpi
|
pascal@19546
|
144 ; get_vcpi_interface() || die("VCPI: low 640k: need 1:1 mapping");
|
pascal@19546
|
145 ;extrn _get_vcpi_interface:near
|
pascal@19546
|
146 ;call _get_vcpi_interface
|
pascal@19546
|
147 mov bx,offset msg_badmapping
|
pascal@20457
|
148 jnz no_vcpi
|
pascal@21757
|
149 inc [word bx+_vcpi-msg_badmapping]
|
pascal@20457
|
150 endcpu386:
|
pascal@20457
|
151 ifdef EXTRA
|
pascal@20457
|
152 pushfd
|
pascal@20457
|
153 pop dx
|
pascal@20457
|
154 pop ax
|
pascal@20457
|
155 mov bl,al
|
pascal@20457
|
156 xor al,20h ; toggle CPUID feature bit 21
|
pascal@20457
|
157 push ax
|
pascal@20457
|
158 push dx
|
pascal@20457
|
159 popfd
|
pascal@20457
|
160 pushfd
|
pascal@20457
|
161 pop dx
|
pascal@20457
|
162 pop ax
|
pascal@20457
|
163 xor al,bl ; clear C
|
pascal@20457
|
164 je @@no_cpuid ; CPUID feature bit changed ?
|
pascal@20457
|
165 mov eax,80000001h ; Extended Processor Info and Feature Bits
|
pascal@20457
|
166 cpuid
|
pascal@20457
|
167 mov [_cpu_features],edx
|
pascal@20457
|
168 @@no_cpuid:
|
pascal@20457
|
169 endif
|
pascal@20457
|
170 endcpu86:
|
pascal@19636
|
171 p8086
|
pascal@19546
|
172
|
pascal@19515
|
173 ;***************************************************************
|
pascal@19515
|
174 ; build argv & argc
|
pascal@19515
|
175 ;***************************************************************
|
pascal@19546
|
176 extrn _heap_top:word
|
pascal@19546
|
177 mov di,[_heap_top]
|
pascal@19546
|
178 ;xor ax,ax
|
pascal@19546
|
179 ;push ax ; envp (already cleared)
|
pascal@19546
|
180 ;mov [word di],ax ; argv[0] = 0 (idem)
|
pascal@19515
|
181 mov si,80h
|
pascal@19515
|
182 lodsb
|
pascal@19515
|
183 cmp al,7Eh
|
pascal@19515
|
184 jbe alok
|
pascal@19515
|
185 mov al,7Eh
|
pascal@19515
|
186 alok:
|
pascal@19546
|
187 cbw
|
pascal@19515
|
188 xchg ax,bx
|
pascal@19515
|
189 mov [bx+si],bh ; set eos
|
pascal@19515
|
190 argbuild:
|
pascal@20160
|
191 ifdef DEBUG
|
pascal@20142
|
192 p386
|
pascal@20142
|
193 pusha
|
pascal@20142
|
194 mov bx,si
|
pascal@20142
|
195 extrn puts:near
|
pascal@20142
|
196 call puts
|
pascal@20142
|
197 popa
|
pascal@20160
|
198 endif
|
pascal@19515
|
199 mov bx,2 ; argc * 2
|
pascal@19515
|
200 argeos:
|
pascal@20451
|
201 mov cx,1 ; look for a start of string
|
pascal@19515
|
202 mov [byte si-1],bh ; mark eos
|
pascal@19515
|
203 mov ah,20h ; space will be eos
|
pascal@19515
|
204 arglp:
|
pascal@19515
|
205 lodsb
|
pascal@19515
|
206 cmp al,0h
|
pascal@19515
|
207 je argdone
|
pascal@19515
|
208 cmp al,20h
|
pascal@19515
|
209 jb argeos
|
pascal@19515
|
210 cmp al,ah
|
pascal@19515
|
211 je argeos
|
pascal@19515
|
212 cmp al,27h
|
pascal@19515
|
213 je isargstr
|
pascal@19515
|
214 cmp al,22h
|
pascal@19515
|
215 je isargstr
|
pascal@20451
|
216 jcxz arglp ; not start of string
|
pascal@19515
|
217 dec si
|
pascal@19884
|
218 ;jmp newarg
|
pascal@20451
|
219 db 0BAh ; mov dx,im opcode
|
pascal@19515
|
220 isargstr:
|
pascal@19515
|
221 mov ah,al ; expected eos
|
pascal@19515
|
222 newarg:
|
pascal@19515
|
223 mov [word bx+di],si ; argv[argc++] = si
|
pascal@19515
|
224 inc bx
|
pascal@19515
|
225 inc bx
|
pascal@20451
|
226 dec cx
|
pascal@19515
|
227 jmp arglp
|
pascal@19515
|
228 argdone:
|
pascal@19515
|
229 ;mov [word bx+di],0 ; argv[argc] = 0
|
pascal@19546
|
230 lea ax,[bx+di+2]
|
pascal@19546
|
231 mov [_heap_top],ax
|
pascal@19515
|
232 push di ; argv
|
pascal@19515
|
233 shr bx,1
|
pascal@19515
|
234 push bx ; argc
|
pascal@19515
|
235 ifndef filearg
|
pascal@19515
|
236 mov bx,[di+2] ; argv[1]
|
pascal@20528
|
237 extrn openargs:near
|
pascal@20528
|
238 call near openargs
|
pascal@19515
|
239 jc argend
|
pascal@19515
|
240 pop bx ; trash argc, argv >> 1Kb !
|
pascal@19546
|
241 global read_cmdline:near
|
pascal@20528
|
242 pop cx ; sizemax=argv
|
pascal@19546
|
243 read_cmdline:
|
pascal@20528
|
244 mov dx,di
|
pascal@20528
|
245 push dx
|
pascal@19515
|
246 push ax
|
pascal@20528
|
247 xchg ax,bx
|
pascal@20528
|
248 extrn @read$cxdxbx:near ; read(fd=bx,buffer=dx,size=cx)
|
pascal@20528
|
249 call near @read$cxdxbx
|
pascal@19515
|
250 pop bx ; fd for close
|
pascal@19515
|
251 pop si ; si=buffer=argv
|
pascal@19515
|
252 add di,ax
|
pascal@19515
|
253 extrn close:near
|
pascal@19515
|
254 call near close
|
pascal@19515
|
255 jmp argbuild
|
pascal@19515
|
256 argend:
|
pascal@19515
|
257 endif
|
pascal@19515
|
258
|
pascal@19515
|
259 ;***************************************************************
|
pascal@21757
|
260 extrn _main:near
|
pascal@21757
|
261 call _main
|
pascal@21757
|
262 ;never return
|
pascal@19538
|
263
|
pascal@19515
|
264 ;***************************************************************
|
pascal@21757
|
265
|
pascal@19515
|
266 ends _TEXT
|
pascal@19515
|
267
|
pascal@19515
|
268
|
pascal@19515
|
269 end _text_start
|
pascal@19515
|
270
|
pascal@19515
|
271 ;###### END OF FILE ############################################
|