source: xtideuniversalbios/trunk/XTIDE_Universal_BIOS/Src/Device/Serial/SerialCommand.asm @ 621

Last change on this file since 621 was 621, checked in by krille_n_, 2 years ago

Changes:

  • Fixed three different bugs all causing the boot menu to show drives using IRQs even though the BIOS had been built without MODULE_IRQ.
  • Fixed two bugs in XTIDECFG where loading a BIOS from file and then loading the old settings from EEPROM would
    • overwrite ROMVARS.wFlags in the loaded BIOS file (in RAM). The possibly resulting mismatch of module flags could make it impossible to change settings for modules included in the BIOS or allow changing settings for modules not included in the BIOS.
    • not copy the color theme over to the loaded BIOS.
  • Also fixed two very minor bugs in XTIDECFG in BiosFile_LoadFileFromDSSItoRamBuffer and BiosFile_SaveRamBufferToFileInDSSI where the error handling in these routines would close whatever file handle that happened to match the error code returned by DOS in AX.
  • Made significant changes to the new flash ROM programming routines to reduce the size. Also fixed a minor bug that would cause the second verification to be skipped and return success when programming a 64 KB block of data.
  • Changed the custom BIOS build file names to the 8.3 format.
  • Changed some help strings in XTIDECFG to clarify things.
  • Other minor optimizations and fixes.
File size: 8.2 KB
RevLine 
[150]1; Project name  :   XTIDE Universal BIOS
2; Description   :   Serial Device Command functions.
3
[376]4;
[526]5; XTIDE Universal BIOS and Associated Tools
6; Copyright (C) 2009-2010 by Tomi Tilli, 2011-2013 by XTIDE Universal BIOS Team.
[376]7;
8; This program is free software; you can redistribute it and/or modify
9; it under the terms of the GNU General Public License as published by
10; the Free Software Foundation; either version 2 of the License, or
11; (at your option) any later version.
[526]12;
[376]13; This program is distributed in the hope that it will be useful,
14; but WITHOUT ANY WARRANTY; without even the implied warranty of
15; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
[526]16; GNU General Public License for more details.
[376]17; Visit http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
[526]18;
[376]19
[150]20; Section containing code
21SECTION .text
22
[292]23%define SERIALSERVER_AH_ALREADY_HAS_COMMAND_BYTE
[526]24%define SERIALSERVER_NO_ZERO_SECTOR_COUNTS
[292]25
[150]26;--------------------------------------------------------------------
[179]27; SerialCommand_OutputWithParameters
[150]28;   Parameters:
[179]29;       BH:     Non-zero if 48-bit addressing used
[567]30;               (ignored at present as 48-bit addressing is not supported)
[179]31;       BL:     IDE Status Register bit to poll after command
[567]32;               (ignored at present, since there is no IDE status register to poll)
[179]33;       ES:SI:  Ptr to buffer (for data transfer commands)
34;       DS:DI:  Ptr to DPT (in RAMVARS segment)
35;       SS:BP:  Ptr to IDEREGS_AND_INTPACK
[150]36;   Returns:
37;       AH:     INT 13h Error Code
[258]38;       CX:     Number of successfully transferred sectors (for transfer commands)
[150]39;       CF:     Cleared if success, Set if error
40;   Corrupts registers:
[179]41;       AL, BX, CX, DX, (ES:SI for data transfer commands)
[150]42;--------------------------------------------------------------------
43ALIGN JUMP_ALIGN
[179]44SerialCommand_OutputWithParameters:
[601]45    mov     ah, SerialServer_Command_Read
46    mov     al, [bp+IDEPACK.bCommand]
[181]47
[601]48    cmp     al, 20h                         ; Read Sectors IDE command
49    je      SHORT .readOrWrite
50    inc     ah                              ; now SerialServer_Protocol_Write
51    cmp     al, 30h                         ; Write Sectors IDE command
52    je      SHORT .readOrWrite
[181]53
[179]54;  all other commands return success
55;  including function 0ech which should return drive information, this is handled with the identify functions
[216]56;
[601]57    xor     ah, ah                          ;  also clears carry
58    ret
[181]59
60.readOrWrite:
[601]61    mov     [bp+IDEPACK.bFeatures], ah      ; store protocol command
[538]62%ifdef USE_AT
[601]63    mov     dh, [bp+IDEPACK.bSectorCount]
[538]64%endif
[601]65    call    IdeTransfer_NormalizePointerInESSI
[538]66%ifdef USE_AT
[601]67    jnc     SHORT .PointerNormalizationWasSuccessful
68    xor     cx, cx                          ; Nothing transferred
69    stc
70    ret
[558]71.PointerNormalizationWasSuccessful:
[538]72%endif
[526]73
[601]74    mov     dx, [di+DPT_SERIAL.wSerialPortAndBaud]
[489]75; fall through to SerialCommand_FallThroughToSerialServer_SendReceive
[526]76
[292]77ALIGN JUMP_ALIGN
[526]78SerialCommand_FallThroughToSerialServer_SendReceive:
[489]79; fall through to SerialServer_SendReceive
[292]80%include "SerialServer.asm"
[181]81
[526]82%ifndef CHECK_FOR_UNUSED_ENTRYPOINTS
[334]83    %if SerialCommand_FallThroughToSerialServer_SendReceive <> SerialServer_SendReceive
84        %error "SerialServer_SendReceive must be the first routine at the top of SerialServer.asm in the Assembly_Library"
85    %endif
[292]86%endif
87
[526]88ALIGN JUMP_ALIGN
89SerialCommand_ReturnError:
[601]90    stc
91    ret
[292]92
[150]93;--------------------------------------------------------------------
[179]94; SerialCommand_IdentifyDeviceToBufferInESSIwithDriveSelectByteInBH
95;   Parameters:
96;       BH:     Drive Select byte for Drive and Head Select Register
97;       DS:     Segment to RAMVARS
98;       ES:SI:  Ptr to buffer to receive 512-byte IDE Information
99;       CS:BP:  Ptr to IDEVARS
100;   Returns:
101;       CF:     Cleared if success, Set if error
102;   Corrupts registers:
103;       AL, BL, CX, DX, SI, DI, ES
104;--------------------------------------------------------------------
105ALIGN JUMP_ALIGN
106SerialCommand_IdentifyDeviceToBufferInESSIwithDriveSelectByteInBH:
[203]107;
[223]108; To improve boot time, we do our best to avoid looking for slave serial drives when we already know the results
109; from the looking for a master.  This is particularly true when doing a COM port scan, as we will end up running
110; through all the COM ports and baud rates a second time.
[203]111;
[223]112; But drive detection isn't the only case - we also need to get the right drive when called on int13h/25h.
[203]113;
114; The decision tree:
115;
116;    Master:
[234]117;          wSerialPortAndBaud Non-Zero:           -> Continue with wSerialPortAndBaud (1)
118;          wSerialPortAndBaud Zero:
[567]119;              previous serial drive not found:   -> Scan (2)
120;              previous serial drive found:       -> Continue with previous serial drive info (3)
[223]121;
[203]122;    Slave:
[234]123;          wSerialPortAndBaud Non-Zero:
[567]124;              previous serial drive not found:   -> Error - Not Found (4)
[242]125;              previous serial drive found:       -> Continue with wSerialPackedAndBaud (5)
[567]126;          wSerialPortAndBaud Zero:
127;              previous serial drive not found:   -> Error - Not Found (4)
[234]128;              previous serial drive found:       -> Continue with previous serial drive info (6)
[203]129;
[223]130; (1) This was a port/baud that was explicitly set with the configurator.  In the drive detection case, as this
[234]131;     is the Master, we are checking out a new controller, and so don't care if we already have a serial drive.
[203]132;     And as with the int13h/25h case, we just go off and get the needed information using the user's setting.
[223]133; (2) We are using the special .ideVarsSerialAuto structure.  During drive detection, we would only be here
[242]134;     if we hadn't already seen a serial drive (since we only scan if no explicit drives are set),
[234]135;     so we go off to scan.
[223]136; (3) We are using the special .ideVarsSerialAuto structure.  We won't get here during drive detection, but
[203]137;     we might get here on an int13h/25h call.  If we have scanned COM drives, they are the ONLY serial drives
[234]138;     in use, and so we use the values from the previously seen serial drive DPT.
[223]139; (4) No master has been found yet, therefore no slave should be found.  Avoiding the slave reduces boot time,
[203]140;     especially in the full COM port scan case.  Note that this is different from the hardware IDE, where we
141;     will scan for a slave even if a master is not present.  Note that if ANY master had been previously found,
[223]142;     we will do the slave scan, which isn't harmful, it just wastes time.  But the most common case (by a wide
[203]143;     margin) will be just one serial controller.
144; (5) A COM port scan for a master had been previously completed, and a drive was found.  In a multiple serial
[223]145;     controller scenario being called with int13h/25h, we need to use the value in bSerialPackedPortAndBaud
[203]146;     to make sure we get the proper drive.
[223]147; (6) A COM port scan for a master had been previously completed, and a drive was found.  We would only get here
148;     if no serial drive was explicitly set by the user in the configurator or that drive had not been found.
149;     Instead of performing the full COM port scan for the slave, use the port/baud value stored during the
[203]150;     master scan.
[223]151;
[601]152    mov     dx, [cs:bp+IDEVARS.wSerialPortAndBaud]
153    xor     ax, ax
[526]154
[601]155    push    si
[621]156    call    FindDPT_ToDSDIforSerialDevice   ; Preserves AX
[601]157    pop     si
[258]158%ifdef MODULE_SERIAL_FLOPPY
[601]159    jnc     SHORT .founddpt
[258]160;
161; If not found above with FindDPT_ToDSDIforSerialDevice, DI will point to the DPT after the last hard disk DPT
[277]162; So, if there was a previously found floppy disk, DI will point to that DPT and we use that value for the slave.
[258]163;
[621]164    cmp     [RAMVARS.xlateVars+XLATEVARS.bFlopCntAndFirst], al  ; Zero?
[601]165    je      SHORT .notfounddpt
[258]166.founddpt:
167%else
[601]168    jc      SHORT .notfounddpt
[258]169%endif
[601]170    mov     ax, [di+DPT_SERIAL.wSerialPortAndBaud]
[242]171.notfounddpt:
[601]172    test    bh, FLG_DRVNHEAD_DRV
173    jz      SHORT .master
[223]174
[601]175    test    ax, ax                          ; Take care of the case that is different between master and slave.
176    jz      SHORT SerialCommand_ReturnError
[179]177
[203]178; fall-through
[223]179.master:
[601]180    test    dx, dx
181    jnz     SHORT .identifyDeviceInDX
[179]182
[601]183    xchg    dx, ax                          ;  move ax to dx (move previously found serial drive to dx, could be zero)
[223]184
[292]185.identifyDeviceInDX:
[489]186; fall through to SerialCommand_FallThroughToSerialServerScan_ScanForServer
[526]187
[292]188ALIGN JUMP_ALIGN
[489]189SerialCommand_FallThroughToSerialServerScan_ScanForServer:
190; fall through to SerialServerScan_ScanForServer
[292]191%include "SerialServerScan.asm"
192
[526]193%ifndef CHECK_FOR_UNUSED_ENTRYPOINTS
[334]194    %if SerialCommand_FallThroughToSerialServerScan_ScanForServer <> SerialServerScan_ScanForServer
195        %error "SerialServerScan_ScanForServer must be the first routine at the top of SerialServerScan.asm in the Assembly_Library"
196    %endif
197%endif
[292]198
Note: See TracBrowser for help on using the repository browser.