📄 ohci.asm
字号:
and (OHCI_ED PTR [di]).Control, (NOT ED_SKIP_TDQ)
ENDIF
pop edi
; Set the periodic start time = 2A27h (10% off from HcFmInterval-2EDFh)
USBPORT_DWORD_WRITE_MEM si, OHCI_PERIODIC_START, 2A27h
; Capture the HC IRQ to point to the common IRQ handler
; SI HCStruc pointer
call USBCaptureHCInterrupt
; Program chipset to enable USB interrupts
mov bx, (HCStruc PTR [si]).wBusDevFuncNum
mov ax, ((USB_ENABLE_INTERRUPT SHL 8) + USB_OHCI)
call USBPort_ProgramHardwareInterrupt
; Set the operational bit in the host controller so that power can be applied
; to the ports.
USBPORT_DWORD_WRITE_MEM si, OHCI_CONTROL_REG, USBOPERATIONAL ; Start HC
; Enable global port power so that new devices can be detected.
USBPORT_DWORD_WRITE_MEM si, OHCI_RH_STATUS, SET_GLOBAL_POWER ; First enable global power
; Set the HcFrameInterval register
USBPORT_DWORD_READ_MEM si, OHCI_FRAME_REMAINING ; Read HcFmRemaining register
; FSLargestDataPacket = (FrameInterval-210) * 6/7 ==> 2778h
; where FrameInterval = 2EDFh
USBPORT_DWORD_WRITE_MEM si, OHCI_FRAME_INTERVAL, 27782EDFh
; Start the host controller for control list only (no periodic list)
USBPORT_DWORD_WRITE_MEM si, OHCI_CONTROL_REG, (CONTROL_LIST_ENABLE OR BULK_LIST_ENABLE OR USBOPERATIONAL)
; Check whether enumeration is already began
cmp bEnumFlag, TRUE
je OST_SkipPortEnumeration ; Yes. Skip enumerating now
; Set enumeration flag and avoid hub port enumeration
mov bEnumFlag, TRUE
; Check the root hub ports to see if a device is connected. If so, then
; call UsbHubPortChange to handle the attachment of a new device.
mov dl, 1 ;CL will count through port numbers
mov ebx, OHCI_RH_PORT1_STATUS;DX will count through port regs
mov dh, (HCStruc PTR [si]).bHCNumber
or dh, BIT7 ; Indicate as root hub
InitRootHubNextPort:
; Enable port power
USBPORT_DWORD_WRITE_MEM si, ebx, SET_PORT_POWER ; Enable individual port's power
; Delay to make sure the power to the port is stabilised
mov ax, ((10 * 1000) / 15) ; 10ms delay
call USBMisc_FixedDelay
; DH HC number
; DL port number
; SI HCStruc pointer
call USBCheckPortChange
USBPORT_DWORD_RESET_MEM si, ebx, 0FFFFh
add bx, 4 ;BX = next root hub status port
inc dl ;CL = next port number
cmp dl, (HCStruc PTR [si]).bNumPorts
jbe InitRootHubNextPort ;Br if still more ports to check
; Reset enumeration flag and enable hub enumeration
mov bEnumFlag, FALSE
OST_SkipPortEnumeration:
; Enable interrupts from the host controller
; Enable SOF, WDH, RHSC interrupts
USBPORT_DWORD_WRITE_MEM si, OHCI_INTERRUPT_ENABLE, \
MASTER_INTERRUPT_ENABLE OR WRITEBACK_DONEHEAD_ENABLE \
OR RH_STATUS_CHANGE_ENABLE OR OWNERSHIP_CHANGE_ENABLE
; Start the host controller for periodic list and control list.
IF MKF_USB_MODE NE 2 ; IRQ mode or IRQ-SMI Mode
USBPORT_DWORD_WRITE_MEM si, OHCI_CONTROL_REG, \
PERIODIC_LIST_ENABLE OR CONTROL_LIST_ENABLE \
OR BULK_LIST_ENABLE OR USBOPERATIONAL
ELSE
USBPORT_DWORD_WRITE_MEM si, OHCI_CONTROL_REG, \
PERIODIC_LIST_ENABLE OR CONTROL_LIST_ENABLE \
OR BULK_LIST_ENABLE OR USBOPERATIONAL OR INTERRUPT_ROUTING
ENDIF
; Set the HC state to running
or (HCStruc PTR [si]).bHCFlag, HC_STATE_RUNNING
; Take 256 Bytes from the data segment
mov eax, OHCI_DATA_AREA_SIZE
jmp SHORT OST_Exit
OST_ErrorExit:
; Free all allocated structure
; SI HCStruc pointer
call OHCI_FreeAllStruc
xor eax, eax
OST_Exit:
pop edi
pop si
pop dx
pop cx
pop ebx
pop fs
ret
OHCI_Start ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure: OHCI_EnumeratePorts
;
; Description: This function enumerates the HC ports for devices
;
; Input: SI Host controller's HCStruc structure
; DS USB_DATA AREA
;
; Output: None
;
; Modified: Nothing
;
; Referrals: None
;
; Notes: This function Mainly used in EHCI to switch the ownership from
; companion controller to EHCI controller. In UHCi and OHCI it has
; no code, needed only for the API consistency.
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>
OHCI_EnumeratePorts PROC NEAR SYSCALL PUBLIC
ret
OHCI_EnumeratePorts ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure: OHCI_EnablePortTrapping
;
; Description: This function enables the port 60h/64h emulation for OHCI
;
; Input: SI Host controller's HCStruc structure
; DS USB data area
;
; Output: None
;
; Modified: Nothing
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>
OHCI_EnablePortTrapping PROC NEAR SYSCALL PUBLIC
IF (MKF_USB_MODE EQ 2) AND (MKF_USB_KBC_EMULATION)
push ax
push ebx
push dx
; Set FS:EDI to the mem base pointer
SET_FS_EDI
; Enable the port 60h/64h trapping SMI
test dUSBInitFlag, USB_PORT_TRAPPING_BIT
jz OEPT_SkipPortTrapping
; Check the presence of port 60h/64h emulation support in the HC
; Read the HCRevision register
USBPORT_DWORD_READ_MEM si, OHCI_REVISION_REG
test eax, BIT8
jnz OEPT_EnableTrapping
; Not supported by the HC. Post an error message.
mov ax, ERRUSB_OHCI_EMUL_NOT_SUPPORTED
call USBLogError
jmp SHORT OEPT_SkipPortTrapping
OEPT_EnableTrapping:
; Enable the emulation hardware
USBPORT_DWORD_WRITE_MEM si, OHCI_HCE_CONTROL, HCE_CNTRL_EMULATION_ENABLE+HCE_CNTRL_CHARACTER_PENDING
IF MKF_USB_DEV_KBD
push ds
push 0
pop ds
mov al, DS:[417h] ; KB LED status
pop ds
and al, 70h
shr al, 1
test al, 08h
jz UST_Continue0
xor al, 48h
UST_Continue0:
and bNonUSBKBShiftKeyStatus, NOT (BIT4+BIT5+BIT6)
or bNonUSBKBShiftKeyStatus, al
ENDIF
OEPT_SkipPortTrapping:
RESTORE_FS_EDI
pop dx
pop ebx
pop ax
ENDIF
ret
OHCI_EnablePortTrapping ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure: OHCI_CheckHCStatus
;
; Description: This function checks whether the host controller is still
; under BIOS
;
; Input: SI Host controller's HCStruc structure
; DS USB data area
;
; Output: ZR If the control is with the BIOS
; NZ If the control is not with the BIOS
;
; Modified: Nothing
;
; Referrals: HCDHeader, HCStruc
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>
OHCI_CheckHCStatus PROC NEAR
push eax
SET_FS_EDI
; Check whether the controller is still under BIOS control
; Read the base address of the Periodic Frame List to the OHCI HCCA
; register and compare with stored value
USBPORT_DWORD_READ_MEM si, OHCI_HCCA_REG
and eax, (NOT 0FFh)
RESTORE_FS_EDI
cmp eax, (HCStruc PTR [si]).dHcdDataArea
; ZR On success (Control is with BIOS)
; NZ On error
pop eax
ret
OHCI_CheckHCStatus ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure: OHCI_Stop
;
; Description: This function stops the OHCI controller.
;
; Input: SI Host controller's HCStruc structure
; DS USB Data Area
;
; Output: None
;
; Modified: Nothing
;
; Referrals: None
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>
OHCI_Stop PROC NEAR SYSCALL
push ax
push bx
push dx
; Set FS:EDI to the mem base pointer
SET_FS_EDI
; Disconnect all the devices connected to its ports
mov dl, 1 ; DL will count through port numbers
mov dh, (HCStruc PTR [si]).bHCNumber
or dh, BIT7 ; Indicate as root hub
OS_DisConnectNextPort:
; DH Hub/HC number
; DL Port number
; SI HCStruc pointer
call USBDisconnectDevice
inc dl ;CL = next port number
cmp dl, (HCStruc PTR [si]).bNumPorts
jbe OS_DisConnectNextPort ;Br if still more ports to check
; Reset the host controller
call OHCI_ResetHC ; SI - HCStruc pointer
; Program chipset to disable USB interrupts
mov bx, (HCStruc PTR [si]).wBusDevFuncNum
mov ax, ((USB_DISABLE_INTERRUPT SHL 8) + USB_OHCI)
call USBPort_ProgramHardwareInterrupt
; Clear the frame list pointers
xor eax, eax ; Value to initialize with
call USBMiscInitFrameList ; SI HCStruc pointer
; Free the TDs
call OHCI_FreeAllStruc ; SI HCStruc ptr
; Set the HC state to stopped
and (HCStruc PTR [si]).bHCFlag, NOT HC_STATE_RUNNING
RESTORE_FS_EDI
pop dx
pop bx
pop ax
ret
OHCI_Stop ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure: OHCI_MoveDataArea
;
; Description: This function moves the data area of the host controller
; without restarting the host controller again.
;
; Input: SI Pointer to the HCStruc structure
; EDI 32bit absolute data area address
;
; Output: AX Success/failure
;
; Modified: EAX
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>
OHCI_MoveDataArea PROC NEAR SYSCALL
ret
OHCI_MoveDataArea ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure: OHCI_DisableInterrupts
;
; Description: This function disables the HC interrupts
;
; Input: SI Pointer to the HCStruc structure
; DS USB Data Area
;
; Output: ZR On Error
; NZ On success
;
; Modified: None
;
; Referrals: HCStruc
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>
OHCI_DisableInterrupts PROC NEAR SYSCALL USES EAX
; Set FS:EDI to the mem base pointer
SET_FS_EDI
; Disable interrupt generation (global) bit (Set bit31)
USBPORT_DWORD_WRITE_MEM si, OHCI_INTERRUPT_DISABLE, MASTER_INTERRUPT_ENABLE
; Disable periodic, isochronous, control and bulk list processing
; Reset bits 2 to 5
USBPORT_DWORD_RESET_MEM si, OHCI_CONTROL_REG, (BIT2 + BIT3 + BIT4 + BIT5)
RESTORE_FS_EDI
or sp, sp ; Clear ZR flag
ret
OHCI_DisableInterrupts ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure: OHCI_EnableInterrupts
;
; Description: This function enables the HC interrupts
;
; Input: SI Pointer to the HCStruc structure
; DS USB Data Area
;
; Output: ZR On error
; NZ On success
;
; Modified: None
;
; Referrals: HCStruc
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>
OHCI_EnableInterrupts PROC NEAR SYSCALL USES EAX
SET_FS_EDI
; Enable periodic, control and bulk list processing
; Set bit 2, 4 & 5
USBPORT_DWORD_SET_MEM si, OHCI_CONTROL_REG, (BIT2 + BIT4 + BIT5)
; Enable interrupt generation (global) bit
USBPORT_DWORD_WRITE_MEM si, OHCI_INTERRUPT_ENABLE, MASTER_INTERRUPT_ENABLE
RESTORE_FS_EDI
or sp, sp
ret
OHCI_EnableInterrupts ENDP
;<AMI_PHDR_START>
;----------------------------------------------------------------------------
;
; Procedure: OHCI_ProcessInterrupt
;
; Description: This function is called when the USB interrupt bit is
; set. This function will parse through the TDs and QHs to
; find out completed TDs and call their respective call
; back functions
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -