1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475
|
;**************************************************************************
;*
;* FLASH - Program FlashCard flash EPROM
;*
;* Module: flash.asm
;* Purpose: Program FlashCard flash EPROM
;* Entries: start
;*
;**************************************************************************
;*
;* Copyright (C) 1995-1998 Gero Kuhlmann <gero@gkminix.han.de>
;*
;* This program is free software; you can redistribute it and/or modify
;* it under the terms of the GNU General Public License as published by
;* the Free Software Foundation; either version 2 of the License, or
;* any later version.
;*
;* This program is distributed in the hope that it will be useful,
;* but WITHOUT ANY WARRANTY; without even the implied warranty of
;* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
;* GNU General Public License for more details.
;*
;* You should have received a copy of the GNU General Public License
;* along with this program; if not, write to the Free Software
;* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
;*
;**************************************************************************
;*
;
;**************************************************************************
;
; The purpose of this program is to program the flash EPROM on the FlashCard
; ISA card. The flash EPROM has to be an AMD 29F010, and the programming
; algorithm is the same as that suggested by AMD in the appropriate data
; sheets.
;
.model small,pascal
.stack 256 ; 256 stack bytes should be sufficient
;
;**************************************************************************
;
; Miscellaneous defines:
;
CMDLINE equ 00080h ; offset of command line into PSP
BUFSIZE equ 512 ; size of read buffer
FNAMSIZE equ 64 ; maximum size of filename
SEGLOW equ 0C800h ; lower range for EPROM segment
SEGHIGH equ 0E800h ; upper range for EPROM segment
SEGMASK equ 0FE00h ; mask for 8kB boundary
AMD_ID equ 2001h ; flash EPROM ID, only support AMD
ERASE1_CMD equ 080h ; first command for erasing full chip
ERASE2_CMD equ 010h ; second command for erasing full chip
READID_CMD equ 090h ; command to read chip ID
PROG_CMD equ 0A0h ; command to program a byte
RESET_CMD equ 0F0h ; command to reset chip state machine
;
;**************************************************************************
;
; Constant segment:
;
.const
cpymsg db 'flash - Flash EPROM programming utility',0Dh,0Ah
db 'Copyright (C) G. Kuhlmann, 1996',0Dh,0Ah
db 0Dh,0Ah,'$'
segerr db 'Illegal segment '
db '(must be between C800 and E800 on 8kB boundary)'
db 0Dh,0Ah,'$'
useerr db 'usage: flash <seg-addr> <file name>'
db 0Dh,0Ah,'$'
filerr db 'Cannot open input file'
db 0Dh,0Ah,'$'
rderr db 'Cannot read from input file'
db 0Dh,0Ah,'$'
iderr db 'Invalid manufacturer ID or no Flash-EPROM installed'
db 0Dh,0Ah,'$'
prgerr db 'Timeout while programming or erasing Flash-EPROM'
db 0Dh,0Ah,'$'
prgmsg db 'Programming... $'
endmsg db 'finished'
db 0Dh,0Ah,'$'
;
;**************************************************************************
;
; Data segment:
;
.data
fseg dw 0D000h ; flash EPROM segment
handle dw 0 ; data file handle
filename db FNAMSIZE dup (0) ; file name buffer
buf db BUFSIZE dup (0) ; read buffer
;
;**************************************************************************
;
; Program start
;
.code
assume cs:_text
assume ds:nothing
assume es:nothing
start: mov ax,@data
mov es,ax
assume es:dgroup
; First analyze the command line. The only arguments for this program
; are the EPROM segment address in hex and the data file name.
mov si,CMDLINE + 1
call skipblank
cmp al,0Dh
je short start5
call gethex ; get hex number
cmp bx,SEGLOW ; should be in the range of C800h
jb short start2 ; and E800h
cmp bx,SEGHIGH
ja short start2
test bx,not SEGMASK ; segment has to be on 8kB boundary
jz short start4
start2: mov dx,offset segerr
start3: mov ax,@data
mov ds,ax
start1: mov ah,09h ; print error message
int 21h
jmp doend
start4: mov es:fseg,bx ; save EPROM segment address
call skipblank
cmp al,0Dh
je short start5
call copyfnam ; copy filename
call skipblank ; nothing should follow anymore
cmp al,0Dh
je short start6
start5: mov dx,offset useerr ; print usage message
jmp short start3
; We now analyzed the whole command line, so the PSP segment in DS is
; no longer needed. Setup all segment registers correctly, and then try
; to open the data file.
start6: mov ax,@data
mov ds,ax ; set segment registers
mov es,ax
assume ds:dgroup
assume es:dgroup
mov dx,offset cpymsg ; print copyright
mov ah,09h
int 21h
mov ax,3D00h
mov dx,offset filename ; open the data file
int 21h
mov dx,offset filerr
jc short error ; print error message if unsuccessful
mov handle,ax ; save file handle
; Read the flash EPROM ID to check if there really is an AMD flash EPROM
; where the user says it should be. Then erase the whole chip to allow
; programming lateron.
call readid ; read manufacturer ID from chip
mov dx,offset iderr
cmp bx,AMD_ID ; check for AMD
jne short error
call erase
mov dx,offset prgerr ; erase the whole chip
jc short error
; Now read every block from the data file and program it into the flash
; EPROM. Verification of the programmed data is not necessary, as the
; flash EPROM will do that by itself. It will return an unsuccessful
; programming cycle if it's internal verification showed an error.
mov dx,offset prgmsg
mov ah,09h ; print programming message
int 21h
xor bx,bx
start7: push bx
mov ax,3F00h
mov bx,handle
mov cx,BUFSIZE ; read next block from data file
mov dx,offset buf
int 21h
pop bx
mov dx,offset rderr ; check for read error
jc short error
or ax,ax ; check for end of file
jz short start8
mov cx,ax
call program ; program the data block into the
mov dx,offset prgerr ; flash EPROM and check for a pro-
jnc short start7 ; gramming error
error: jmp start1
start8: mov dx,offset endmsg
mov ah,09h ; print end-of-programming message
int 21h
doend: mov ax,4C01h ; terminate program
int 21h
ret
;
;**************************************************************************
;
; Skip blanks on command line.
; Input: DS:SI - pointer to command line
; Output: DS:SI - pointer to first non-blank
; AL - first non-blank character
; Registers changed: AX, SI
;
skipblank proc near
cld
skip1: lodsb
cmp al,' ' ; skip blanks
je short skip1
cmp al,09h ; skip tabs
je short skip1
dec si ; point SI to first non-blank
ret
skipblank endp
;
;**************************************************************************
;
; Return hex number from string pointed to by DS:SI.
; Input: DS:SI - pointer to string
; Output: DS:SI - pointer to first character after hex number
; BX - hex number
; Registers changed: AX, BX, CX, SI
;
gethex proc near
xor bx,bx
geth1: lodsb
cmp al,'0'
jb short geth9 ; check for valid hex digit
cmp al,'9'
jbe short geth3
cmp al,'A'
jb short geth9
cmp al,'a'
jb short geth2
sub al,20h ; convert character to upper case
geth2: cmp al,'F'
ja short geth9
sub al,7
geth3: sub al,'0' ; convert character to digit
and al,0Fh
mov cl,4
shl bx,cl ; include digit into result
or bl,al
jmp short geth1 ; get next character
geth9: dec si ; point SI to last non-digit
ret
gethex endp
;
;**************************************************************************
;
; Copy filename from command line into buffer
; Input: DS:SI - pointer to string
; Output: DS:SI - pointer to first character after filename
; Registers changed: AX, CX, SI, DI
;
copyfnam proc near
push es
mov ax,@data
mov es,ax
mov cx,FNAMSIZE - 1 ; don't copy past filename buffer
mov di,offset filename ; put address to filename buffer
cld ; into ES:DI
copyf1: lodsb
or al,al
jz short copyf9 ; check for valid filename character
cmp al,' '
jbe short copyf9
cmp al,7Fh
jae short copyf9
stosb ; copy character
loop short copyf1
copyf9: xor al,al
stosb ; copy terminating null
dec si
pop es
ret
copyfnam endp
;
;**************************************************************************
;
; Read manufacturer ID from Flash-EPROM
; Input: none
; Output: BX - manufacturer ID
; Registers changed: AX, BX
;
readid proc near
mov al,READID_CMD
call sendop ; send READID command
push es
mov es,fseg
mov bx,es:[0000h] ; read manufacturer ID
pop es
mov al,RESET_CMD
call sendop ; reset chip
ret
readid endp
;
;**************************************************************************
;
; Erase whole chip
; Input: none
; Output: carry flag set if error
; Registers changed: AX, BX
;
erase proc near
mov al,ERASE1_CMD
call sendop ; send ERASE1 command
mov al,ERASE2_CMD
call sendop ; send ERASE2 command
xor bx,bx
mov al,0FFh
call waitop ; wait until operation finished
jnc short erase9
mov al,RESET_CMD
call sendop ; reset chip
stc
erase9: ret
erase endp
;
;**************************************************************************
;
; Program Flash-EPROM with contents in read buffer
; Input: BX - offset to next byte to program
; CX - number of bytes to program
; Output: BX - offset to byte after last programmed byte
; carry flag set if error
; Registers changed: AX, BX, CX, SI
;
program proc near
mov si,offset buf
prog1: mov al,PROG_CMD
call sendop ; send programming command
lodsb ; get next byte from buffer
push es
mov es,fseg
mov es:[bx],al ; write next byte into flash EPROM
pop es
call waitop ; wait until programming operation is
jc short prog9 ; completed
inc bx
loop prog1 ; continue with next byte
clc ; return without error
prog9: ret
program endp
;
;**************************************************************************
;
; Send OP code to Flash_EPROM. This involves writing three bytes into the
; flash EPROM at exactly specified locations. See AMD data sheets for
; further information.
; Input: AL - command byte
; Output: none
; Registers changed: none
;
sendop proc near
push es
mov es,fseg
mov byte ptr es:[5555h],0AAh
jcxz @F
@@: jcxz @F
@@: mov byte ptr es:[2AAAh],055h
jcxz @F
@@: jcxz @F
@@: mov byte ptr es:[5555h],al
pop es
ret
sendop endp
;
;**************************************************************************
;
; Wait for the chip to process programming/erase. When programming is in
; progress, the flash EPROM toggles the highest bit, and converts it back
; to it's original value when the programming is done. For a further ex-
; planation of this algorithm see the AMD data sheets.
; Input: AL - programmed byte
; BX - offset to programming location
; Output: carry flag set if error
; Registers changed: AX
;
waitop proc near
push cx
and al,10000000b
push es
mov es,fseg
wait1: mov ah,es:[bx]
mov ch,ah
and ah,10000000b
cmp al,ah
je short wait8
test ch,00100000b
jz short wait1
mov ah,es:[bx]
and ah,10000000b
cmp al,ah
je short wait8
stc
jmp short wait9
wait8: clc
wait9: pop es
pop cx
ret
waitop endp
;
;**************************************************************************
;
end start
|