
=== Trace listing source: xmssize.lst
     1                                  ; This is meant to be compiled into a .EXE file which can be used as a device
     2                                  ; Copyright (C) 1996, 2005 Marko Kohtala
     3                                  ; Released under GNU GPL, read the file 'COPYING' for more information
     4                                  
     5                                  ; Use commands: "tasm xmssize" and "tlink xmssize". No options necessary.
     6                                  
     7                                  cpu 186
     8                                  
=== Switch to base=000000h -> "_TEXT"
     9                                  section _TEXT align=16 class=CODE
    10                                                  assume ds:nothing, es:nothing, ss:nothing, cs:_TEXT
    11                                                  ; Device driver header
     0 00000000 FFFF0000                                dd 0FFFFh       ; next
     0 00000004 0080                                    dw 8000h        ; character device
     0 00000006 [C001]                                  dw offset strategy
     0 00000008 [CB01]                                  dw offset interrupt
     0 0000000A 584D5353495A4520                        db 'XMSSIZE '
    17                                  
     0 00000012 00000000                request_ptr     dd 0
     0 00000016 584D5353495A452031      intro_txt       db 'XMSSIZE 1.00 Copyright (c) 1996 Marko Kohtala',13,10
     0 0000001F 2E303020436F707972
     0 00000028 696768742028632920
     0 00000031 31393936204D61726B
     0 0000003A 6F204B6F6874616C61
     0 00000043 0D0A
     0 00000045 546869732070726F67                      db 'This program modifies XMS handle table to support more than 64M of RAM.',13,10
     0 0000004E 72616D206D6F646966
     0 00000057 69657320584D532068
     0 00000060 616E646C6520746162
     0 00000069 6C6520746F20737570
     0 00000072 706F7274206D6F7265
     0 0000007B 207468616E2036344D
     0 00000084 206F662052414D2E0D
     0 0000008D 0A
     0 0000008E 55736520617420796F                      db 'Use at your own risk.',13,10,'$'
     0 00000097 7572206F776E207269
     0 000000A0 736B2E0D0A24
     0 000000A6 0D0A55736167653A20      usage_txt       db 13,10,'Usage: XMSSIZE <Kbytes>',13,10
     0 000000AF 584D5353495A45203C
     0 000000B8 4B62797465733E0D0A
     0 000000C1 3C4B62797465733E20                      db '<Kbytes> is the total amount of memory, not just XMS.',13,10,'$'
     0 000000CA 69732074686520746F
     0 000000D3 74616C20616D6F756E
     0 000000DC 74206F66206D656D6F
     0 000000E5 72792C206E6F74206A
     0 000000EE 75737420584D532E0D
     0 000000F7 0A24
     0 000000F9 0D0A54686973207072      cpu_txt         db 13,10,'This program works only on 386 or better.',13,10,'$'
     0 00000102 6F6772616D20776F72
     0 0000010B 6B73206F6E6C79206F
     0 00000114 6E20333836206F7220
     0 0000011D 6265747465722E0D0A
     0 00000126 24
     0 00000127 0D0A584D5320647269      noXMS_txt       db 13,10,'XMS driver not present or too old.',13,10,'$'
     0 00000130 766572206E6F742070
     0 00000139 726573656E74206F72
     0 00000142 20746F6F206F6C642E
     0 0000014B 0D0A24
     0 0000014E 0D0A4F706572617469      lastUsed_txt    db 13,10,'Operation is too difficult.'
     0 00000157 6F6E20697320746F6F
     0 00000160 20646966666963756C
     0 00000169 742E
     0 0000016B 20446F206974207269                      db ' Do it right after loading HIMEM.SYS',13,10,'$'
     0 00000174 676874206166746572
     0 0000017D 206C6F6164696E6720
     0 00000186 48494D454D2E535953
     0 0000018F 0D0A24
     0 00000192 0D0A43616E206E6F74      tooLittle_txt   db 13,10,'Can not give that little memory.',13,10,'$'
     0 0000019B 206769766520746861
     0 000001A4 74206C6974746C6520
     0 000001AD 6D656D6F72792E0D0A
     0 000001B6 24
     0 000001B7 0D0A446F6E650D0A24      done_txt        db 13,10,'Done',13,10,'$'
    30                                  
    31                                  %ifdef DEBUG
    32                                  intstart_txt    db 'START $'
    33                                  toinit_txt    db 'TOINIT $'
    34                                  init_txt    db 'INIT $'
    35                                  locarg_txt    db 'LOCARG $'
    36                                  exit_txt    db 'EXIT $'
    37                                  tocmd_txt    db 'TOCMD $'
    38                                  cmd_txt    db 'CMD $'
    39                                  %macro debugm 1
    40                                          push dx
    41                                          push ds
    42                                          push ax
    43                                          push cs
    44                                          pop ds
    45                                          mov dx,offset %1
    46                                          mov ah,9
    47                                          int 21h
    48                                          pop ax
    49                                          pop ds
    50                                          pop dx
    51                                  %endmacro
    52                                  %else
    53                                  %macro debugm 1
    54                                  %endmacro
    55                                  %endif
    56                                  
     0 000001C0 2E891E[1200]            strategy:       mov word ptr [cs:request_ptr],bx
     0 000001C5 2E8C06[1400]                            mov word ptr [cs:request_ptr+2],es
     0 000001CA CB                                      retf
    60                                  
     0 000001CB 9C                      interrupt:      pushf
     0 000001CC 06                                      push es
     0 000001CD 1E                                      push ds
     0 000001CE 57                                      push di
     0 000001CF 56                                      push si
     0 000001D0 52                                      push dx
     0 000001D1 51                                      push cx
     0 000001D2 53                                      push bx
     0 000001D3 50                                      push ax
    70                                                  debugm intstart_txt
     0 000001D4 2EC53E[1200]                            lds di,[cs:request_ptr]
     0 000001D9 C745030381                              mov word [di+3],8103h        ; error, done, unknown command...
     0 000001DE C7450E0000                              mov word ptr [di+14],0  ; free this driver
     0 000001E3 8C4D10                                  mov [di+16],cs
     0 000001E6 807D0200                                cmp byte ptr [di+2],0   ; is it init?
     0 000001EA 7532                                    jnz int_exit
    77                                  
    78                                                  debugm toinit_txt
     0 000001EC E85C00                                  call init               ; banner, check CPU
     0 000001EF 7227                                    jc int_error
    81                                  
    82                                                  debugm locarg_txt
     0 000001F1 C57512                                  lds si,[di+18]          ; locate arguments
    84                                  %ifdef DEBUG
    85                                                  mov dx,si
    86                                                  push word [si+4]
    87                                                  mov byte ptr [si+4],'$'
    88                                                  mov ah,9
    89                                                  int 21h
    90                                                  pop word [si+4]
    91                                  %endif
     0 000001F4 BA[A600]                                mov dx,offset usage_txt
     0 000001F7 B95000                                  mov cx,80
    94                                  
     0 000001FA AC                      next_sys_char:  lodsb                   ; must skip the driver name
     0 000001FB 3C0D                                    cmp al,13
     0 000001FD 7419                                    je int_error
     0 000001FF 3C0A                                    cmp al,10
     0 00000201 7415                                    je int_error
     0 00000203 3C20                                    cmp al,' '
     0 00000205 E0F3                                    loopne next_sys_char
     0 00000207 750F                                    jne int_error
   103                                  
   104                                                  debugm tocmd_txt
   105                                  %ifdef DEBUG
   106                                                  mov dx,si
   107                                                  push word [si+4]
   108                                                  mov byte ptr [si+4],'$'
   109                                                  mov ah,9
   110                                                  int 21h
   111                                                  pop word [si+4]
   112                                  %endif
   113                                  cpu 386
     0 00000209 6650                                    push eax
     0 0000020B 6653                                    push ebx
     0 0000020D 6656                                    push esi
     0 0000020F E86E00                                  call cmdline            ; parse arguments
     0 00000212 665E                                    pop esi
     0 00000214 665B                                    pop ebx
     0 00000216 6658                                    pop eax
   121                                  cpu 186
   122                                  int_error:
     0 00000218 0E                                      push cs
     0 00000219 1F                                      pop ds
     0 0000021A B409                                    mov ah,9
     0 0000021C CD21                                    int 21h
   127                                  int_exit:
   128                                                  debugm exit_txt
     0 0000021E 58                                      pop ax
     0 0000021F 5B                                      pop bx
     0 00000220 59                                      pop cx
     0 00000221 5A                                      pop dx
     0 00000222 5E                                      pop si
     0 00000223 5F                                      pop di
     0 00000224 1F                                      pop ds
     0 00000225 07                                      pop es
     0 00000226 9D                                      popf
     0 00000227 CB                                      retf
   139                                  
   140                                                  ;; EXE entry point
   141                                  
   142                                  ..start:
   143                                  main:
     0 00000228 E82000                                  call init
     0 0000022B 720C                                    jc exe_error
     0 0000022D 8A0E8000                                mov cl,[80h]
     0 00000231 30ED                                    xor ch,ch
     0 00000233 BE8100                                  mov si,81h
     0 00000236 E84700                                  call cmdline
   150                                  exe_error:
     0 00000239 9C                                      pushf
     0 0000023A 0E                                      push cs
     0 0000023B 1F                                      pop ds
     0 0000023C B409                                    mov ah,9
     0 0000023E CD21                                    int 21h
     0 00000240 B8004C                                  mov ax,4C00h
     0 00000243 9D                                      popf
     0 00000244 1400                                    adc al,0
     0 00000246 CD21                                    int 21h
   160                                                  ; This should not be reached
     0 00000248 CD20                                    int 20h
   162                                                  ; Surely we are dead already...
     0 0000024A C3                                      ret
   164                                  
   165                                                  ;; FROM THIS ON, IT IS COMMON TO DEVICE AND EXECUTABLE
   166                                  
   167                                                  ;; init preserves ds, whatever it is, and returns with
   168                                                  ;; dx offsetting the error text in cs if carry is set
   169                                                  ;; or happily with success if carry is not set
   170                                  init proc
     0 0000024B BA[1600]                                mov dx,offset intro_txt
     0 0000024E 1E                                      push ds
     0 0000024F 0E                                      push cs
     0 00000250 1F                                      pop ds
     0 00000251 B409                                    mov ah,9
     0 00000253 CD21                                    int 21h
     0 00000255 1F                                      pop ds
   178                                  
     0 00000256 9C                                      pushf           ; Save these to be sure
   180                                  
   181                                  ; From CPUID by Intel
   182                                  ;
   183                                  ;       This procedure determines the type of CPU in a system
   184                                  ;       and sets the cpu_type variable with the appropriate
   185                                  ;       value.
   186                                  ;       All registers are used by this procedure, none are preserved.
   187                                  
   188                                  ;       Intel 8086 CPU check
   189                                  ;       Bits 12-15 of the FLAGS register are always set on the
   190                                  ;       8086 processor.
   191                                  ;
     0 00000257 9C                              pushf                   ; push original FLAGS
     0 00000258 58                              pop     ax              ; get original FLAGS
     0 00000259 89C1                            mov     cx, ax          ; save original FLAGS
     0 0000025B 25FF0F                          and     ax, 0fffh       ; clear bits 12-15 in FLAGS
     0 0000025E 50                              push    ax              ; save new FLAGS value on stack
     0 0000025F 9D                              popf                    ; replace current FLAGS value
     0 00000260 9C                              pushf                   ; get new FLAGS
     0 00000261 58                              pop     ax              ; store new FLAGS in AX
     0 00000262 2500F0                          and     ax, 0f000h      ; if bits 12-15 are set, then CPU
     0 00000265 3D00F0                          cmp     ax, 0f000h      ;   is an 8086/8088
     0 00000268 740D                            je      cpu_error       ; jump if CPU is 8086/8088
   203                                  
   204                                  ;       Intel 286 CPU check
   205                                  ;       Bits 12-15 of the FLAGS register are always clear on the
   206                                  ;       Intel 286 processor in real-address mode.
   207                                  ;
     0 0000026A 81C900F0                        or      cx, 0f000h      ; try to set bits 12-15
     0 0000026E 51                              push    cx              ; save new FLAGS value on stack
     0 0000026F 9D                              popf                    ; replace current FLAGS value
     0 00000270 9C                              pushf                   ; get new FLAGS
     0 00000271 58                              pop     ax              ; store new FLAGS in AX
     0 00000272 2500F0                          and     ax, 0f000h      ; if bits 12-15 clear, CPU=80286
     0 00000275 7506                            jnz     cpu_ok          ; if no bits set, CPU is 80286
   215                                  cpu_error:
     0 00000277 BA[F900]                        mov     dx,offset cpu_txt
     0 0000027A 9D                              popf                    ; restore original flags
     0 0000027B F9                              stc
     0 0000027C C3                              ret
   220                                  
   221                                  cpu_ok:
     0 0000027D 9D                              popf            ; restore original flags
     0 0000027E F8                              clc
     0 0000027F C3                              ret
   225                                  init endp
   226                                  
   227                                                  ;; cmdline expects to have ds:si pointing to argument string
   228                                                  ;; and cx telling the argument string length
   229                                                  ;; Returns with dx pointing to error string in cs.
   230                                                  ;; Carry is set if there really was an error.
   231                                  cmdline proc
   232                                  cpu 386
     0 00000280 6631DB                                  xor ebx,ebx
     0 00000283 FC                                      cld
     0 00000284 E32B                                    jcxz show_usage
     0 00000286 6631C0                                  xor eax,eax     ; clear for easier addition to ebx
     0 00000289 AC                      nextspace:      lodsb
     0 0000028A 3C20                                    cmp al,' '
     0 0000028C 7504                                    jne nextdigit
     0 0000028E E2F9                                    loop nextspace
     0 00000290 EB1F                                    jmp show_usage
   242                                  nextdigit:
     0 00000292 3C0D                                    cmp al,13
     0 00000294 7416                                    jz end_of_line
     0 00000296 3C0A                                    cmp al,10
     0 00000298 7412                                    jz end_of_line
     0 0000029A 3C39                                    cmp al,'9'
     0 0000029C 7713                                    ja show_usage
     0 0000029E 2C30                                    sub al,'0'
     0 000002A0 720F                                    jb show_usage
     0 000002A2 666BDB0A                                imul ebx,10
     0 000002A6 6601C3                                  add ebx,eax
     0 000002A9 AC                                      lodsb
     0 000002AA E2E6                                    loop nextdigit
   255                                  end_of_line:
     0 000002AC 6609DB                                  or ebx,ebx
     0 000002AF 7505                                    jnz doit
   258                                  show_usage:
     0 000002B1 BA[A600]                                mov dx,offset usage_txt
     0 000002B4 F9                                      stc
     0 000002B5 C3                                      ret
   262                                  doit:
     0 000002B6 6653                                    push ebx
     0 000002B8 B80943                                  mov ax,4309h            ; get handle table pointer
     0 000002BB CD2F                                    int 2Fh
     0 000002BD 3C43                                    cmp al,43h
     0 000002BF 7523                                    jnz noXMS_error
     0 000002C1 268A5701                                mov dl,[es:bx+1]
     0 000002C5 30F6                                    xor dh,dh               ; dx is the structure size
     0 000002C7 268B4F02                                mov cx,[es:bx+2]        ; cx is the table size
     0 000002CB E317                                    jcxz noXMS_error
     0 000002CD 26C55F04                                lds bx,[es:bx+4]        ; ds:bx points to structure table
     0 000002D1 6631F6                                  xor esi,esi     ; esi found top of memory
     0 000002D4 31FF                                    xor di,di       ; di best top of memory handle
   275                                  checkhandle:
     0 000002D6 8A07                                    mov al,[bx]    ; 1 = free, 2 = used, 4 = ignored
     0 000002D8 3C04                                    cmp al,4
     0 000002DA 7421                                    jz nexthandle
     0 000002DC 3C01                                    cmp al,1
     0 000002DE 740B                                    jz goodhandle
     0 000002E0 3C02                                    cmp al,2
     0 000002E2 7407                                    jz goodhandle
   283                                  noXMS_error:
     0 000002E4 665B                                    pop ebx
     0 000002E6 BA[2701]                                mov dx,offset noXMS_txt
   286                                  error_ret:
     0 000002E9 F9                                      stc
     0 000002EA C3                                      ret
   289                                  
     0 000002EB 668B4702                goodhandle:     mov eax,[bx+2]
     0 000002EF 66034706                                add eax,[bx+6]         ; eax is now the top of the block
     0 000002F3 6639F0                                  cmp eax,esi
     0 000002F6 7205                                    jb nexthandle
     0 000002F8 89DF                                    mov di,bx
     0 000002FA 6689C6                                  mov esi,eax
     0 000002FD 01D3                    nexthandle:     add bx,dx
     0 000002FF E2D5                                    loop checkhandle
   298                                  
     0 00000301 6658                                    pop eax
     0 00000303 BA[4E01]                                mov dx,offset lastUsed_txt
     0 00000306 833D01                                  cmp word ptr [di],1
     0 00000309 75DE                                    jne error_ret
   303                                  
     0 0000030B BA[9201]                                mov dx,offset tooLittle_txt
     0 0000030E 662B4502                                sub eax,[di+2]
     0 00000312 76D5                                    jbe error_ret
     0 00000314 66894506                                mov [di+6],eax
     0 00000318 BA[B701]                                mov dx,offset done_txt
     0 0000031B F8                                      clc
     0 0000031C C3                                      ret
   311                                  cpu 186
   312                                  cmdline endp
   313                                  ; (no prior section) ; _TEXT ENDS
   314                                  
=== Switch to base=000320h -> "_STACK"
   315                                  section _STACK stack class=CODE
   316 00000000 <res C8h>                               db 200 dup (?)
   317                                  ; (no prior section) ; _STACK ENDS
   318                                                  end main
