Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

940 lines
23 KiB

  1. DOSSEG
  2. .MODEL LARGE
  3. include disk.inc
  4. ;
  5. ; Disk record structure specific to int13-visible disks.
  6. ;
  7. INT13_DISK_INFO STRUC
  8. ;
  9. ; First part is a DiskInfo structure
  10. ;
  11. DiskInfo db SIZE DISK_INFO DUP (?)
  12. ;
  13. ; Int13 unit number and drive geometry for drive.
  14. ;
  15. Int13DiskUnit db ?
  16. Int13SectorsPerTrack db ?
  17. Int13Heads dw ?
  18. Int13Cylinders dw ?
  19. Int13xSectorCountl dw ?
  20. Int13xSectorCounth dw ?
  21. INT13_DISK_INFO ENDS
  22. .DATA?
  23. extrn DiskList:dword
  24. ;
  25. ; Table of drives for which xint13 is disabled
  26. ; 128 units at 1 bit each = 128 bits = 16 bytes = 8 words
  27. ;
  28. ; We support this solely by returning a zero
  29. ; extended sector count from pGetExtendedInt13SectorCount;
  30. ; this forces everyone else into regular int13 mode.
  31. ;
  32. xInt13DisableTable db 16 dup (?)
  33. .CODE
  34. ASSUME ds:NOTHING
  35. extrn _malloc:far
  36. .386
  37. ;++
  38. ;
  39. ; UINT
  40. ; _far
  41. ; InitializeInt13DiskList(
  42. ; IN UINT FirstDiskId
  43. ; );
  44. ;
  45. ; Routine Description:
  46. ;
  47. ; This routine determines the number of int13 disk units and
  48. ; gathers information about each, which is saved in a structure.
  49. ; The structures are stored in a linked list whose head is
  50. ; the DiskList global variable.
  51. ;
  52. ; Arguments:
  53. ;
  54. ; FirstDiskId - supplies the id to be used for the first disk.
  55. ;
  56. ; Return Value:
  57. ;
  58. ; non-0 - success
  59. ; 0 - failure
  60. ;
  61. ;--
  62. FirstDiskId equ word ptr [bp+6]
  63. public InitializeInt13DiskList
  64. InitializeInt13DiskList proc far
  65. push bp
  66. mov bp,sp
  67. push ds
  68. push es
  69. push bx
  70. push si
  71. push di
  72. mov ah,8
  73. mov dl,80h
  74. int 13h
  75. jnc @f
  76. xor dl,dl
  77. @@: or dl,80h
  78. xor dh,dh
  79. mov di,dx ; di = int13 disk limit
  80. mov si,80h ; si = current int13 disk
  81. nextdisk:
  82. cmp si,di
  83. je ildoneok ; no more disks
  84. push ds
  85. push DGROUP
  86. pop ds ; crt needs ds to address _DATA
  87. push SIZE INT13_DISK_INFO
  88. call _malloc
  89. add sp,2
  90. pop ds
  91. mov cx,ax
  92. or cx,dx
  93. jz ildone ; ax already 0 for error return
  94. push ax
  95. push dx ; save disk record pointer
  96. push si ; save current int13 unit #
  97. push di ; save int13 unit # limit
  98. mov dx,si ; dl = int13 unit #
  99. mov ah,8
  100. int 13h
  101. pop di ; di = int13 disk limit
  102. pop bx ; bl = int13 unit #, bh = 0
  103. pop ds
  104. pop si ; ds:si -> new disk record
  105. jnc @f
  106. mov ax,0
  107. jmp short ildone
  108. ;
  109. ; Store int13 unit number in disk record.
  110. ; Also generate a disk id.
  111. ;
  112. @@: mov ax,bx
  113. sub ax,80h
  114. add ax,FirstDiskId
  115. mov [si].DiskInfo.DiskInfoDiskId,ax
  116. mov [si].DiskInfo.DiskInfoDiskOpen,bh ; bh=0, set disk not open
  117. mov [si].Int13DiskUnit,bl
  118. ;
  119. ; Max head is in in dh, convert to count in dx
  120. ;
  121. shr dx,8
  122. inc dx
  123. mov [si].Int13Heads,dx
  124. ;
  125. ; Deal with sectors per track in cl
  126. ;
  127. mov al,cl
  128. and al,3fh
  129. mov [si].Int13SectorsPerTrack,al
  130. ;
  131. ; Deal with cylinder count wierdness
  132. ;
  133. xchg ch,cl
  134. shr ch,6
  135. inc cx
  136. mov [si].Int13Cylinders,cx
  137. ;
  138. ; Fetch extended int13 count. Comes back as 0 if xint13
  139. ; not supported for the drive.
  140. ;
  141. push bx
  142. call far ptr pGetExtendedInt13SectorCount
  143. pop cx ; cl = int13 unit#, ch = 0
  144. mov [si].Int13xSectorCountl,ax
  145. mov [si].Int13xSectorCounth,dx
  146. ;
  147. ; Now link the disk record into the linked list.
  148. ;
  149. mov dx,di ; dx = int13 unit # limit
  150. mov ax,DGROUP
  151. mov es,ax
  152. mov di,OFFSET DGROUP:DiskList ; es:di = &DiskList
  153. mov ax,es:[di]
  154. mov [si].DiskInfo.DiskInfoNextl,ax
  155. mov ax,es:[di+2]
  156. mov [si].DiskInfo.DiskInfoNexth,ax
  157. mov es:[di],si
  158. mov ax,ds
  159. mov es:[di+2],ax
  160. mov di,dx ; di = int13 unit # limit
  161. mov si,cx ; si = int13 unit #
  162. inc si
  163. jmp nextdisk
  164. ildoneok:
  165. mov ax,si
  166. sub ax,80h ; ax = int13 disk count
  167. ildone:
  168. pop di
  169. pop si
  170. pop bx
  171. pop es
  172. pop ds
  173. leave
  174. retf
  175. InitializeInt13DiskList endp
  176. ;++
  177. ;
  178. ; BOOL
  179. ; _far
  180. ; OpenInt13Disk(
  181. ; IN FPINT13_DISK_INFO DiskRecord
  182. ; );
  183. ;
  184. ; Routine Description:
  185. ;
  186. ; This routine "opens" an int13 disk.
  187. ; Housekeeping such as locking, etc, is performed.
  188. ;
  189. ; It is assumed that a disk can be opened only once at a time,
  190. ; but the caller is responsible for enforcing this.
  191. ;
  192. ; Arguments:
  193. ;
  194. ; DiskRecord - supplies a far pointer to the disk record struct
  195. ; for the disk to be opened.
  196. ;
  197. ; Return Value:
  198. ;
  199. ; non-0 - success
  200. ; 0 - failure
  201. ;
  202. ;--
  203. DiskRecord equ dword ptr [bp+6]
  204. public OpenInt13Disk
  205. OpenInt13Disk proc far
  206. ;
  207. ; BUGBUG perform locking for OSR2
  208. ;
  209. mov ax,1
  210. retf
  211. OpenInt13Disk endp
  212. ;++
  213. ;
  214. ; VOID
  215. ; _far
  216. ; CloseInt13Disk(
  217. ; IN FPINT13_DISK_INFO DiskRecord
  218. ; );
  219. ;
  220. ; Routine Description:
  221. ;
  222. ; This routine "closes" an int13 disk previously opened with
  223. ; OpenInt13Disk. Housekeeping such as locking, etc, is performed.
  224. ;
  225. ; Arguments:
  226. ;
  227. ; DiskRecord - supplies a far pointer to the disk record struct
  228. ; for the disk to be closed.
  229. ;
  230. ; Return Value:
  231. ;
  232. ; None.
  233. ;
  234. ;--
  235. DiskRecord equ dword ptr [bp+6]
  236. public CloseInt13Disk
  237. CloseInt13Disk proc far
  238. ;
  239. ; BUGBUG perform unlocking for OSR2
  240. ;
  241. retf
  242. CloseInt13Disk endp
  243. ;
  244. ; BOOL
  245. ; _far
  246. ; pInt13Read(
  247. ; IN FPINT13_DISK_INFO DiskRecord,
  248. ; IN ULONG StartSector,
  249. ; IN BYTE SectorCount,
  250. ; OUT FPVOID Buffer
  251. ; );
  252. ;
  253. ; BOOL
  254. ; _far
  255. ; pInt13Read(
  256. ; IN FPINT13_DISK_INFO DiskRecord,
  257. ; IN ULONG StartSector,
  258. ; IN BYTE SectorCount,
  259. ; IN FPVOID Buffer
  260. ; );
  261. ;
  262. DiskRecord equ dword ptr [bp+6]
  263. StartSectorl equ word ptr [bp+10]
  264. StartSectorh equ word ptr [bp+12]
  265. SectorCount equ byte ptr [bp+14]
  266. Buffer equ dword ptr [bp+16]
  267. public pInt13Read
  268. pInt13Read label far
  269. mov ah,2
  270. jmp short pInt13IO
  271. public pInt13Write
  272. pInt13Write label far
  273. mov ah,3
  274. pInt13IO proc far
  275. push bp
  276. mov bp,sp
  277. push ds
  278. push es
  279. push bx
  280. push si
  281. push di
  282. push ax
  283. lds si,DiskRecord
  284. ;
  285. ; Calculate sectors per cylinder, which is a max of 63*256 = 16128,
  286. ; which fits in a word register. But we do a full 32-bit multiply,
  287. ; because the heads count could be 256 (which doesn't fit in al).
  288. ;
  289. mov al,[si].Int13SectorsPerTrack
  290. cbw ; ax = sectors per track
  291. mul [si].Int13Heads ; ax = sectors per cylinder
  292. mov bx,ax ; bx = sectors per cylinder
  293. mov dx,StartSectorh
  294. mov ax,StartSectorl ; dx:ax = start sector
  295. div bx ; ax = cyl, dx = sector in cyl
  296. ;
  297. ; Set up the cylinder in cx in int13 format:
  298. ;
  299. ; ch = bits 0-7 of the cylinder
  300. ; bits 6,7 of cl = bits 8,9 of the cylinder
  301. ;
  302. mov cx,ax
  303. xchg cl,ch
  304. shl cl,6
  305. ;
  306. ; Now calculate the head and sector. The head is max 255
  307. ; and the sector is max 62, meaning we can do a 16-bit divide.
  308. ;
  309. mov ax,dx ; ax = sector within cylinder
  310. div [si].Int13SectorsPerTrack ; al = head, ah = sector
  311. ;
  312. ; Pack everything into int13 format.
  313. ;
  314. inc ah ; sector is 1-based (1-63)
  315. or cl,ah
  316. mov dh,al ; dh = head
  317. mov dl,[si].Int13DiskUnit
  318. les bx,Buffer
  319. pop ax ; ah = operation (2 or 3)
  320. mov al,SectorCount
  321. int 13h
  322. setnc al
  323. cbw
  324. pop di
  325. pop si
  326. pop bx
  327. pop es
  328. pop ds
  329. leave
  330. retf
  331. pInt13IO endp
  332. ;
  333. ; BOOL
  334. ; _far
  335. ; pXInt13Read(
  336. ; IN FPINT13_DISK_INFO DiskRecord,
  337. ; IN ULONG StartSector,
  338. ; IN BYTE SectorCount,
  339. ; OUT FPVOID Buffer
  340. ; );
  341. ;
  342. ; BOOL
  343. ; _far
  344. ; pXInt13Read(
  345. ; IN FPINT13_DISK_INFO DiskRecord,
  346. ; IN ULONG StartSector,
  347. ; IN BYTE SectorCount,
  348. ; IN FPVOID Buffer
  349. ; );
  350. ;
  351. DiskRecord equ dword ptr [bp+6]
  352. StartSector equ dword ptr [bp+10]
  353. SectorCount equ byte ptr [bp+14]
  354. Buffer equ dword ptr [bp+16]
  355. public pXInt13Read
  356. pXInt13Read label far
  357. mov ah,42h
  358. jmp short pXInt13IO
  359. public pXInt13Write
  360. pXInt13Write label far
  361. mov ax,4300h ; need to clear bit 0 (verify flag)
  362. pXInt13IO proc far
  363. push bp
  364. mov bp,sp
  365. push ds
  366. push es
  367. push bx
  368. push si
  369. push di
  370. lds si,DiskRecord ; ds:si -> disk record
  371. mov dl,[si].Int13DiskUnit
  372. push 0 ; high dword of sector # is 0
  373. push 0
  374. push StartSector
  375. push Buffer
  376. mov bl,SectorCount ; sector count
  377. xor bh,bh ; make sure high byte is 0
  378. push bx
  379. push 16 ; packet size
  380. push ss
  381. pop ds
  382. mov si,sp ; ds:si -> param packet on stack
  383. int 13h ; ax already set up from above
  384. setnc al
  385. cbw ; ax: 0=failure, 1=success
  386. add sp,16 ; get rid of param packet on stack
  387. pop di
  388. pop si
  389. pop bx
  390. pop es
  391. pop ds
  392. leave
  393. retf
  394. pXInt13IO endp
  395. ;++
  396. ;
  397. ; BOOL
  398. ; _far
  399. ; Int13DiskIo(
  400. ; IN FPINT13_DISK_INFO DiskRecord
  401. ; IN ULONG StartSector,
  402. ; IN BYTE SectorCount,
  403. ; IN OUT FPVOID Buffer,
  404. ; IN BOOL Write
  405. ; );
  406. ;
  407. ; Routine Description:
  408. ;
  409. ; This routine performs disk i/o using int13 services, automatically
  410. ; using extended int13 services if available for the drive.
  411. ;
  412. ; This routine DOES ensure that i/o will not cross a track boundary
  413. ; to ensure maximum compatibility with various BIOSes out there.
  414. ;
  415. ; Arguments:
  416. ;
  417. ; DiskRecord - supplies pointer to the disk record structure for the
  418. ; disk to be read from or written to.
  419. ;
  420. ; StartSector - supplies the physical start sector where the transfer
  421. ; is to start.
  422. ;
  423. ; SectorCount - supplies the number of sectors to be transfered.
  424. ;
  425. ; Buffer - supplies the target buffer for reads or the data for write.
  426. ;
  427. ; Write - non-0 means write operation, 0 means read operation.
  428. ;
  429. ; Return Value:
  430. ;
  431. ; non-0 - success
  432. ; 0 - failure
  433. ;
  434. ;--
  435. DiskRecord equ dword ptr [bp+6]
  436. StartSector equ dword ptr [bp+10]
  437. StartSectorl equ word ptr [bp+10]
  438. StartSectorh equ word ptr [bp+12]
  439. SectorCount equ byte ptr [bp+14]
  440. Buffer equ dword ptr [bp+16]
  441. Bufferl equ word ptr [bp+18]
  442. Bufferh equ word ptr [bp+18]
  443. Write equ word ptr [bp+20]
  444. IoRoutine equ dword ptr [bp-4]
  445. IoRoutinel equ word ptr [bp-4]
  446. IoRoutineh equ word ptr [bp-2]
  447. public Int13DiskIo
  448. Int13DiskIo proc far
  449. push bp
  450. mov bp,sp
  451. sub sp,4
  452. push ds
  453. push es
  454. push bx
  455. push si
  456. push di
  457. ;
  458. ; Address the disk record structure to determine
  459. ; which set of int13 services to use (standard or extended).
  460. ; We'll use extended if they are supported for the drive.
  461. ; Even in that case, however, we'll do i/o a track at a time
  462. ; to ensure maximum compatibility.
  463. ;
  464. lds si,DiskRecord
  465. mov ax,Write
  466. cmp [si].Int13xSectorCountl,0
  467. jnz io_xint13
  468. cmp [si].Int13xSectorCounth,0
  469. jnz io_xint13
  470. cmp ax,1
  471. je @f
  472. mov dx,SEG pInt13Read
  473. mov ax,OFFSET pInt13Read
  474. jmp short store_io
  475. @@: mov dx,SEG pInt13Write
  476. mov ax,OFFSET pInt13Write
  477. jmp short store_io
  478. io_xint13:
  479. cmp ax,1
  480. je @f
  481. mov dx,SEG pXInt13Read
  482. mov ax,OFFSET pXInt13Read
  483. jmp short store_io
  484. @@: mov dx,SEG pXInt13Write
  485. mov ax,OFFSET pXInt13Write
  486. store_io:
  487. mov IoRoutinel,ax
  488. mov IoRoutineh,dx
  489. ;
  490. ; Figure out how many sectors are left in the first track.
  491. ; Note that this calculation can overflow, since the sector
  492. ; can be very large (like in the xint13 case) and thus the
  493. ; absolute track number can easily be > 64k. To get around this
  494. ; we calculate the cylinder and remainder first, and then
  495. ; degenerate the remainder into track and sector.
  496. ;
  497. ; Max sectors per cylinder = 63*256, which fits in a word register.
  498. ;
  499. mov al,[si].Int13SectorsPerTrack
  500. cbw
  501. mul [si].Int13Heads ; ax = sectors per cylinder
  502. mov cx,ax ; cx = sectors per cylinder
  503. mov dx,StartSectorh
  504. mov ax,StartSectorl ; dx:ax = lba start sector
  505. div cx ; dx = sector within cylinder
  506. mov ax,dx ; ax = sector within cylinder
  507. div [si].Int13SectorsPerTrack ; ah = sector in track
  508. mov al,[si].Int13SectorsPerTrack
  509. sub al,ah ; al = sectors left in track
  510. cbw ; ah = 0
  511. nexttrack:
  512. cmp al,SectorCount ; see if we need that many
  513. jbe @f
  514. mov al,SectorCount
  515. @@: push Buffer
  516. push ax ; al = count, ah = 0
  517. mov di,ax ; save sector count
  518. push StartSector
  519. push ds
  520. push si
  521. call IoRoutine
  522. add sp,14
  523. cmp ax,0
  524. jz iodone ; ax already 0 for error exit
  525. mov ax,di ; al = #sectors we just read, ah = 0
  526. add StartSectorl,ax ; adjust start sector
  527. adc StartSectorh,0
  528. sub SectorCount,al ; adjust sector count
  529. jz iodone ; ax already non-0 for success return
  530. ;
  531. ; To avoid segment wraps, we'll do arithmetic on the segment
  532. ; instead of the offset. The maximum number of sectors per track
  533. ; is 3fh. Each sector is 200h bytes, which expressed as the offset
  534. ; to the next segment is 20h = 2^5. Thus shifting the sector count
  535. ; left by 5 yields a result between 20h and 7e0h, which we add
  536. ; to the segment of the transfer address.
  537. ;
  538. ; Note that at this point ah = 0.
  539. ;
  540. shl ax,5
  541. add Bufferh,ax
  542. mov al,[si].Int13SectorsPerTrack
  543. cbw ; ax = whole track for next read
  544. jmp short nexttrack
  545. iodone:
  546. pop di
  547. pop si
  548. pop bx
  549. pop es
  550. pop ds
  551. leave
  552. retf
  553. Int13DiskIo endp
  554. ;++
  555. ;
  556. ; ULONG
  557. ; _far
  558. ; pGetExtendedInt13SectorCount(
  559. ; IN BYTE Int13Unit
  560. ; );
  561. ;
  562. ; Routine Description:
  563. ;
  564. ; This routine determines the number of sectors available on an int13
  565. ; disk via extended int13 services.
  566. ;
  567. ; Arguments:
  568. ;
  569. ; Int13Unit - supplies the int13 unit # for the disk.
  570. ;
  571. ; Return Value:
  572. ;
  573. ; 0 - extended int13 services not available for drive.
  574. ; non-0 - number of sectors available for i/o via xint13 on the drive.
  575. ;
  576. ;--
  577. Int13Unit equ byte ptr [bp+6]
  578. pGetExtendedInt13SectorCount proc far
  579. push bp
  580. mov bp,sp
  581. sub sp,26
  582. push ds
  583. push es
  584. push bx
  585. push si
  586. push di
  587. ;
  588. ; See if xint13 is disabled for this unit.
  589. ;
  590. push DGROUP
  591. pop ds
  592. mov si,OFFSET DGROUP:xInt13DisableTable
  593. mov al,Int13Unit
  594. and al,7fh
  595. cbw ; ah = 0
  596. mov bx,ax ; bh = 0
  597. and al,7 ; al = bit offset within byte
  598. shr bl,3 ; bx = offset to byte
  599. bt [si+bx],al ; see if disabled bit set
  600. jc notpresent ; bit set, don't use xint13
  601. ;
  602. ; check extensions present
  603. ;
  604. mov ah,41h
  605. mov bx,55aah
  606. mov dl,Int13Unit
  607. int 13h
  608. jc notpresent
  609. cmp bx,0aa55h
  610. jne notpresent
  611. test cx,1
  612. jz notpresent
  613. ;
  614. ; now we think the extensions are present, go get
  615. ; extended geometry. Note that there are plenty of
  616. ; broken BIOSes out there that will return success to this
  617. ; call even though they don't really support extended int13.
  618. ; So we zero out the buffer ourselves first. If the BIOS
  619. ; doesn't fill the buffer the extended sector count will
  620. ; be returned as zero, which is what we want.
  621. ;
  622. mov ax,ss
  623. mov ds,ax
  624. mov es,ax
  625. lea di,[bp-24] ; don't bother with first word (size)
  626. xor ax,ax
  627. mov cx,12 ; 24 bytes
  628. cld
  629. rep stosw
  630. lea si,[bp-26]
  631. mov word ptr [si],26 ; set up size of info buffer
  632. mov ah,48h
  633. mov dl,Int13Unit
  634. int 13h
  635. jc notpresent
  636. ;
  637. ; OK, everything worked, return sector count.
  638. ;
  639. mov ax,[bp-10]
  640. mov dx,[bp-8]
  641. jmp short xdone
  642. notpresent:
  643. xor ax,ax
  644. mov dx,ax
  645. xdone:
  646. pop di
  647. pop si
  648. pop bx
  649. pop es
  650. pop ds
  651. leave
  652. ret
  653. pGetExtendedInt13SectorCount endp
  654. ;++
  655. ;
  656. ; VOID
  657. ; _far
  658. ; DisableExtendedInt13(
  659. ; IN BYTE Int13Unit OPTIONAL
  660. ; );
  661. ;
  662. ; Routine Description:
  663. ;
  664. ; This routine disables use of extended int13 services on a particular
  665. ; int13 disk unit, or for all int13 disk units. This works by forcing
  666. ; the extended sector count to 0, which in a chain reaction ensures
  667. ; that no one will ever invoke an xint13 service for that unit.
  668. ;
  669. ; This routine MUST be called before InitializeDiskList or it will
  670. ; have no effect!
  671. ;
  672. ; Arguments:
  673. ;
  674. ; Int13Unit - supplies the int13 unit # on which to disable xint13.
  675. ; (The high bit is assumed set and ignored.) If this value
  676. ; is 0, xint13 is disabled for all drives.
  677. ;
  678. ; Return Value:
  679. ;
  680. ; None.
  681. ;
  682. ;--
  683. Int13Unit equ byte ptr [bp+6]
  684. public _DisableExtendedInt13
  685. _DisableExtendedInt13 proc far
  686. push bp
  687. mov bp,sp
  688. push es
  689. push bx
  690. push di
  691. ;
  692. ; Address the xint13 disabled list table.
  693. ;
  694. push DGROUP
  695. pop es
  696. mov di,OFFSET DGROUP:xInt13DisableTable
  697. ;
  698. ; See if we're supposed to disable for all disks.
  699. ;
  700. mov al,Int13Unit
  701. cmp al,0
  702. jz allunits
  703. ;
  704. ; One unit only, take care of it here.
  705. ;
  706. and al,7fh
  707. cbw ; ah = 0
  708. mov bx,ax ; bh = 0
  709. and al,7 ; al = bit offset within byte
  710. shr bl,3 ; bx = offset to byte
  711. bts es:[di+bx],al
  712. jmp dxidone
  713. allunits:
  714. ;
  715. ; Set all bits in the table to 1
  716. ;
  717. cbw ; ax = 0
  718. dec ax ; ax = ff
  719. mov cx,8 ; 8 words = 16 bytes = 128 bits
  720. cld
  721. rep stosw
  722. dxidone:
  723. pop di
  724. pop bx
  725. pop es
  726. leave
  727. ret
  728. _DisableExtendedInt13 endp
  729. ;++
  730. ;
  731. ; VOID
  732. ; _far
  733. ; GetInt13DiskInfo(
  734. ; IN FPINT13_DISK_INFO DiskRecord,
  735. ; OUT FPBYTE Int13UnitNumber,
  736. ; OUT FPBYTE SectorsPerTrack,
  737. ; OUT FPUSHORT Heads,
  738. ; OUT FPUSHORT Cylinders,
  739. ; OUT FPULONG ExtendedSectorCount
  740. ; );
  741. ;
  742. ; Routine Description:
  743. ;
  744. ; These routines fetches information about a disk.
  745. ;
  746. ; Arguments:
  747. ;
  748. ; Return Value:
  749. ;
  750. ; None.
  751. ;
  752. ;--
  753. DiskRecord equ dword ptr [bp+6]
  754. Int13UnitNumber equ dword ptr [bp+10]
  755. SectorsPerTrack equ dword ptr [bp+14]
  756. Heads equ dword ptr [bp+18]
  757. Cylinders equ dword ptr [bp+22]
  758. ExtendedSecCnt equ dword ptr [bp+26]
  759. public GetInt13DiskInfo
  760. GetInt13DiskInfo proc far
  761. push bp
  762. mov bp,sp
  763. push ds
  764. push es
  765. push si
  766. push di
  767. lds si,DiskRecord
  768. add si,Int13DiskUnit
  769. cld
  770. les di,Int13UnitNumber
  771. movsb
  772. .errnz (Int13SectorsPerTrack - Int13DiskUnit) - 1
  773. les di,SectorsPerTrack
  774. movsb
  775. .errnz (Int13Heads - Int13SectorsPerTrack) - 1
  776. les di,Heads
  777. movsw
  778. .errnz (Int13Cylinders - Int13Heads) - 2
  779. les di,Cylinders
  780. movsw
  781. .errnz (Int13xSectorCountl - Int13Cylinders) - 2
  782. les di,ExtendedSecCnt
  783. movsw
  784. movsw
  785. pop di
  786. pop si
  787. pop es
  788. pop ds
  789. leave
  790. retf
  791. GetInt13DiskInfo endp
  792. end