diff options
Diffstat (limited to 'v4.0/src/DEV/XMAEM/INDEGDT.ASM')
| -rw-r--r-- | v4.0/src/DEV/XMAEM/INDEGDT.ASM | 379 |
1 files changed, 379 insertions, 0 deletions
diff --git a/v4.0/src/DEV/XMAEM/INDEGDT.ASM b/v4.0/src/DEV/XMAEM/INDEGDT.ASM new file mode 100644 index 0000000..e945373 --- /dev/null +++ b/v4.0/src/DEV/XMAEM/INDEGDT.ASM | |||
| @@ -0,0 +1,379 @@ | |||
| 1 | PAGE 60,132 | ||
| 2 | TITLE INDEGDT - 386 XMA Emulator - Build Global Descriptor Table | ||
| 3 | |||
| 4 | COMMENT # | ||
| 5 | * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * | ||
| 6 | * * | ||
| 7 | * MODULE NAME : INDEGDT * | ||
| 8 | * * | ||
| 9 | * * | ||
| 10 | * 5669-196 (C) COPYRIGHT 1988 Microsoft Corp. * | ||
| 11 | * * | ||
| 12 | * DESCRIPTIVE NAME: Build the Global Descriptor Table (GDT) * | ||
| 13 | * * | ||
| 14 | * STATUS (LEVEL) : Version (0) Level (1.0) * | ||
| 15 | * * | ||
| 16 | * FUNCTION : Build the Global Descriptor Table (GDT) for the 80386 * | ||
| 17 | * XMA emulator * | ||
| 18 | * * | ||
| 19 | * MODULE TYPE : ASM * | ||
| 20 | * * | ||
| 21 | * REGISTER USAGE : 80386 Standard * | ||
| 22 | * * | ||
| 23 | * RESTRICTIONS : None * | ||
| 24 | * * | ||
| 25 | * DEPENDENCIES : None * | ||
| 26 | * * | ||
| 27 | * ENTRY POINT : GDT_BLD * | ||
| 28 | * * | ||
| 29 | * LINKAGE : Called NEAR from INDEINI * | ||
| 30 | * * | ||
| 31 | * INPUT PARMS : None * | ||
| 32 | * * | ||
| 33 | * RETURN PARMS : None * | ||
| 34 | * * | ||
| 35 | * OTHER EFFECTS : None * | ||
| 36 | * * | ||
| 37 | * EXIT NORMAL : Return to INDEINI * | ||
| 38 | * * | ||
| 39 | * EXIT ERROR : None * | ||
| 40 | * * | ||
| 41 | * EXTERNAL * | ||
| 42 | * REFERENCES : None * | ||
| 43 | * * | ||
| 44 | * SUB-ROUTINES : SREG_2_24BITS - Convert the 16 bit value in AX to a 24 * | ||
| 45 | * bit value in DH and AX. * | ||
| 46 | * ADDOFF - Add the 16 bit offset in AX to the 24 bit value * | ||
| 47 | * in DH and BX. * | ||
| 48 | * * | ||
| 49 | * MACROS : DESCR_DEF - Declare a descriptor entry * | ||
| 50 | * DESCR_INIT - Initialize a descriptor * | ||
| 51 | * * | ||
| 52 | * CONTROL BLOCKS : INDEDAT - System data structures * | ||
| 53 | * * | ||
| 54 | * CHANGE ACTIVITY : * | ||
| 55 | * * | ||
| 56 | * $MOD(INDEGDT) COMP(LOAD) PROD(3270PC) : * | ||
| 57 | * * | ||
| 58 | * $D0=D0004700 410 870530 D : NEW FOR RELEASE 1.1 * | ||
| 59 | * $P1=P0000293 410 870731 D : LIMIT LINES TO 80 CHARACTERS * | ||
| 60 | * $P2=P0000312 410 870804 D : CHANGE COMPONENT FROM MISC TO LOAD * | ||
| 61 | * $P3=P0000410 410 870918 D : RELOCATE DATA AREAS TO MAKE ROOM FOR BIT MAP * | ||
| 62 | * * | ||
| 63 | * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * | ||
| 64 | # | ||
| 65 | |||
| 66 | .286P ; Enable recognition of 286 privileged instructs. | ||
| 67 | |||
| 68 | .XLIST ; Turn off the listing | ||
| 69 | INCLUDE INDEDAT.INC ; Include system data structures | ||
| 70 | INCLUDE INDEACC.INC ; Include access byte definitions | ||
| 71 | |||
| 72 | IF1 ; Only include macros on the first pass | ||
| 73 | INCLUDE INDEDES.MAC ; Descriptor macros | ||
| 74 | ENDIF | ||
| 75 | .LIST ; Turn on the listing | ||
| 76 | |||
| 77 | PROG SEGMENT PARA PUBLIC 'PROG' | ||
| 78 | |||
| 79 | ASSUME CS:PROG | ||
| 80 | ASSUME SS:NOTHING | ||
| 81 | ASSUME DS:PROG | ||
| 82 | ASSUME ES:NOTHING | ||
| 83 | |||
| 84 | INDEGDT LABEL NEAR | ||
| 85 | |||
| 86 | PUBLIC INDEGDT | ||
| 87 | PUBLIC GDT_BLD | ||
| 88 | PUBLIC GDT_DATA_START | ||
| 89 | PUBLIC SREG_2_24BITS | ||
| 90 | |||
| 91 | ; The following data define a pre-initialized GDT. They represent | ||
| 92 | ; all structures which will exist when the emulator comes up. | ||
| 93 | ; THESE MUST BE INITIALIZED IN THE ORDER IN WHICH THEY APPEAR IN THE | ||
| 94 | ; GDT_DEF STRUCTURE DEFINITION AS IT APPEARS IN INDEDAT.INC. This data | ||
| 95 | ; area will be copied from the code segment to the final GDT resting | ||
| 96 | ; place during initialization. | ||
| 97 | |||
| 98 | GDT_DATA_START LABEL WORD | ||
| 99 | |||
| 100 | ; First entry is unusable | ||
| 101 | |||
| 102 | DESCR_DEF SEG, 0, 0, 0, 0 | ||
| 103 | |||
| 104 | ; The descriptor for GDT itself | ||
| 105 | |||
| 106 | DESCR_DEF SEG, GDT_LEN, GDT_LOC, 3, CPL0_DATA_ACCESS | ||
| 107 | PAGE | ||
| 108 | |||
| 109 | ; The system IDT descriptor | ||
| 110 | |||
| 111 | DESCR_DEF SEG, SIDT_LEN, SIDT_LOC, 3, CPL0_DATA_ACCESS | ||
| 112 | |||
| 113 | ; The real system data area descriptor (XMA pages) | ||
| 114 | |||
| 115 | DESCR_DEF SEG, 0FFFFH, 0000H, 11H, CPL0_DATA_ACCESS | ||
| 116 | |||
| 117 | ; The virtual IDT descriptor (not needed so use for all memory) | ||
| 118 | |||
| 119 | DESCR_DEF SEG, MAX_SEG_LEN, NSEG@_LO, NSEG@_HI, CPL0_DATA_ACCESS | ||
| 120 | |||
| 121 | ; The LOADALL descriptor | ||
| 122 | |||
| 123 | DESCR_DEF SEG, 0, 0, 0, 0 | ||
| 124 | PAGE | ||
| 125 | |||
| 126 | ; Compatible monochrome display | ||
| 127 | |||
| 128 | DESCR_DEF SEG, MCRT_SIZE, MCRT@_LO, MCRT@_HI, CPL0_DATA_ACCESS | ||
| 129 | |||
| 130 | ; Compatible color display | ||
| 131 | |||
| 132 | DESCR_DEF SEG, CCRT_SIZE, CCRT@_LO, CCRT@_HI, CPL0_DATA_ACCESS | ||
| 133 | |||
| 134 | ; Enhanced color display - one entry for each 64K P1C | ||
| 135 | |||
| 136 | DESCR_DEF SEG, ECCRT_SIZE, ECCRT@_LO_LO, ECCRT@_LO_HI, CPL0_DATA_ACCESS | ||
| 137 | |||
| 138 | ; Second part of enhanced display P1C | ||
| 139 | |||
| 140 | DESCR_DEF SEG, ECCRT_SIZE, ECCRT@_HI_LO, ECCRT@_HI_HI, CPL0_DATA_ACCESS | ||
| 141 | PAGE | ||
| 142 | |||
| 143 | ; Code segment for ROM code, system IDT | ||
| 144 | |||
| 145 | DESCR_DEF SEG, MAX_SEG_LEN, CSEG@_LO, CSEG@_HI, CPL0_CODE_ACCESS | ||
| 146 | |||
| 147 | ; Data segment for ROM code, system IDT | ||
| 148 | |||
| 149 | DESCR_DEF SEG, MAX_SEG_LEN, CSEG@_LO, CSEG@_HI, CPL0_CODE_ACCESS | ||
| 150 | |||
| 151 | ; Temporarily, the monitor is installed using the patch | ||
| 152 | ; segment descriptors in the GDT | ||
| 153 | |||
| 154 | MSEG@_LO EQU 00000H | ||
| 155 | MSEG@_HI EQU 008H | ||
| 156 | |||
| 157 | |||
| 158 | ; Code segment for patch code, system IDT | ||
| 159 | |||
| 160 | DESCR_DEF SEG, MAX_SEG_LEN, MSEG@_LO, MSEG@_HI, CPL0_CODE_ACCESS | ||
| 161 | |||
| 162 | ; Data segment for patch code, system IDT | ||
| 163 | |||
| 164 | DESCR_DEF SEG, MAX_SEG_LEN, MSEG@_LO, MSEG@_HI, CPL0_DATA_ACCESS | ||
| 165 | PAGE | ||
| 166 | |||
| 167 | ; Code segment for ROM code, virtual IDT | ||
| 168 | |||
| 169 | DESCR_DEF SEG, MAX_SEG_LEN, CSEG@_LO, CSEG@_HI, CPL0_CODE_ACCESS | ||
| 170 | |||
| 171 | ; Data segment for ROM code, virtual IDT | ||
| 172 | |||
| 173 | DESCR_DEF SEG, MAX_SEG_LEN, CSEG@_LO, CSEG@_HI, CPL0_CODE_ACCESS | ||
| 174 | |||
| 175 | ; Code segment for patch code, virtual IDT | ||
| 176 | |||
| 177 | DESCR_DEF SEG, NULL_SEG_LEN, NSEG@_LO, NSEG@_HI, NULL_ACCESS | ||
| 178 | |||
| 179 | ; Data segment for patch code, virtual IDT | ||
| 180 | |||
| 181 | DESCR_DEF SEG, NULL_SEG_LEN, NSEG@_LO, NSEG@_HI, NULL_ACCESS | ||
| 182 | PAGE | ||
| 183 | |||
| 184 | ; Temporary descriptors for ES, CS, SS, and DS | ||
| 185 | |||
| 186 | DESCR_DEF SEG, MAX_SEG_LEN, NSEG@_LO, NSEG@_HI, CPL0_DATA_ACCESS | ||
| 187 | |||
| 188 | DESCR_DEF SEG, MAX_SEG_LEN, NSEG@_LO, NSEG@_HI, CPL0_CODE_ACCESS | ||
| 189 | |||
| 190 | DESCR_DEF SEG, MAX_SEG_LEN, NSEG@_LO, NSEG@_HI, CPL0_DATA_ACCESS | ||
| 191 | |||
| 192 | DESCR_DEF SEG, MAX_SEG_LEN, NSEG@_LO, NSEG@_HI, CPL0_DATA_ACCESS | ||
| 193 | PAGE | ||
| 194 | |||
| 195 | ; These DQ's pad out the space between the last MultiPC descriptor and the | ||
| 196 | ; PMVM descriptors. They don't need initialization. | ||
| 197 | |||
| 198 | DQ 9 DUP (0) ; These 9 are for the Monitor descriptors | ||
| 199 | |||
| 200 | ; This is for the keyboard owner (not used) | ||
| 201 | |||
| 202 | DQ 0 | ||
| 203 | |||
| 204 | ; These 16 are for the virtual timer support | ||
| 205 | |||
| 206 | DQ 16 DUP (0) | ||
| 207 | |||
| 208 | ; The following 32 descriptors are for exception condition task gates. | ||
| 209 | |||
| 210 | REPT 32 | ||
| 211 | DQ 0 | ||
| 212 | ENDM | ||
| 213 | |||
| 214 | ; The following 16 pairs are for the hardware interrupt handling tasks. | ||
| 215 | |||
| 216 | REPT 16 | ||
| 217 | DQ 0 | ||
| 218 | DQ 0 | ||
| 219 | ENDM | ||
| 220 | |||
| 221 | ; The following pair is for the DISPATCH task | ||
| 222 | |||
| 223 | DESCR_DEF SEG, TSS_LEN, DISPATCH_LOC, 3, <TSS_ACCESS OR FREE_TSS> | ||
| 224 | DESCR_DEF SEG, TSS_LEN, DISPATCH_LOC, 3, CPL0_DATA_ACCESS | ||
| 225 | |||
| 226 | DESCR_DEF SEG, 0, 0, 0,LDT_DESC | ||
| 227 | |||
| 228 | ; BASIC's segment | ||
| 229 | |||
| 230 | DESCR_DEF SEG, 07FFFH, 06000H, 0FH, CPL0_DATA_ACCESS | ||
| 231 | |||
| 232 | ; BIOS's segment | ||
| 233 | |||
| 234 | DESCR_DEF SEG, 01FFFH, 00000H, 0FH, CPL0_DATA_ACCESS | ||
| 235 | |||
| 236 | DQ 13 DUP (0) ; Reserved guys | ||
| 237 | |||
| 238 | ; The following guys are junk ! Used before the first TSS allocated. These | ||
| 239 | ; have to be in the PMVM location in the GDT. | ||
| 240 | |||
| 241 | DESCR_DEF SEG, TSS_LEN, 0C000H, 0, FREE_TSS ; For the TR | ||
| 242 | |||
| 243 | DESCR_DEF SEG, TSS_LEN, 0C000H, 0, CPL0_DATA_ACCESS ; TSS as data | ||
| 244 | |||
| 245 | DESCR_DEF SEG, GDT_LEN, 0D000H, 0, LDT_DESC ; For the LDTR | ||
| 246 | |||
| 247 | DESCR_DEF SEG, GDT_LEN, 0D000H, 0, CPL0_DATA_ACCESS ; LDT as data | ||
| 248 | |||
| 249 | GDT_DATA_END LABEL WORD | ||
| 250 | |||
| 251 | COPY_LEN EQU GDT_DATA_END-GDT_DATA_START | ||
| 252 | |||
| 253 | ; | ||
| 254 | ; End of pre-allocated GDT | ||
| 255 | ; | ||
| 256 | |||
| 257 | PAGE | ||
| 258 | |||
| 259 | GDT_BLD PROC NEAR | ||
| 260 | |||
| 261 | ; Copy the pre-initialized GDT into its proper location in memory | ||
| 262 | |||
| 263 | CLI ; All string operations go forward | ||
| 264 | |||
| 265 | MOV SI,OFFSET GDT_DATA_START ; DS:SI points to the pre-initialized | ||
| 266 | ; GDT above | ||
| 267 | MOV CX,COPY_LEN/2 ; CX = number of words to copy | ||
| 268 | MOV DI,GDT_LOC ; ES:DI points to the GDT location | ||
| 269 | REP MOVSW ; Copy GDT into its final resting place | ||
| 270 | |||
| 271 | ; Now let's initialize some of the GDT entries | ||
| 272 | |||
| 273 | ; Set up the descriptors for our code segment and data segment | ||
| 274 | |||
| 275 | MOV AX,CS ; Get our CS | ||
| 276 | CALL SREG_2_24BITS ; And convert it to a 24 bit offset | ||
| 277 | MOV BX,AX ; Get the monitor offset | ||
| 278 | |||
| 279 | ALLSET: | ||
| 280 | DESCR_INIT SEG, SYS_PATCH_CS, 07FFFH, BX, DH, CPL0_CODE_ACCESS | ||
| 281 | DESCR_INIT SEG, SYS_PATCH_DS, 0FFFFH, BX, DH, CPL0_DATA_ACCESS | ||
| 282 | |||
| 283 | ; Initialize the descriptor for the GDT | ||
| 284 | |||
| 285 | MOV AX,ES ; Get the segment of the GDT | ||
| 286 | CALL SREG_2_24BITS ; Convert to a 24 bit offset | ||
| 287 | MOV DL,DH ; Save a copy of the hi byte | ||
| 288 | MOV BX,GDT_LOC ; Add on the offset of the GDT | ||
| 289 | CALL ADDOFF | ||
| 290 | |||
| 291 | DESCR_INIT SEG, GDT_PTR, GDT_LEN, BX, DH, CPL0_DATA_ACCESS | ||
| 292 | |||
| 293 | ; Initialize the descriptor for the IDT | ||
| 294 | |||
| 295 | MOV BX,SIDT_LOC ; DH,AX already contains the segment | ||
| 296 | ; converted to 24 bits so all we | ||
| 297 | CALL ADDOFF ; have to do is add on the offset | ||
| 298 | |||
| 299 | DESCR_INIT SEG, MON_IDT_PTR, SIDT_LEN, BX, DH, CPL0_DATA_ACCESS | ||
| 300 | |||
| 301 | ; Initialize the descriptor that accesses all of memory as data | ||
| 302 | |||
| 303 | DESCR_INIT BSEG, HUGE_PTR, 0FFFFH, 0, 0, CPL0_DATA_ACCESS | ||
| 304 | |||
| 305 | ; Initialize the descriptors for the V86 task's LDT | ||
| 306 | |||
| 307 | MOV BX,DISPATCH_LOC ; @P3C | ||
| 308 | CALL ADDOFF | ||
| 309 | |||
| 310 | DESCR_INIT SEG,SCRUBBER.VM_LDTR,00FFFH,BX,DH,LDT_DESC | ||
| 311 | DESCR_INIT SEG,SCRUBBER.LDT_PTR,00FFFH,BX,DH,CPL0_DATA_ACCESS | ||
| 312 | |||
| 313 | ; Initialize the descriptors for the V86 task's TR | ||
| 314 | |||
| 315 | MOV BX,DISPATCH_LOC ; @P3C | ||
| 316 | CALL ADDOFF | ||
| 317 | |||
| 318 | DESCR_INIT SEG,SCRUBBER.VM_TR,TSS_LEN,BX,DH,FREE_TSS_386 ; @P3C | ||
| 319 | DESCR_INIT SEG,SCRUBBER.TSS_PTR,TSS_LEN,BX,DH,CPL0_DATA_ACCESS; @P3C | ||
| 320 | |||
| 321 | RET | ||
| 322 | |||
| 323 | GDT_BLD ENDP | ||
| 324 | |||
| 325 | PAGE | ||
| 326 | ; SREG_2_24BITS converts the segment register 16 bit value in the AX register | ||
| 327 | ; into a 24 bit value in DH and AX | ||
| 328 | ; | ||
| 329 | ; Input : AX = segment register value | ||
| 330 | ; | ||
| 331 | ; Output: AX = 24 bit low word | ||
| 332 | ; DH = 24 bit high byte | ||
| 333 | |||
| 334 | |||
| 335 | SREG_2_24BITS PROC NEAR | ||
| 336 | |||
| 337 | ; Put the high four bits of AH into the low four bits of DH | ||
| 338 | |||
| 339 | MOV DH,AH ; Get the high byte of the segment value | ||
| 340 | ; into DH | ||
| 341 | AND DH,0F0H ; Strip off the low nibble | ||
| 342 | SHR DH,4 ; Shift right four bits | ||
| 343 | |||
| 344 | ; Now shift AX left four bits | ||
| 345 | |||
| 346 | AND AH,00FH ; Strip high nibble from AH | ||
| 347 | ; This keeps the carry flag from being | ||
| 348 | ; set which could effect later ADDs. | ||
| 349 | SHL AX,4 ; Shift AX | ||
| 350 | |||
| 351 | RET | ||
| 352 | |||
| 353 | SREG_2_24BITS ENDP | ||
| 354 | |||
| 355 | PAGE | ||
| 356 | ; ADDOFF adds the 16 bit offset in BX to the 24 bit value in DL and AX. The | ||
| 357 | ; result is left in DH and BX. | ||
| 358 | ; | ||
| 359 | ; Input : DL = 24 bit high byte | ||
| 360 | ; AX = 24 bit low word | ||
| 361 | ; BX = offset to be added | ||
| 362 | ; | ||
| 363 | ; Output: DH = 24 bit high byte | ||
| 364 | ; BX = 24 bit low word | ||
| 365 | |||
| 366 | ADDOFF PROC NEAR | ||
| 367 | |||
| 368 | MOV DH,DL ; Restore the high byte that was saved | ||
| 369 | ; in DL | ||
| 370 | ADD BX,AX ; Add on the offset | ||
| 371 | ADC DH,0 ; Add the carry, if any, to the high | ||
| 372 | ; byte | ||
| 373 | RET | ||
| 374 | |||
| 375 | ADDOFF ENDP | ||
| 376 | |||
| 377 | PROG ENDS | ||
| 378 | |||
| 379 | END | ||