diff options
Diffstat (limited to 'v4.0/src/CMD/CHKDSK/CHKFAT.ASM')
| -rw-r--r-- | v4.0/src/CMD/CHKDSK/CHKFAT.ASM | 1064 |
1 files changed, 1064 insertions, 0 deletions
diff --git a/v4.0/src/CMD/CHKDSK/CHKFAT.ASM b/v4.0/src/CMD/CHKDSK/CHKFAT.ASM new file mode 100644 index 0000000..badd48c --- /dev/null +++ b/v4.0/src/CMD/CHKDSK/CHKFAT.ASM | |||
| @@ -0,0 +1,1064 @@ | |||
| 1 | TITLE CHKFAT - procedures that acces the fat and/or fatmap | ||
| 2 | page ,132 ; | ||
| 3 | |||
| 4 | .xlist | ||
| 5 | include chkseg.inc ;an005;bgb | ||
| 6 | INCLUDE CHKCHNG.inc | ||
| 7 | INCLUDE DOSSYM.inc | ||
| 8 | INCLUDE CHKEQU.inc | ||
| 9 | INCLUDE CHKMACRO.inc | ||
| 10 | include pathmac.inc | ||
| 11 | |||
| 12 | |||
| 13 | CONST SEGMENT PUBLIC PARA 'DATA' | ||
| 14 | EXTRN CREATMES:byte,FIXMES_ARG:word | ||
| 15 | EXTRN FREEMES:byte | ||
| 16 | EXTRN BADW_ARG:word,FATAL_END:word | ||
| 17 | EXTRN badrw_num:word,BADRW_STR:WORD,HAVFIX:byte | ||
| 18 | EXTRN FREEBYMES1:byte,FREEBYMES2:byte | ||
| 19 | EXTRN FREE_ARG1:WORD,FREE_ARG2:WORD,FREE_ARG3:WORD,ORPHCNT:dword | ||
| 20 | EXTRN DIRTYFAT:byte,CROSSCNT:dword,DOFIX:byte,SECONDPASS:byte | ||
| 21 | EXTRN BADSIZ:word,ORPHSIZ:word,LCLUS:word,ORPHFCB:byte | ||
| 22 | EXTRN HECODE:byte,USERDIR:byte,FRAGMENT:byte | ||
| 23 | EXTRN ORPHEXT:byte,ALLDRV:byte,FIXMFLG:byte,DIRCHAR:byte | ||
| 24 | EXTRN BIGFAT:byte,EOFVAL:word,BADVAL:word | ||
| 25 | extrn fTrunc:BYTE, rarg1:word ;an018;bgb | ||
| 26 | extrn temp_dd:dword ;an049;bgb | ||
| 27 | CONST ENDS | ||
| 28 | |||
| 29 | DATA SEGMENT PUBLIC PARA 'DATA' | ||
| 30 | extrn fatcnt:byte ;an005;bgb | ||
| 31 | EXTRN THISDPB:dword,NUL_ARG:byte | ||
| 32 | EXTRN NAMBUF:byte,SRFCBPT:word,FATMAP:word | ||
| 33 | EXTRN MCLUS:word,CSIZE:byte,SSIZE:word | ||
| 34 | EXTRN DSIZE:word,ARG1:word,ARG_BUF:byte,ERRCNT:byte | ||
| 35 | EXTRN USERDEV:byte,HARDCH:dword,CONTCH:dword | ||
| 36 | EXTRN ExitStatus:Byte,Read_Write_Relative:Byte | ||
| 37 | extrn bytes_per_sector:word, fattbl:word ;an005;bgb | ||
| 38 | extrn sec_count:word, secs_per_64k:word, paras_per_64k:word ;an005;bgb | ||
| 39 | extrn fattbl_seg:word, fatsiz:word, paras_per_fat:word ;an005;bgb | ||
| 40 | extrn end_of_fatmap:word ;an030;bgb | ||
| 41 | extrn root_entries:word ;ac048;bgb;an047;bgb | ||
| 42 | DATA ENDS | ||
| 43 | |||
| 44 | CODE SEGMENT PUBLIC PARA 'CODE' | ||
| 45 | ASSUME CS:DG,DS:DG,ES:DG,SS:DG | ||
| 46 | EXTRN PRINTF_CRLF:NEAR,FCB_TO_ASCZ:NEAR, recover:near | ||
| 47 | EXTRN EPRINT:NEAR, makorphnam:near | ||
| 48 | EXTRN DOINT26:NEAR,PROMPTYN:NEAR,CHECKFILES:NEAR,DIRPROC:NEAR | ||
| 49 | EXTRN DOCRLF:NEAR, getfilsiz:near, fatal:near, write_disk:near | ||
| 50 | EXTRN GETENT:NEAR,CHECKNOFMES:NEAR, systime:near | ||
| 51 | EXTRN multiply_32_bits:near ;an049;bgb | ||
| 52 | |||
| 53 | public calc_fatmap_seg, MARKMAP, CHKMAP, CHKMAPLP, ORPHAN, CONTLP, RET18 | ||
| 54 | public PromptRecover, NOCHAINREC, CHKMAPLP2, NEXTCLUS | ||
| 55 | public DISPFRB, FINDCHAIN, CHKMAPLP3, CHAINLP, INSERTEOF, FAT12_4, CHKCHHEAD | ||
| 56 | public ADDCHAIN, CHGOON, NEXTCLUS2, | ||
| 57 | public CHAINREC, MAKFILLP, GOTENT, OPAGAIN, GOTORPHNAM, ENTMADE, NEXTENT | ||
| 58 | public NXTORP, RET100, nextorph | ||
| 59 | public AMDONE, REWRITE, WRTLOOP | ||
| 60 | public WRTOK, NOWRITE, DONE, CROSSCHK, calc_fat_addr, pack, unpack | ||
| 61 | .list | ||
| 62 | PHONEY_STACK DW 5 DUP(0) ;ac048;bgb | ||
| 63 | |||
| 64 | pathlabl chkfat | ||
| 65 | ;***************************************************************************** ;an005;bgb | ||
| 66 | ; CALC-FAT-ADDR - calculate the seg/off of the fat cell from the cell number ;an005;bgb | ||
| 67 | ; ;an005;bgb | ||
| 68 | ; Inputs: es - fat table segment | ||
| 69 | ; si - cluster number | ||
| 70 | ; | ||
| 71 | ; Outputs: es - fat table segment + cluster seg | ||
| 72 | ; di - cluster offset | ||
| 73 | ; ;an005;bgb | ||
| 74 | ; LARGE FAT SUPPORT ;an005;bgb | ||
| 75 | ;******************* ;an005;bgb | ||
| 76 | ; the offset into the fat table is cluster number times 2 (2 bytes per fat entry) ;an005;bgb | ||
| 77 | ; This will result not only in the segment boundary being passed, but also in ;an005;bgb | ||
| 78 | ; a single-word math overflow. So, we calculate the the address as follows: ;an005;bgb | ||
| 79 | ; 0. start with cluster number (1-65535) ;an005;bgb | ||
| 80 | ; 1. divide by 8 to get the number of paragraphs per fat-cell (0-8191) ;an005;bgb | ||
| 81 | ; remainder = (0-7) ;an005;bgb | ||
| 82 | ; 2. multiply the remainder by 2 to get offset in bytes (0-15) ;an005;bgb | ||
| 83 | ; You now have a paragraph-offset number that you can use to calc the addr into ;an005;bgb | ||
| 84 | ; the fat table. To get the physical addr you must add it to the offset of the ;an005;bgb | ||
| 85 | ; table in memory. ;an005;bgb | ||
| 86 | ; 3. add the paras to the segment register ;an005;bgb | ||
| 87 | ; 4. add the offset to the offset register ;an005;bgb | ||
| 88 | ;****************************************************************************** ;an005;bgb | ||
| 89 | Procedure calc_fat_addr,near ;an005;bgb | ||
| 90 | savereg <ax,bx,dx> ; ;an005;bgb | ||
| 91 | mov ax,si ;get cluster number from si | ||
| 92 | mov bx,0008h ; div by para (* 2 bytes per clus) ;an005;bgb | ||
| 93 | xor dx,dx ; zero dx for word divide ;an005;bgb | ||
| 94 | div bx ; do it ;an022;bgb;bgb | ||
| 95 | mov bx,es ; get fat table segment ;an005;bgb | ||
| 96 | add bx,ax ; add number of paras to the cluster ;an005;bgb | ||
| 97 | mov es,bx ; move it back ;an005;bgb | ||
| 98 | shl dx,1 ; remainder times 2 ;an005;bgb | ||
| 99 | mov di,dx ; offset = 00 + remainder ;an005;bgb | ||
| 100 | restorereg <dx,bx,ax> ;an005;bgb | ||
| 101 | return ;an005;bgb | ||
| 102 | EndProc calc_fat_addr ;an005;bgb | ||
| 103 | |||
| 104 | ;========================================================================= | ||
| 105 | ; UNPACK : This routine calculates the position in the FAT | ||
| 106 | ; where the cluster number resides and obtains | ||
| 107 | ; its contents. | ||
| 108 | ; | ||
| 109 | ; Inputs : SI - Cluster number | ||
| 110 | ; Outputs : DI - Cluster contents | ||
| 111 | ; zero flag is set if fat cell = zero | ||
| 112 | ; | ||
| 113 | ; LOGIC | ||
| 114 | ; - get addr of fat table | ||
| 115 | ; - if 16-bit fat, | ||
| 116 | ; then get the address of the cell (calc_fat_addr) | ||
| 117 | ; mov it into di | ||
| 118 | ; set the zero flag | ||
| 119 | ; else multiply the cluster-number by 1.5 to get the byte-offset | ||
| 120 | ; move the contents of the cluster into di | ||
| 121 | ; if the cluster-number is odd, | ||
| 122 | ; then shift it right by 1 nibble | ||
| 123 | ; set the zero flag | ||
| 124 | ; else (its already shifted right) | ||
| 125 | ; set the zero flag | ||
| 126 | ;========================================================================= | ||
| 127 | UNPACK proc near ;ac005; dms;unpack FAT | ||
| 128 | push es ;an005;bgb | ||
| 129 | mov es,fattbl_seg ;point to FAT in memory ;an005;bgb | ||
| 130 | mov DI,SI ;put cluster number in DI | ||
| 131 | cmp [BIGFAT],0 ;big fat? | ||
| 132 | ; $IF nz ;yes | ||
| 133 | JZ $$IF1 | ||
| 134 | call calc_fat_addr ;calc addr of cluster ;an005;bgb | ||
| 135 | mov di,word ptr es:[di] ;es:bx points to fat cluster ;an005;bgb | ||
| 136 | or DI,DI ; Set zero | ||
| 137 | ; $ELSE ;small fat | ||
| 138 | JMP SHORT $$EN1 | ||
| 139 | $$IF1: | ||
| 140 | SHR DI,1 | ||
| 141 | ADD DI,SI ; Mult by 1.5 | ||
| 142 | mov DI,word ptr es:[di] | ||
| 143 | TEST SI,1 ;is the cluster number odd? | ||
| 144 | ; $IF nz ;last bit is non-zero; means it is odd | ||
| 145 | JZ $$IF3 | ||
| 146 | SHR DI,1 ;shift by 1 nibble | ||
| 147 | SHR DI,1 | ||
| 148 | SHR DI,1 | ||
| 149 | SHR DI,1 | ||
| 150 | and di,0fffh ;ac005; dms; | ||
| 151 | ; $ELSE ;ac005; dms;even cluster bound. | ||
| 152 | JMP SHORT $$EN3 | ||
| 153 | $$IF3: | ||
| 154 | AND DI,0FFFH | ||
| 155 | ; $ENDIF | ||
| 156 | $$EN3: | ||
| 157 | ; $ENDIF | ||
| 158 | $$EN1: | ||
| 159 | pop es | ||
| 160 | return | ||
| 161 | UNPACK endp ;ac005; dms; | ||
| 162 | |||
| 163 | ;========================================================================= | ||
| 164 | ; PACK : This routine puts data into the FAT. | ||
| 165 | ; | ||
| 166 | ; Inputs : SI - Cluster number to be packed | ||
| 167 | ; dx - Data to be packed | ||
| 168 | ; | ||
| 169 | ; Outputs : Altered FAT | ||
| 170 | ; LOGIC | ||
| 171 | ; - set the fat-changed-flags | ||
| 172 | ; - get the seg of the fat-table | ||
| 173 | ; - if 16-bit fat, | ||
| 174 | ; then get the address of the cell (calc_fat_addr) | ||
| 175 | ; mov the new value into it | ||
| 176 | ; else multiply the cluster-number by 1.5 to get the byte-offset | ||
| 177 | ; move the contents of the cluster into di | ||
| 178 | ; if the cluster-number is odd, | ||
| 179 | ; then shift it right by 1 nibble | ||
| 180 | ; set the zero flag | ||
| 181 | ; else (its already shifted right) | ||
| 182 | ; set the zero flag | ||
| 183 | ;========================================================================= | ||
| 184 | PACK proc near ;ac005; dms; | ||
| 185 | savereg <si,di,es> ;ac048;bgb | ||
| 186 | mov [DIRTYFAT],1 ;Set FAT dirty byte | ||
| 187 | mov [HAVFIX],1 ;Indicate a fix | ||
| 188 | mov es,fattbl_seg ; ;an005;bgb | ||
| 189 | mov DI,SI | ||
| 190 | cmp [BIGFAT],0 | ||
| 191 | ; $IF nz ;ac005; dms;big fat? | ||
| 192 | JZ $$IF7 | ||
| 193 | call calc_fat_addr ;calc addr of cluster ;an005;bgb | ||
| 194 | mov es:[di],dx ;move dx into cluster ;an005;bgb | ||
| 195 | ; $ELSE | ||
| 196 | JMP SHORT $$EN7 | ||
| 197 | $$IF7: | ||
| 198 | shr di,1 ;offset = clus-num * 1.5 | ||
| 199 | add di,si ;offset = clus-num * 1.5 | ||
| 200 | push di ;save cluster offset | ||
| 201 | mov DI,es:[di] ;get previous value, 4 nibbles | ||
| 202 | test si,1 ;is the cluster number odd? | ||
| 203 | ; $IF nz ;last bit is non-zero; means it is odd | ||
| 204 | JZ $$IF9 | ||
| 205 | SHL dx,1 ;shift by 1 nibble | ||
| 206 | SHL dx,1 | ||
| 207 | SHL dx,1 | ||
| 208 | SHL dx,1 | ||
| 209 | AND DI,0FH ;zero out 1st 3 nibbles '000f' | ||
| 210 | ; $ELSE ;even cluster number | ||
| 211 | JMP SHORT $$EN9 | ||
| 212 | $$IF9: | ||
| 213 | AND DI,0F000H ;zero out last 3 nibbles 'f000' | ||
| 214 | ; $ENDIF | ||
| 215 | $$EN9: | ||
| 216 | or DI,dx ;put new value in with old | ||
| 217 | pop si ;get cluster offset | ||
| 218 | mov es:[SI],DI | ||
| 219 | ; $ENDIF | ||
| 220 | $$EN7: | ||
| 221 | restorereg <es,di,si> ;ac048;bgb | ||
| 222 | ret | ||
| 223 | PACK endp ;ac005; dms; | ||
| 224 | |||
| 225 | ;========================================================================= ;an005;bgb | ||
| 226 | ; CROSSCHK : this proc gets the value of the fatmap entry that is pointed ;an005;bgb | ||
| 227 | ; to by an orphan ;an005;bgb | ||
| 228 | ; ;an005;bgb | ||
| 229 | ; Inputs : si - cluster number of the orphan ;an005;bgb | ||
| 230 | ; ;an005;bgb | ||
| 231 | ; Outputs : ah - contents of the fatmap pointed to by di ;an005;bgb | ||
| 232 | ; LOGIC ;an005;bgb | ||
| 233 | ; ***** ;an005;bgb | ||
| 234 | ;========================================================================= ;an005;bgb | ||
| 235 | procedure CROSSCHK ;an005;bgb | ||
| 236 | push es | ||
| 237 | mov es,fatmap ;an005;bgb | ||
| 238 | xor di,di ;an005;bgb | ||
| 239 | ADD DI,SI | ||
| 240 | mov ah,es:[di] ;an005;bgb | ||
| 241 | TEST AH,10H | ||
| 242 | pop es | ||
| 243 | ret | ||
| 244 | EndProc CROSSCHK ;an005;bgb | ||
| 245 | |||
| 246 | ;***************************************************************************** ;an005;bgb | ||
| 247 | ; INIT_FATMAP ;an005;bgb | ||
| 248 | ; description: initialize the fatmap area to all zeros ;an005;bgb | ||
| 249 | ; ;an005;bgb | ||
| 250 | ; called from: main-routine ;an005;bgb | ||
| 251 | ; ;an005;bgb | ||
| 252 | ;Change History: Created 8/31/87 bgb ;an005;bgb | ||
| 253 | ; ;an005;bgb | ||
| 254 | ;Input: segment addr of the fatmap ;an005;bgb | ||
| 255 | ; number of clusters in the fat (1-65535) ;an005;bgb | ||
| 256 | ; ;an005;bgb | ||
| 257 | ;Output: fatmap ;an005;bgb | ||
| 258 | ; ;an005;bgb | ||
| 259 | ; LOGIC ;an005;bgb | ||
| 260 | ;---------- ;an005;bgb | ||
| 261 | ;***************************************************************************** ;an005;bgb | ||
| 262 | Procedure init_fatmap,Near ;AN000;bgb ;an005;bgb | ||
| 263 | savereg <es,di,ax,cx> | ||
| 264 | mov es,fatmap ;get seg of the fatmap ;an005;bgb | ||
| 265 | xor di,di ;get off of the fatmap ;an005;bgb | ||
| 266 | mov cx,[MCLUS] ;do once for each cluster | ||
| 267 | xor AL,AL ;zero means free | ||
| 268 | REP STOSB ;Initialize fatmap to all free | ||
| 269 | mov byte ptr es:[di],al ; ;an010;bgb | ||
| 270 | restorereg <cx,ax,di,es> | ||
| 271 | return | ||
| 272 | endproc init_fatmap ; ;AN000; | ||
| 273 | ; | ||
| 274 | ;***************************************************************************** ;an005;bgb | ||
| 275 | ; CALC_FATMAP_SEG ;an005;bgb | ||
| 276 | ; description: calculate the segment of the fatmap for addressing purposes ;an005;bgb | ||
| 277 | ; ;an005;bgb | ||
| 278 | ; called from: main-routine ;an005;bgb | ||
| 279 | ; ;an005;bgb | ||
| 280 | ;Change History: Created 8/31/87 bgb ;an005;bgb | ||
| 281 | ; ;an005;bgb | ||
| 282 | ;Input: bytes-per-sector ;an005;bgb | ||
| 283 | ; fatsiz ;an005;bgb | ||
| 284 | ; ;an005;bgb | ||
| 285 | ;Output: ram-based fat table ;an005;bgb | ||
| 286 | ; paras-per-fat - number of paragraphs of mem in the fat | ||
| 287 | ; fattbl-seg - segment number of fat table | ||
| 288 | ; fatmap - segment number of the fat map table | ||
| 289 | ; ;an005;bgb | ||
| 290 | ; LOGIC ;an005;bgb | ||
| 291 | ;---------- ;an005;bgb | ||
| 292 | ; - calc length fat-table (in paras) ;an005;bgb | ||
| 293 | ; = bytes-per-sector / 16 * sectors-per-fat ;an005;bgb | ||
| 294 | ; - calc segment of fat table in memory ;an005;bgb | ||
| 295 | ; = es + 64k ;an005;bgb | ||
| 296 | ; - calc segment of fatmap area in memory ;an005;bgb | ||
| 297 | ; = es + 64k + length of fat-table ;an005;bgb | ||
| 298 | ;***************************************************************************** ;an005;bgb | ||
| 299 | Procedure calc_fatmap_seg,Near ;AN000;bgb ;an005;bgb | ||
| 300 | ; calc fat table length ;an005;bgb | ||
| 301 | push es | ||
| 302 | mov ax,bytes_per_sector ; bytes per sector ;an005;bgb | ||
| 303 | xor dx,dx ;an005;bgb | ||
| 304 | mov bx,16 ;an005;bgb | ||
| 305 | div bx ; paras per sector ;an022;bgb;bgb | ||
| 306 | mov cx,fatsiz ;2 ; get sectors per fat ;an005;bgb | ||
| 307 | xor dx,dx ;an005;bgb | ||
| 308 | mul cx ; paras per fat ;an005;bgb | ||
| 309 | mov paras_per_fat,ax ;an005;bgb | ||
| 310 | ; calc fat table segment ;an005;bgb | ||
| 311 | mov bx,es ;get seg of fat-table ;an005;bgb | ||
| 312 | add bx,01000h ;add 64k for end of pgm seg ;an005;bgb | ||
| 313 | mov fattbl_seg,bx ;starting segment of fattbl ;an005;bgb | ||
| 314 | ; calc fatmap segment :an005;bgb | ||
| 315 | add ax,bx ;seg of fatmap= seg of fattbl + size of fattbl ;an005;bgb | ||
| 316 | mov fatmap,ax ;this is the seg of the fatmap ;an005;bgb | ||
| 317 | ; find segment number of end of fatmap ;an030;bgb | ||
| 318 | ;ptm p5000 mov bx,paras_per_fat ;each fat cell is 2 bytes ;an030;bgb | ||
| 319 | ;ptm p5000 shr bx,1 ;each fatmap cell is 1 byte = ;an030;bgb | ||
| 320 | mov bx, [MCLUS] ;P5000 INIT_FATMAP use [MCLUS] | ||
| 321 | shr bx, 1 ;P5000 convert it to para. | ||
| 322 | shr bx, 1 ;P5000 | ||
| 323 | shr bx, 1 ;P5000 | ||
| 324 | shr bx, 1 ;P5000 | ||
| 325 | add ax,bx ;add in fatmap seg = ;an030;bgb | ||
| 326 | inc ax ;P5000 | ||
| 327 | mov end_of_fatmap,ax ;last seg value ;an030;bgb | ||
| 328 | pop es | ||
| 329 | ret ; ;AN000; | ||
| 330 | endproc calc_fatmap_seg ; ;AN000; | ||
| 331 | ; | ||
| 332 | ;ac048;bgb | ||
| 333 | ;***************************************************************************** ;ac048;bgb | ||
| 334 | ; FIX_ENTRY - fill in the dir entry with the lost cluster information, give it ;ac048;bgb | ||
| 335 | ; unique filename, and write it back to disk. ;ac048;bgb | ||
| 336 | ; ;ac048;bgb | ||
| 337 | ; WARNING!! NOTE!! --> ;ac048;bgb | ||
| 338 | ; ;ac048;bgb | ||
| 339 | ; called by - CHAINREC ;ac048;bgb | ||
| 340 | ; ;ac048;bgb | ||
| 341 | ; inputs: AX - drive number ;ac048;bgb | ||
| 342 | ; BX - ram offset of beginning of sector ;ac048;bgb | ||
| 343 | ; CX - ;ac048;bgb | ||
| 344 | ; DX - sector number low ;ac048;bgb | ||
| 345 | ; SP - ;ac048;bgb | ||
| 346 | ; BP - ;ac048;bgb | ||
| 347 | ; SI - cluster number of first cluster in this lost chain ;ac048;bgb | ||
| 348 | ; DI - points to entry in ram ;ac048;bgb | ||
| 349 | ; ;ac048;bgb | ||
| 350 | ; output: AX - ;ac048;bgb | ||
| 351 | ; BX - ;ac048;bgb | ||
| 352 | ; CX - ;ac048;bgb | ||
| 353 | ; DX - ;ac048;bgb | ||
| 354 | ; SP - ;ac048;bgb | ||
| 355 | ; BP - ;ac048;bgb | ||
| 356 | ; SI - ;ac048;bgb | ||
| 357 | ; DI- ;ac048;bgb | ||
| 358 | ; ;ac048;bgb | ||
| 359 | ; Regs abused - di,si,cx ;ac048;bgb | ||
| 360 | ; ;ac048;bgb | ||
| 361 | ;logic: 1. save the starting cluster number ;ac048;bgb | ||
| 362 | ; ;ac048;bgb | ||
| 363 | ; 2. if the recovered file name already exists, then use the next one. ;ac048;bgb | ||
| 364 | ; do this until the name is unique. ;ac048;bgb | ||
| 365 | ; ;ac048;bgb | ||
| 366 | ; 3. move all the pertinant info into the dir entry. ;ac048;bgb | ||
| 367 | ; ;ac048;bgb | ||
| 368 | ; 4. write the dir entry out to disk. ;ac048;bgb | ||
| 369 | ;***************************************************************************** ;ac048;bgb | ||
| 370 | procedure fix_entry,near ;ac048;bgb | ||
| 371 | mov ds:[DI+26],SI ;move 1st clus num into dir entry ;ac048;bgb ;an005;bgb | ||
| 372 | savereg <ax,dx,bx> ;Save INT 26 data ;ac048;bgb | ||
| 373 | ;make sure this name is unique ;ac048;bgb | ||
| 374 | DOS_Call Disk_Reset ;func 0d - flush buffers ;AC000;ac048;bgb; | ||
| 375 | mov dx,OFFSET DG:ORPHFCB ;point to filename file0000.chk ;ac048;bgb | ||
| 376 | mov AH,FCB_OPEN ;open the file just put into the dir ;ac048;bgb | ||
| 377 | OPAGAIN: ;ac048;bgb | ||
| 378 | ; $do ;ac048;bgb | ||
| 379 | $$DO13: | ||
| 380 | INT 21H ;ac048;bgb | ||
| 381 | or AL,AL ;did the open fail? ;ac048;bgb | ||
| 382 | ; $leave nz ;ac048;bgb | ||
| 383 | JNZ $$EN13 | ||
| 384 | call MAKORPHNAM ;Try next name ;ac048;bgb | ||
| 385 | ; $enddo ;ac048;bgb | ||
| 386 | JMP SHORT $$DO13 | ||
| 387 | $$EN13: | ||
| 388 | GOTORPHNAM: ;di still points to entry ;ac048;bgb | ||
| 389 | mov SI,OFFSET DG:ORPHFCB + 1 ;ORPHFCB Now has good name ;ac048;bgb | ||
| 390 | mov cx,11 ;move filename, ext ;ac048;bgb | ||
| 391 | REP MOVSB ;ac048;bgb | ||
| 392 | call MAKORPHNAM ;Make next name ;ac048;bgb | ||
| 393 | xor ax,ax ;fill dir entry with zeros ;ac048;bgb | ||
| 394 | mov cx,11 ;ac048;bgb | ||
| 395 | REP STOSB ;ac048;bgb | ||
| 396 | ; Add in time for orphan file - BAS July 17/85 ;ac048;bgb | ||
| 397 | push dx ;save starting sector number ;ac048;bgb;an045;bgb | ||
| 398 | call SYSTIME ;ac048;bgb | ||
| 399 | STOSW ; Time ;ac048;bgb | ||
| 400 | mov ax,dx ;ac048;bgb | ||
| 401 | STOSW ; Date ;ac048;bgb | ||
| 402 | pop dx ;restore starting sector number ;ac048;bgb ;an045;bgb | ||
| 403 | mov SI,ds:[DI] ;get starting cluster number ;ac048;bgb ;an005;bgb | ||
| 404 | inc DI ;skip firstclus in entry ;ac048;bgb | ||
| 405 | inc DI ;ac048;bgb | ||
| 406 | PUSH DI ;save it from getfilsiz ;ac048;bgb | ||
| 407 | call GETFILSIZ ;calc file size from number of clus ;ac048;bgb | ||
| 408 | POP DI ;restore di ;ac048;bgb | ||
| 409 | STOSW ;ax=file size low ;ac048;bgb | ||
| 410 | mov ax,dx ;dx=filesize high ;ac048;bgb | ||
| 411 | STOSW ; ;ac048;bgb | ||
| 412 | restorereg <bx,dx,ax> ;offset, sector num, drive num ;ac048;bgb | ||
| 413 | mov cx,1 ;number of sectors = 1 ;ac048;bgb | ||
| 414 | call DOINT26 ;write it out to disk ;ac048;bgb | ||
| 415 | ret ;ac048;bgb | ||
| 416 | endproc fix_entry ;ac048;bgb | ||
| 417 | ;ac048;bgb | ||
| 418 | ;***************************************************************************** ;ac048;bgb;an047;bgb | ||
| 419 | ; NEXTORPH - find the cluster number of the next orphan. This assumes that ;ac048;bgb;an047;bgb | ||
| 420 | ; there is at least one lost cluster available. ;ac048;bgb;an047;bgb | ||
| 421 | ; ;ac048;bgb;an047;bgb | ||
| 422 | ; WARNING!! NOTE!! --> ;ac048;bgb;an047;bgb | ||
| 423 | ; ;ac048;bgb;an047;bgb | ||
| 424 | ; called by - PROCEDURE NAME ;ac048;bgb;an047;bgb | ||
| 425 | ; ;ac048;bgb;an047;bgb | ||
| 426 | ; inputs: AX - ;ac048;bgb;an047;bgb | ||
| 427 | ; BX - ;ac048;bgb;an047;bgb | ||
| 428 | ; CX - ;ac048;bgb;an047;bgb | ||
| 429 | ; DX - ;a;ac048;bgbn047;bgb | ||
| 430 | ; SP - ;;ac048;bgban047;bgb | ||
| 431 | ; BP - ;a;ac048;bgbn047;bgb | ||
| 432 | ; SI - cluster number of the previous orphan ;a;ac048;bgbn047;bgb | ||
| 433 | ; DI - ;a;ac048;bgbn047;bgb | ||
| 434 | ; DS - ;a;ac048;bgbn047;bgb | ||
| 435 | ; ES - points to one byte map of the fat ;a;ac048;bgbn047;bgb | ||
| 436 | ; ;a;ac048;bgbn047;bgb | ||
| 437 | ; output: AX - ;;ac048;bgban047;bgb | ||
| 438 | ; BX - ;a;ac048;bgbn047;bgb | ||
| 439 | ; CX - ;;ac048;bgban047;bgb | ||
| 440 | ; DX - ;a;ac048;bgbn047;bgb | ||
| 441 | ; SP - ;a;ac048;bgbn047;bgb | ||
| 442 | ; BP - ;a;ac048;bgbn047;bgb | ||
| 443 | ; SI - cluster number of one past the orphan ;ac048;bgb;an047;bgb | ||
| 444 | ; DI - cluster number of the orphan ;a;ac048;bgbn047;bgb | ||
| 445 | ; DS - ;a;ac048;bgbn047;bgb | ||
| 446 | ; ES - ;a;ac048;bgbn047;bgb | ||
| 447 | ; ;a;ac048;bgbn047;bgb | ||
| 448 | ; Regs abused - none ;ac048;bgb;an047;bgb | ||
| 449 | ; ;;ac048;bgban047;bgb | ||
| 450 | ;logic: 1. save ax & es, and point to fat map ;ac048;bgb;an047;bgb | ||
| 451 | ; ;a;ac048;bgbn047;bgb | ||
| 452 | ; 2. do until the head of a chain is found: ;ac048;bgb ;an047;bgb | ||
| 453 | ; ;;ac048;bgban047;bgb | ||
| 454 | ; 3. get the next cell ;ac048;bgb ;an047;bgb | ||
| 455 | ; ;;ac048;bgban047;bgb | ||
| 456 | ; 4. bump pointers into fat map ;ac048;bgb ;an047;bgb | ||
| 457 | ; ;;ac048;bgban047;bgb | ||
| 458 | ; 5. restore ax & es ;;ac048;bgban047;bgb | ||
| 459 | ;*****************************************************************************;a;ac048;bgbn047;bgb | ||
| 460 | procedure NEXTORPH,near ;a;ac048;bgbn047;bgb | ||
| 461 | savereg <ax,es> ;save regs abused ;ac048;bgb | ||
| 462 | mov es,[FATMAP] ;point to fat map ;ac048;bgb | ||
| 463 | ; $do ;ac048;bgb | ||
| 464 | $$DO16: | ||
| 465 | loopno: mov al,byte ptr es:[si] ;get the indicated fatmap entry ;ac048;bgb ;an005;bgb | ||
| 466 | inc si ;point to the next one ;ac048;bgb ;an005;bgb | ||
| 467 | inc di ;point to the next one ;ac048;bgb ;an005;bgb | ||
| 468 | cmp AL,89H ;stop when you find an 89 ;ac048;bgb | ||
| 469 | ; $leave z ;this means head(80), found(1), and orphan(8) ;ac048;bgb | ||
| 470 | JZ $$EN16 | ||
| 471 | ; $enddo ;ac048;bgb | ||
| 472 | JMP SHORT $$DO16 | ||
| 473 | $$EN16: | ||
| 474 | restorereg <es,ax> ;restore regs ;ac048;bgb | ||
| 475 | return ;ac048;bgb | ||
| 476 | endproc nextorph ;ac048;bgb | ||
| 477 | ;ac048;bgb | ||
| 478 | ;ac048;bgb | ||
| 479 | |||
| 480 | ;**************************************************************************** | ||
| 481 | ; MARKMAP - make a mark in the fat map for every cluster encountered | ||
| 482 | ; | ||
| 483 | ; called by - markfat, | ||
| 484 | ; | ||
| 485 | ; inputs - AL - the mark | ||
| 486 | ; DI - cluster number | ||
| 487 | ; | ||
| 488 | ; outputs - CY if crosslink found | ||
| 489 | ; - AH - previous mark | ||
| 490 | ; - crosscnt (count of number of crosslinks found) | ||
| 491 | ; - fatmap marked | ||
| 492 | ; | ||
| 493 | ; LOGIC | ||
| 494 | ;****** | ||
| 495 | ; - point to fatmap with es | ||
| 496 | ; - if that cell has been found before, | ||
| 497 | ; then mark it crossed x'10' | ||
| 498 | ; else mark it found al | ||
| 499 | ;**************************************************************************** | ||
| 500 | markmap: savereg <si,es> ;Save registers ;AN000; | ||
| 501 | xor si,si ;Get addr of map ;an005;bgb | ||
| 502 | mov es,[FATMAP] ;Get addr of map ;an005;bgb | ||
| 503 | mov ah,es:[di] ;Get entry at that spot ;an005;bgb | ||
| 504 | or ah,ah ;Is it zero? ; ; | ||
| 505 | ; $IF NZ ;already found - mark crossed;If not, we got crosslink ;AC000; | ||
| 506 | JZ $$IF19 | ||
| 507 | add word ptr crosscnt,1 ;Count the crosslink ; ; | ||
| 508 | adc word ptr crosscnt+2,0 ;Count the crosslink ; ; | ||
| 509 | or byte ptr es:[di],10H ;Resets zero in map ;An005;bgb | ||
| 510 | stc ;Indicate crosslink on ret ; ; | ||
| 511 | ; $ELSE ;not found - mark found ;No crosslink ; ; | ||
| 512 | JMP SHORT $$EN19 | ||
| 513 | $$IF19: | ||
| 514 | mov es:[di],al ;Set mark in map ;Ac005;bgb | ||
| 515 | clc ;Indicate things okay ; ; | ||
| 516 | ; $ENDIF ; ;AN000; | ||
| 517 | $$EN19: | ||
| 518 | restorereg <es,si> ; ;AN005;bgb | ||
| 519 | ret ; ; ; | ||
| 520 | |||
| 521 | |||
| 522 | ;**************************************************************************** | ||
| 523 | ; CHKMAP - Compare FAT and FATMAP looking for badsectors and orphans | ||
| 524 | ; | ||
| 525 | ; called by - | ||
| 526 | ; | ||
| 527 | ; inputs - fatmap | ||
| 528 | ; - dsize - number of clusters on the disk | ||
| 529 | ; | ||
| 530 | ; outputs - badsiz - | ||
| 531 | ; - | ||
| 532 | ; - | ||
| 533 | ; LOGIC | ||
| 534 | ;****** | ||
| 535 | ; - get addr of fatmap | ||
| 536 | ; - get offset of 1st cluster in fatmap | ||
| 537 | ; - do for all the clusters on the disk: | ||
| 538 | ; - if the cluster has been found | ||
| 539 | ; then get the next cluster in its chain | ||
| 540 | ; if the cell was never pointed to by anyone (0) | ||
| 541 | ; then get the contents of that cell from the fat | ||
| 542 | ; (the contents of the fat cell should be zero, too) | ||
| 543 | ; if the fat-cell is not zero | ||
| 544 | ; then (it should only be a bad sector) | ||
| 545 | ; if it is a bad sector, inc the bad-sector-counter | ||
| 546 | ; otherwise, we have found an orphan sector | ||
| 547 | ; end-of-loop | ||
| 548 | ; - if there are any orphans, | ||
| 549 | ; then recover them | ||
| 550 | ;**************************************************************************** | ||
| 551 | CHKMAP: | ||
| 552 | push es ;an014;bgb | ||
| 553 | mov es,fatmap ;get segment of the fatmap ;an005;bgb | ||
| 554 | xor si,si ;get the offset of the fatmap ;an005;bgb | ||
| 555 | mov si,2 ;go past the first two (invalid) entries;an005;bgb | ||
| 556 | ;do for all the clusters on the disk | ||
| 557 | mov cx,[DSIZE] ;loop for the number of clusters on the disk | ||
| 558 | CHKMAPLP: | ||
| 559 | mov al,es:[si] ;move a byte from the fatmap to al ;an005;bgb | ||
| 560 | or al,al ;is the cluster found already? | ||
| 561 | ; $IF Z ;fatmap cell is zero | ||
| 562 | JNZ $$IF22 | ||
| 563 | call unpack ;get the contents of it | ||
| 564 | ; $IF NZ ;is there something in the cell? | ||
| 565 | JZ $$IF23 | ||
| 566 | cmp di,[badval] ;is the fat cell pointing to a bad sector? fff7 | ||
| 567 | ; $IF Z ; yes | ||
| 568 | JNZ $$IF24 | ||
| 569 | inc [badsiz] ;inc the bad sector counter | ||
| 570 | mov byte ptr es:[si],4 ;Flag the map ;an005;bgb | ||
| 571 | ; $ELSE ; no, not a bad sector | ||
| 572 | JMP SHORT $$EN24 | ||
| 573 | $$IF24: | ||
| 574 | orphan: inc [orphsiz] ; then its an orphan | ||
| 575 | mov byte ptr es:[si],8 ;Flag it ;an005;bgb | ||
| 576 | ; $ENDIF | ||
| 577 | $$EN24: | ||
| 578 | ; $ENDIF | ||
| 579 | $$IF23: | ||
| 580 | ; $ENDIF | ||
| 581 | $$IF22: | ||
| 582 | CONTLP: | ||
| 583 | inc si ;point si to next cluster | ||
| 584 | loop chkmaplp | ||
| 585 | cmp [orphsiz],0 ;an005;bgb | ||
| 586 | ; $IF A ;if there are any orphans, go recover them ;an005;bgb | ||
| 587 | JNA $$IF29 | ||
| 588 | call recover | ||
| 589 | ; $ENDIF | ||
| 590 | $$IF29: | ||
| 591 | pop es ;an014;bgb | ||
| 592 | RET18: ret | ||
| 593 | |||
| 594 | ;***************************************************************************** | ||
| 595 | ; PROMPTRECOVER - do the actual recovering of files | ||
| 596 | ; | ||
| 597 | ; inputs: es - points to fatmap | ||
| 598 | ; ax - | ||
| 599 | ; bx - | ||
| 600 | ; cx - | ||
| 601 | ; dx - | ||
| 602 | ; | ||
| 603 | ; outputs: | ||
| 604 | ; LOGIC | ||
| 605 | ; - ask the user if he wants to convert the orphans to files | ||
| 606 | ; - | ||
| 607 | ; - | ||
| 608 | ;*************************************************************************** | ||
| 609 | PromptRecover: | ||
| 610 | mov dx,OFFSET DG:FREEMES | ||
| 611 | call PROMPTYN ;Ask user | ||
| 612 | ; $IF Z | ||
| 613 | JNZ $$IF31 | ||
| 614 | jmp CHAINREC | ||
| 615 | ; $ENDIF | ||
| 616 | $$IF31: | ||
| 617 | NOCHAINREC: | ||
| 618 | mov es,[fatmap] ;Free all orphans ;an005;bgb | ||
| 619 | mov si,2 ;an005;bgb | ||
| 620 | mov cx,[dsize] | ||
| 621 | xor dx,dx ;dx is the new value (free) | ||
| 622 | CHKMAPLP2: | ||
| 623 | mov al,es:[si] ;get next byte from fatmap into al | ||
| 624 | TEST AL,8 ; is it an orphan? | ||
| 625 | ; $IF NZ ;yes | ||
| 626 | JZ $$IF33 | ||
| 627 | call PACK ;si=cluster number dx=new value | ||
| 628 | ; $ENDIF | ||
| 629 | $$IF33: | ||
| 630 | NEXTCLUS: | ||
| 631 | inc si | ||
| 632 | loop CHKMAPLP2 | ||
| 633 | xor ax,ax | ||
| 634 | XCHG ax,[ORPHSIZ] ;number of orphans = zero | ||
| 635 | mov cx,OFFSET DG:FREEBYMES1 ;print msg | ||
| 636 | cmp [DOFIX],0 | ||
| 637 | ; $IF Z | ||
| 638 | JNZ $$IF35 | ||
| 639 | mov cx,OFFSET DG:FREEBYMES2 | ||
| 640 | mov [LCLUS],ax ;move number of lost clust would be ;an049;bgb | ||
| 641 | ; $ENDIF | ||
| 642 | $$IF35: | ||
| 643 | DISPFRB: ;ax=lost clusters (1-fff6) | ||
| 644 | push bx ;save it ;an049;bgb | ||
| 645 | push cx ;save it ;an049;bgb | ||
| 646 | mov cl,[csize] ;get sectors per cluster (1-32) ;an049;bgb | ||
| 647 | xor ch,ch ;zero out high byte ;an049;bgb | ||
| 648 | xor dx,dx ;zero out hi word for word mult ;an049;bgb | ||
| 649 | mul cx ;cx*ax=dx:ax lost sectors (1-1ffec0);an049;bgb | ||
| 650 | mov bx,dx ;move high word for call ;an049;bgb | ||
| 651 | mov cx,ssize ;word to mult with ;an049;bgb | ||
| 652 | call multiply_32_bits ;bx:ax is result ;an049;bgb | ||
| 653 | mov word ptr rarg1,ax ;low word into low word ;an049;bgb | ||
| 654 | mov word ptr rarg1+2,bx ;hi word into hi word ;an049;bgb | ||
| 655 | mov [free_arg1],ax | ||
| 656 | mov [free_arg2],bx ;an049;bgb | ||
| 657 | mov [free_arg3],cx | ||
| 658 | pop cx | ||
| 659 | pop bx | ||
| 660 | mov dx,cx ;Point to right message;an049;bgb | ||
| 661 | call printf_crlf | ||
| 662 | ret | ||
| 663 | |||
| 664 | |||
| 665 | |||
| 666 | |||
| 667 | ;***************************************************************************** | ||
| 668 | ; FINDCHAIN - | ||
| 669 | ; | ||
| 670 | ; called by - recover | ||
| 671 | ; | ||
| 672 | ; inputs: | ||
| 673 | ; | ||
| 674 | ; outputs: | ||
| 675 | ; LOGIC - search thru entire fatmap | ||
| 676 | ; - | ||
| 677 | ; - | ||
| 678 | ;*************************************************************************** | ||
| 679 | lostdeb equ 0 ;set private build version on ;an047;bgb | ||
| 680 | lost_str db '00000' ;max size of cluster number | ||
| 681 | FINDCHAIN: | ||
| 682 | ;Do chain recovery on orphans | ||
| 683 | mov es,[FATMAP] ; point to fatmap | ||
| 684 | mov SI,2 ; point to fatmap | ||
| 685 | mov dx,si ; point to fatmap | ||
| 686 | mov cx,[DSIZE] ;get total number of clusters on disk | ||
| 687 | CHKMAPLP3: | ||
| 688 | mov al,es:[si] ;get next fatmap entry | ||
| 689 | inc si ;point to next fatmap entry | ||
| 690 | ;has to be an orphan(08) | ||
| 691 | TEST AL,8 ;Orphan? | ||
| 692 | jz NEXTCLUS2 ;Nope | ||
| 693 | ;make sure its not a regular file entry | ||
| 694 | TEST AL,1 ;Seen before ? | ||
| 695 | jnz NEXTCLUS2 ;Yup | ||
| 696 | ;recover this chain | ||
| 697 | savereg <si,cx,dx> ;Save search environment | ||
| 698 | dec SI | ||
| 699 | or byte ptr es:[si],81H ;Mark as seen and head | ||
| 700 | |||
| 701 | |||
| 702 | IF LOSTDEB ;is this private build version? | ||
| 703 | call lostdisp ;display lost cluster numbers | ||
| 704 | ENDIF | ||
| 705 | |||
| 706 | add word ptr orphcnt,1 ;Found a chain | ||
| 707 | adc word ptr orphcnt+2,0 ;Found a chain | ||
| 708 | mov SI,dx ;point to the next fatmap entry | ||
| 709 | CHAINLP: | ||
| 710 | call UNPACK ;si = fat cell | ||
| 711 | XCHG SI,DI ;si=contents, di=cell number | ||
| 712 | cmp SI,[EOFVAL] ;is this the end of the file? | ||
| 713 | JAE CHGOON ;yes, then we are done | ||
| 714 | PUSH DI ;no, not eof | ||
| 715 | ;dont do this next part if any of two conditions: | ||
| 716 | ; 1. invalid cluster number | ||
| 717 | ; 2. points to itself | ||
| 718 | cmp SI,2 ;well, is it a valid cluster number? | ||
| 719 | JB INSERTEOF ;Bad cluster number | ||
| 720 | cmp SI,[dsize] | ||
| 721 | JA INSERTEOF ;Bad cluster number | ||
| 722 | cmp SI,DI ;how bout if it points to itself? | ||
| 723 | jz INSERTEOF ;Tight loop | ||
| 724 | ; find out what it points TO | ||
| 725 | call CROSSCHK | ||
| 726 | TEST AH,8 ;Points to a non-orphan? | ||
| 727 | jnz CHKCHHEAD ;Nope | ||
| 728 | ;orphan points to nothing | ||
| 729 | INSERTEOF: | ||
| 730 | ; you come here if: | ||
| 731 | ; 1. invalid cluster number | ||
| 732 | ; 2. points to itself | ||
| 733 | ; 3. points to nothing | ||
| 734 | POP SI ;the previous cluster number | ||
| 735 | mov dx,0FFFH ;get eof value (12-bit) | ||
| 736 | cmp [BIGFAT],0 | ||
| 737 | jz FAT12_4 | ||
| 738 | mov dx,0FFFFH ;get eof value (16-bit) | ||
| 739 | FAT12_4: | ||
| 740 | call PACK ;stick it in! | ||
| 741 | jmp SHORT CHGOON ;and we are done | ||
| 742 | ; orphan point to a head entry | ||
| 743 | CHKCHHEAD: | ||
| 744 | TEST AH,80H ;Previosly marked head? | ||
| 745 | jz ADDCHAIN ;Nope | ||
| 746 | AND BYTE PTR es:[DI],NOT 80H ;Turn off head bit | ||
| 747 | sub word ptr orphcnt,1 ;Wasn't really a head | ||
| 748 | sbb word ptr orphcnt+2,0 ;Wasn't really a head | ||
| 749 | POP DI ;Clean stack | ||
| 750 | jmp SHORT CHGOON | ||
| 751 | ADDCHAIN: | ||
| 752 | TEST AH,1 ;Previosly seen? | ||
| 753 | jnz INSERTEOF ;Yup, don't make a cross link | ||
| 754 | or BYTE PTR es:[DI],1 ;Mark as seen | ||
| 755 | POP DI ;Clean stack | ||
| 756 | jmp CHAINLP ;Follow chain | ||
| 757 | CHGOON: | ||
| 758 | POP dx ;Restore search | ||
| 759 | POP cx | ||
| 760 | POP SI | ||
| 761 | NEXTCLUS2: | ||
| 762 | inc dx | ||
| 763 | loop CHKMAPLP3 | ||
| 764 | ret | ||
| 765 | |||
| 766 | |||
| 767 | |||
| 768 | ;***************************************************************************** ;ac048;bgb | ||
| 769 | ; CHAINREC - the user has requested us to recover the lost clusters ;ac048;bgb | ||
| 770 | ; ;ac048;bgb | ||
| 771 | ; inputs: ;ac048;bgb | ||
| 772 | ; note: although called from PROMPTRECOVER, this routine returns control to ;ac048;bgb | ||
| 773 | ; recover via the ret instruction. ;ac048;bgb | ||
| 774 | ;***************************************************************************** ;ac048;bgb | ||
| 775 | ;ac048;bgb | ||
| 776 | ;***************************************************************************** ;ac048;bgb | ||
| 777 | ; CHAINREC - The user has requested us to recover the lost clusters ;ac048;bgb | ||
| 778 | ; ;ac048;bgb | ||
| 779 | ; WARNING!! NOTE!! --> the count of the number of lost cluster chains remains, | ||
| 780 | ; for this proc, a single word. More than 64k chains | ||
| 781 | ; will cause this proc to fail. | ||
| 782 | ; ;ac048;bgb | ||
| 783 | ; called by - PROCEDURE NAME ;ac048;bgb | ||
| 784 | ; ;ac048;bgb | ||
| 785 | ; inputs: AX - N/A ;ac048;bgb | ||
| 786 | ; bx - ;ac048;bgb | ||
| 787 | ; cx - N/A ;ac048;bgb | ||
| 788 | ; dx - N/A ;ac048;bgb | ||
| 789 | ; SP - ;ac048;bgb | ||
| 790 | ; BP - N/A ;ac048;bgb | ||
| 791 | ; SI - N/A ;ac048;bgb | ||
| 792 | ; DI - N/A ;ac048;bgb | ||
| 793 | ; data: root_entries ;ac048;bgb | ||
| 794 | ; orphcnt ;ac048;bgb | ||
| 795 | ; ;ac048;bgb | ||
| 796 | ; output: AX - ;ac048;bgb | ||
| 797 | ; bx - ;ac048;bgb | ||
| 798 | ; cx - ;ac048;bgb | ||
| 799 | ; dx - ;ac048;bgb | ||
| 800 | ; SP - ;ac048;bgb | ||
| 801 | ; BP - ;ac048;bgb | ||
| 802 | ; SI - ;ac048;bgb | ||
| 803 | ; DI- ;ac048;bgb | ||
| 804 | ; ;ac048;bgb | ||
| 805 | ; Regs abused - ;ac048;bgb | ||
| 806 | ; ;ac048;bgb | ||
| 807 | ;logic: 1. ;ac048;bgb | ||
| 808 | ;***************************************************************************** ;ac048;bgb | ||
| 809 | CHAINREC: ;ac048;bgb | ||
| 810 | push es ;save es if it is used for anything ;ac048;bgb | ||
| 811 | push ds ;make es point to data ;ac048;bgb | ||
| 812 | pop es ;ac048;bgb | ||
| 813 | ;find the cluster number of the orphan ;ac048;bgb | ||
| 814 | mov SI,2 ;start at first cluster ;an005;bgb ;ac048;bgb | ||
| 815 | mov DI,1 ;point to previous cluster? ;ac048;bgb | ||
| 816 | call NEXTORPH ;di points to orphan ;ac048;bgb | ||
| 817 | ;init for loop ;ac048;bgb | ||
| 818 | savereg <si,di> ;save orphan, orphan+1 ;ac048;bgb | ||
| 819 | mov SI,DI ;si point to orphan ;ac048;bgb | ||
| 820 | xor ax,ax ;set count of dir entries processed to zero;ac048;bgb | ||
| 821 | mov dx,word ptr orphcnt ;get low word of lost clusters ;ac048;bgb;an049;bgb | ||
| 822 | mov word ptr temp_dd,dx ;get low word of lost clusters ;an049;bgb | ||
| 823 | mov dx,word ptr orphcnt+2 ;get hi word of lost clusters ;an049;bgb | ||
| 824 | mov word ptr temp_dd+2,dx ;get hi word of lost clusters ;an049;bgb | ||
| 825 | mov BP,OFFSET DG:PHONEY_STACK ;Set BP to point to "root" ;ac048;bgb | ||
| 826 | ;do for all dir entries: ;ac048;bgb | ||
| 827 | MAKFILLP: ;ac048;bgb | ||
| 828 | ; $DO ;do for all root entries ;ac048;bgb | ||
| 829 | $$DO37: | ||
| 830 | savereg <ax> ;cnt of entries processed, num orphans ;ac048;bgb;an049;bgb | ||
| 831 | call GETENT ;DI points to entry ;ac048;bgb | ||
| 832 | cmp BYTE PTR ds:[DI],0E5H ;is this dir entry erased? ;an;ac048;bgb005;bgb | ||
| 833 | ; $if z,or ;ac048;bgb | ||
| 834 | JZ $$LL38 | ||
| 835 | cmp BYTE PTR ds:[DI],0 ;is this dir entry empty? ;an;ac048;bgb005;bgb | ||
| 836 | ; $if z ;ac048;bgb | ||
| 837 | JNZ $$IF38 | ||
| 838 | $$LL38: | ||
| 839 | GOTENT: mov [HAVFIX],1 ;Making a fix ;ac048;bgb | ||
| 840 | cmp [DOFIX],0 ;/f parameter specified? ;ac048;bgb | ||
| 841 | ; $if NZ ;yes- do the fix ;ac048;bgb | ||
| 842 | JZ $$IF39 | ||
| 843 | call fix_entry ;ac048;bgb | ||
| 844 | ; $endif ;ac048;bgb | ||
| 845 | $$IF39: | ||
| 846 | ENTMADE: restorereg <ax,di,si> ;ac048;bgb;an049;bgb | ||
| 847 | sub word ptr temp_dd,1 ;finished with one orphan ;ac048;bgb;an049;bgb | ||
| 848 | sbb word ptr temp_dd+2,0 ;finished with one orphan ;ac048;bgb;an049;bgb | ||
| 849 | cmp word ptr temp_dd,0 ;is that the last one? ;ac048;bgb;an049;bgb | ||
| 850 | ; $IF Z,AND ;no, check the hi word ;an049;bgb | ||
| 851 | JNZ $$IF41 | ||
| 852 | cmp word ptr temp_dd+2,0;is that the last one? ;ac048;bgb;an049;bgb | ||
| 853 | ; $IF Z ;neither are zero ;an049;bgb | ||
| 854 | JNZ $$IF41 | ||
| 855 | jmp RET100 ; yes,we are done ;ac048;bgb;an049;bgb | ||
| 856 | ; $endif ;an049;bgb | ||
| 857 | $$IF41: | ||
| 858 | call NEXTORPH ;get the cluster of the next one ;ac048;bgb | ||
| 859 | savereg <si,di> ;ac048;bgb | ||
| 860 | mov SI,DI ;ac048;bgb | ||
| 861 | ; $else ;dir entry was not erased or zero ;ac048;bgb | ||
| 862 | JMP SHORT $$EN38 | ||
| 863 | $$IF38: | ||
| 864 | NEXTENT: restorereg <ax> ;ac048;bgb;an049;bgb | ||
| 865 | ; $endif ;ac048;bgb | ||
| 866 | $$EN38: | ||
| 867 | NXTORP: inc ax ;ac048;bgb | ||
| 868 | cmp ax,root_entries ;do for 0 to (root_entries - 1) ;ac048;bgb | ||
| 869 | ; $leave z ;ac048;bgb | ||
| 870 | JZ $$EN37 | ||
| 871 | ; $ENDDO ;ac048;bgb | ||
| 872 | JMP SHORT $$DO37 | ||
| 873 | $$EN37: | ||
| 874 | restorereg <ax,ax> ;Clean Stack from si,di ;ac048;bgb | ||
| 875 | sub word ptr orphcnt,dx ;Couldn't make them all ;ac048;bgb | ||
| 876 | sbb word ptr orphcnt+2,0 ;Couldn't make them all ;ac048;bgb | ||
| 877 | mov dx,OFFSET DG:CREATMES ;ac048;bgb | ||
| 878 | mov byte ptr [arg_buf],0 ;ac048;bgb | ||
| 879 | call EPRINT ;ac048;bgb | ||
| 880 | RET100: pop es ;restore es ;ac048;bgb | ||
| 881 | ret ;ac048;bgb | ||
| 882 | ;ac048;bgb | ||
| 883 | ;ac048;bgb | ||
| 884 | ;ac048;bgb | ||
| 885 | |||
| 886 | ;***************************************************************************** | ||
| 887 | ;***************************************************************************** | ||
| 888 | SUBTTL AMDONE - Finish up routine | ||
| 889 | PAGE | ||
| 890 | Public AmDone | ||
| 891 | AMDONE: | ||
| 892 | ASSUME DS:NOTHING | ||
| 893 | cmp [DIRTYFAT],0 | ||
| 894 | jz NOWRITE ;FAT not dirty | ||
| 895 | cmp [DOFIX],0 | ||
| 896 | jz NOWRITE ;Not supposed to fix | ||
| 897 | REWRITE: | ||
| 898 | LDS bx,[THISDPB] | ||
| 899 | ASSUME DS:NOTHING | ||
| 900 | mov cx,[bx.dpb_FAT_size] ;Sectors for one fat (DCR) ;AC000; | ||
| 901 | mov DI,cx | ||
| 902 | mov CL,[bx.dpb_FAT_count] ;Number of FATs | ||
| 903 | mov dx,[bx.dpb_first_FAT] ;First sector of FAT | ||
| 904 | PUSH CS | ||
| 905 | POP DS | ||
| 906 | ASSUME DS:DG | ||
| 907 | mov [ERRCNT],0 | ||
| 908 | ; set up to write to the disk | ||
| 909 | xor bx,bx ;offset of the fat-table ;an005;bgb | ||
| 910 | mov es,fattbl_seg ;segment of the fat-table ;an005;bgb | ||
| 911 | mov AL,[ALLDRV] | ||
| 912 | dec AL | ||
| 913 | mov AH,1 | ||
| 914 | PUSH cx | ||
| 915 | WRTLOOP: | ||
| 916 | XCHG cx,DI | ||
| 917 | PUSH dx | ||
| 918 | PUSH cx | ||
| 919 | PUSH DI | ||
| 920 | PUSH ax | ||
| 921 | |||
| 922 | call Write_Disk ;Do relative sector write ;AC000; | ||
| 923 | |||
| 924 | JNC WRTOK | ||
| 925 | inc [ERRCNT] | ||
| 926 | ;mov [badrw_str],offset dg:writing | ||
| 927 | POP ax ; Get fat # in AH | ||
| 928 | PUSH ax ; Back on stack | ||
| 929 | xchg al,ah ; Fat # to AL | ||
| 930 | xor ah,ah ; Make it a word | ||
| 931 | mov [badrw_num],ax | ||
| 932 | mov dx,offset dg:badw_arg | ||
| 933 | call PRINTf_crlf | ||
| 934 | WRTOK: | ||
| 935 | POP ax | ||
| 936 | POP cx | ||
| 937 | POP DI | ||
| 938 | POP dx | ||
| 939 | inc AH | ||
| 940 | ADD dx,DI | ||
| 941 | loop WRTLOOP ;Next FAT | ||
| 942 | POP cx ;Number of FATs | ||
| 943 | cmp CL,[ERRCNT] ;Error on all? | ||
| 944 | ; $if e | ||
| 945 | JNE $$IF47 | ||
| 946 | jmp fatal | ||
| 947 | ; $endif | ||
| 948 | $$IF47: | ||
| 949 | ; make sure that the data fields are always adressable, because | ||
| 950 | ;we can come here after a ctl - break has happened. so point to them w/ cs: | ||
| 951 | NOWRITE: | ||
| 952 | DOS_Call Disk_Reset ; ;AC000; | ||
| 953 | mov dx,OFFSET DG:USERDIR ;Recover users directory | ||
| 954 | DOS_Call ChDir ; ;AC000; | ||
| 955 | cmp BYTE PTR cs:[FRAGMENT],1 ;Check for any fragmented files? ;an029;bgb | ||
| 956 | jnz DONE ;No -- we're finished | ||
| 957 | call CHECKFILES ;Yes -- report any fragments | ||
| 958 | Public Done | ||
| 959 | DONE: | ||
| 960 | ASSUME DS:NOTHING | ||
| 961 | mov DL,cs:[USERDEV] ;Recover users drive ;an029;bgb | ||
| 962 | DOS_Call Set_Default_Drive ; ;AC000; | ||
| 963 | ret | ||
| 964 | |||
| 965 | |||
| 966 | |||
| 967 | |||
| 968 | |||
| 969 | |||
| 970 | |||
| 971 | |||
| 972 | |||
| 973 | IF LOSTDEB ;is this private build version? | ||
| 974 | Procedure lostdisp,near ;an005;bgb | ||
| 975 | savereg <ax,bx,cx,dx,si,di> ; ;an005;bgb | ||
| 976 | mov ax,dx ;save orig value | ||
| 977 | |||
| 978 | mov cl,12 ;shift 3 nibbles | ||
| 979 | shr dx,cl ;remove al but last nibble | ||
| 980 | and dx,000fh | ||
| 981 | cmp dx,0ah | ||
| 982 | ; $IF B | ||
| 983 | JNB $$IF49 | ||
| 984 | add dx,30h ;make it char | ||
| 985 | ; $ELSE | ||
| 986 | JMP SHORT $$EN49 | ||
| 987 | $$IF49: | ||
| 988 | add dx,37h | ||
| 989 | ; $ENDIF | ||
| 990 | $$EN49: | ||
| 991 | push ax | ||
| 992 | mov ah,2 | ||
| 993 | int 21h | ||
| 994 | pop ax | ||
| 995 | |||
| 996 | mov dx,ax ;get orig value | ||
| 997 | mov cl,8 | ||
| 998 | shr dx,cl | ||
| 999 | and dx,000fh | ||
| 1000 | cmp dx,0ah | ||
| 1001 | ; $IF B | ||
| 1002 | JNB $$IF52 | ||
| 1003 | add dx,30h ;make it char | ||
| 1004 | ; $ELSE | ||
| 1005 | JMP SHORT $$EN52 | ||
| 1006 | $$IF52: | ||
| 1007 | add dx,37h | ||
| 1008 | ; $ENDIF | ||
| 1009 | $$EN52: | ||
| 1010 | push ax | ||
| 1011 | mov ah,2 | ||
| 1012 | int 21h | ||
| 1013 | pop ax | ||
| 1014 | |||
| 1015 | mov dx,ax ;get orig value | ||
| 1016 | mov cl,4 | ||
| 1017 | shr dx,cl | ||
| 1018 | and dx,000fh | ||
| 1019 | cmp dx,0ah | ||
| 1020 | ; $IF B | ||
| 1021 | JNB $$IF55 | ||
| 1022 | add dx,30h ;make it char | ||
| 1023 | ; $ELSE | ||
| 1024 | JMP SHORT $$EN55 | ||
| 1025 | $$IF55: | ||
| 1026 | add dx,37h | ||
| 1027 | ; $ENDIF | ||
| 1028 | $$EN55: | ||
| 1029 | push ax | ||
| 1030 | mov ah,2 | ||
| 1031 | int 21h | ||
| 1032 | pop ax | ||
| 1033 | |||
| 1034 | mov dx,ax ;get orig value | ||
| 1035 | and dx,000fh | ||
| 1036 | cmp dx,0ah | ||
| 1037 | ; $IF B | ||
| 1038 | JNB $$IF58 | ||
| 1039 | add dx,30h ;make it char | ||
| 1040 | ; $ELSE | ||
| 1041 | JMP SHORT $$EN58 | ||
| 1042 | $$IF58: | ||
| 1043 | add dx,37h | ||
| 1044 | ; $ENDIF | ||
| 1045 | $$EN58: | ||
| 1046 | mov ah,2 | ||
| 1047 | int 21h | ||
| 1048 | |||
| 1049 | mov dl,' ' ;space after last number | ||
| 1050 | mov ah,2 | ||
| 1051 | int 21h | ||
| 1052 | |||
| 1053 | restorereg <di,si,dx,bx,cx,ax> ;an005;bgb | ||
| 1054 | return ;an005;bgb | ||
| 1055 | EndProc lostdisp ;an005;bgb | ||
| 1056 | ENDIF | ||
| 1057 | |||
| 1058 | |||
| 1059 | pathlabl chkfat | ||
| 1060 | |||
| 1061 | |||
| 1062 | CODE ENDS | ||
| 1063 | END | ||
| 1064 | \ No newline at end of file | ||