⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 usb.asm

📁 dos下的USB源码(包括UHCI
💻 ASM
📖 第 1 页 / 共 5 页
字号:
	pop	ds
	mov	eax, DWORD PTR DS:[6Ch]
	pop	ds

; EAX = Current Tick Counter
; EBX = Last Tick Counter when we left SMI

; Check whether we are in the first 5 second of day
	cmp	eax, (5 * 18)
	jb	fUSH_WithinFirst5Sec

; Check whether 5 second had elapsed from last time we left SMI to now
	add	ebx, (5 * 18)
; EBX - Last time + 5 seconds
	cmp	ebx, eax		; Is there any USB SMI in last 5 sec?
	ja	SHORT fUSH_ProcessTimeDone	; Yes ...

fUSH_SetReInitFlag:
; We are getting a USB SMI after 5 or more seconds. Set HC re-initialize
; flag

; Test to see if we are in POST. No need to set this flag in POST
	cmp	USBAcquiredByOS, TRUE
	jne	fUSH_ProcessTimeDone

	mov	bReInitUSB, TRUE
	jmp	SHORT fUSH_ProcessTimeDone

fUSH_WithinFirst5Sec:

; EAX = Current Tick Counter
; EBX = Last Tick Counter when we left SMI

	mov	ecx, 17FE80h
; ECX = Int1A ticks in one day...

	sub	ecx, ebx
; ECX = Int1A ticks left in yesterday...

	mov	ebx, (5 * 18)
; EBX = Int1A ticks in 5 Secs...

	sub	ebx, ecx
; EBX = Highest Current Int1A tick counter possible in 5 sec window
	cmp	ebx, eax		; Are we in 5 sec window?
	ja	SHORT fUSH_SetReInitFlag

fUSH_ProcessTimeDone:

; Give control to all the HCs
	mov	si, OFFSET HCTable
	mov	cx, MKF_USB_MAX_HC

; Save re-init USB flag
	mov	dl, bReInitUSB

UWIH_TryNextHC:

; Restore re-init USB flag. Re-init USB flag will be cleared by
; HC process interrupt routine after service. So we have to
; re-initialize the value for next HC
	mov	bReInitUSB, dl

; Structure found
	mov	bx, (HCStruc PTR [si]).pHCDPointer
	or	bx, bx
	jz	UWIH_PrepareForLoop

; SI - HCStruc pointer
	call	(HCDHEADER PTR cs:[bx]).pHCDProcessInterrupt

; Check for more HCs using same IRQ
UWIH_PrepareForLoop:
	add	si, SIZE HCStruc
	loop	UWIH_TryNextHC

; Disable Re-init flag
	mov	bReInitUSB, FALSE

; Save the time we left the USB SMI
	push	ds
	push	40h
	pop	ds
	mov	eax, dword ptr ds:[6Ch]		; EAX = Current Int1A Tick Counter
	pop	ds

; Store Current Int1A Tick Counter
	mov	dTimeLastInSMI, eax


UWIH_ExitISR:
	popad
	pop	es
	pop	ds
	ret

farUSBSMIHandler		ENDP

ENDIF	; MKF_USB_MODE GE 2

;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure:	USBCheckPortChange
;
; Description:	This routine processes the port status change (like connect,
;		disconnect etc) for the root hub and external hubs
;
; Input: 	DH	USB device address of the hub whose status
;			has changed
;			bit 7	: 1 - Root hub, 0 for other hubs
;			bit 6-0	: Device address of the hub
;		DL	Port number
;		SI	HCStruc of the host controller
;
; Output: 	Nothing
;
; Modified:	Nothing
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>

USBCheckPortChange	PROC NEAR SYSCALL PUBLIC USES AX BX CX DX SI

	LOCAL	bPortStatus:BYTE

; Set look count
	xor	cx, cx

UCPC_ConnectDeviceAgain:

; Get the port status for the hub
	test	dh, BIT7
	jz	UCPC_HubDevice

; Get the status from the root hub
; Call appropriate controller to get the root hub status
; SI - HCStruc pointer
; AL - bPortNum
	mov	al, dl
	push	bx
	mov	bx, (HCStruc PTR [si]).pHCDPointer
	call	(HCDHEADER PTR cs:[bx]).pHCDGetRootHubStatus
	pop	bx
	jmp	SHORT UCPC_CheckStatus

UCPC_HubDevice:

IF	MKF_USB_DEV_HUB
; SI 	HCStruc pointer
	call	USBHub_GetPortStatus
ELSE
	jmp	SHORT UHCPC_PortChangeDone
ENDIF

UCPC_CheckStatus:

	or	al, al
	jz	UHCPC_PortChangeDone
	mov	bPortStatus, al

	cmp	cx, 0
	ja	UCPC_DetNewDev

; Test connect status change flag
	test	al, USB_PORT_STAT_DEV_CONNECT_CHANGED
	jz	UHCPC_PortChangeDone	; If connect status has not changed

; Test device connected status flag
	test	al, USB_PORT_STAT_DEV_CONNECTED
	jz	UHCPC_Disconnect		; If device has been disconnected

UCPC_DetNewDev:

; Check hand over in progress flag
	cmp	bHandOverInProgress, TRUE
	jne	UCPC_ProceedToDetect

; Disable the hub port
; DH	Hub/HC number
; DL	Port number
; SI	HCStruc pointer
	call	USBDisableHubPort
	jmp	SHORT UHCPC_PortChangeDone


UCPC_ProceedToDetect:


; Connect status found
	mov	al, bPortStatus
; DH - Hub address
; DL - Port number
; SI - HCStruc
; AL - Port status
	call	USB_DetectNewDevice
	or	ax, ax
	jz	UCPC_Beep

; Check for get descriptor 8 error
	cmp	ax, USB_ERR_DEV_INIT_GET_DESC_8
	jne	UCPC_Beep	; No beep and exit

; Get descriptor 8 error
; Assume that the device may come back
; Delay for 100ms
	mov	ax, ((100 * 1000) / 15)	; 100ms delay
	call	USBMisc_FixedDelay

	inc	cx
	cmp	cx, 40		; Wait for 4 sec
	jbe	UCPC_ConnectDeviceAgain

; Disable the hub port
; DH	Hub/HC number
; DL	Port number
; SI	HCStruc pointer
	call	USBDisableHubPort

	xor	ax, ax
UCPC_Beep:
	cmp	ax, USB_ERR_DEV_INIT_GET_DESC_200
	ja	UHCPC_PortChangeDone

	or	ax, ax
	jz	UHCPC_PortChangeDone

	xor	ax, ax		; Return with error
; Issue error beep
	mov	bl, 64
	mov	cx, 4000h
	call	USBMisc_SpeakerBeep

	jmp	SHORT UHCPC_PortChangeDone

UHCPC_Disconnect:

; Disconnect device and its children from the port
; DH	Hub/HC number
; DL	Port number
; SI	HCStruc pointer
	call	USBDisconnectDevice

; Issue an error beep indicating that the device is disabled
	mov	bl, 8
	mov	cx, 1000h
	call	USBMisc_SpeakerBeep


UHCPC_PortChangeDone:
	ret
USBCheckPortChange	ENDP

;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure:	USBDisableHubPort
;
; Description:	This routine disables the hub port in the Standard/root hub
;
; Input: 	DH	USB device address of the hub whose status
;			has changed
;			bit 7	: 1 - Root hub, 0 for other hubs
;			bit 6-0	: Device address of the hub
;		DL	Port number
;		SI	HCStruc of the host controller
;
; Output: 	ZR	On error
;		NZ	On success
;
; Modified:	Nothing
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>

USBDisableHubPort	PROC NEAR SYSCALL PUBLIC USES BX SI

; Check for standard/root hub
	test	dh, BIT7
	jz	UDHP_StdHub

; Disable the port in the root hub
; Call appropriate controller to disable the root hub status
	push	bx
	mov	bx, (HCStruc PTR [si]).pHCDPointer
	mov	al, dl
	call	(HCDHEADER PTR cs:[bx]).pHCDDisableRootHub
	pop	bx
	jmp	SHORT UDHP_Exit

UDHP_StdHub:

IF	MKF_USB_DEV_HUB
; DH	Hub/HC number
; DL	Port number
; SI	HCStruc pointer
	call	USBHub_DisablePort
ENDIF

UDHP_Exit:
	ret
USBDisableHubPort	ENDP

;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure:	USBEnableHubPort
;
; Description:	This routine disables the hub port in the Standard/root hub
;
; Input: 	DH	USB device address of the hub whose status
;				has changed
;				bit 7	: 1 - Root hub, 0 for other hubs
;				bit 6-0	: Device address of the hub
;		DL	Port number
;		SI	HCStruc of the host controller
;
; Output: 	AX	0 on error, 0FFFFh on success
;
; Modified:	Nothing
;
; Referrals:
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>

USBEnableHubPort	PROC NEAR SYSCALL PUBLIC USES BX DX SI

; Check for standard/root hub
	test	dh, BIT7
	jz	UEHP_StdHub

; Enable the port in the root hub
; Call appropriate controller to enable the root hub status
	mov	al, dl
; SI	HCStruc pointer
; AL	port number
	mov	bx, (HCStruc PTR [si]).pHCDPointer
	call	(HCDHEADER PTR CS:[bx]).pHCDEnableRootHub
	jmp	SHORT UEHP_Exit

UEHP_StdHub:

IF	MKF_USB_DEV_HUB
; DH	Hub/HC number
; DL	Port number
; SI	HCStruc pointer
	call	USBHub_EnablePort
ENDIF

UEHP_Exit:
	ret
USBEnableHubPort	ENDP

;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure:	USBCheckNonCompliantDevice
;
; Description:	This function checks for non-compliant USB devices by
;		by comparing the device's vendor and device id with
;		the non-compliant device table list and updates the
;		data structures appropriately to support the device.
;
; Input: 	SI	HCStruc pointer
;		BX	Device information structure pointer
;		DI	Pointer to the descriptor structure
;		CX	End offset of the device descriptor
;
; Output: 	None
;
; Modified:	Nothing
;
; Referrals:	MassDeviceInfo, DeviceInfo
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>

USBCheckNonCompliantDevice	PROC NEAR SYSCALL PUBLIC

	push	ax
	push	edx
	push	si

; Get the current device's vendor & device ID
	mov	dx, (DeviceInfo PTR [bx]).wDeviceId
	shl	edx,16
	mov	dx, (DeviceInfo PTR [bx]).wVendorId

; Search the bad device table to get the structure for this device
	mov	si, OFFSET CS:USBBadDeviceTable

UCNCD_Loop:
	cmp	si, OFFSET CS:USBBadDeviceTableEnd
	jae	UCNCD_Exit		; NC, ok configure device

	cmp	edx, DWORD PTR CS:[si]	; Compare with table entry
	je	UCNCD_DeviceFound

; Prepare to check next device
	add	si, SIZE stBadUSBDevice
	jmp	SHORT UCNCD_Loop

UCNCD_DeviceFound:

; Save the incompatibility flag into device info structure
	mov	ax, (stBadUSBDevice PTR CS:[si]).wFlags
	mov	(DeviceInfo PTR [bx]).wIncompatFlags, ax

; Check which fields to update in the interface descriptor

; Check for base class field
	cmp	(stBadUSBDevice PTR CS:[si]).bBaseClass, 0
	jz	UCNCD_CheckSubClass
; Update base class field in the interface descriptor
	mov	al, (stBadUSBDevice PTR CS:[si]).bBaseClass
	mov	(InterfaceDescriptor PTR [di]).bBaseClass, al

UCNCD_CheckSubClass:
; Check for sub class field
	cmp	(stBadUSBDevice PTR CS:[si]).bSubClass, 0
	jz	UCNCD_CheckProtocol
; Update sub class field in the interface descriptor
	mov	al, (stBadUSBDevice PTR CS:[si]).bSubClass
	mov	(InterfaceDescriptor PTR [di]).bSubClass, al

UCNCD_CheckProtocol:
; Check for protocol field
	cmp	(stBadUSBDevice PTR CS:[si]).bProtocol, 0
	jz	UCNCD_Exit
; Update protocol field in the interface descriptor
	mov	al, (stBadUSBDevice PTR CS:[si]).bProtocol
	mov	(InterfaceDescriptor PTR [di]).bProtocol, al

UCNCD_Exit:

	pop	si
	pop	edx
	pop	ax
	ret
USBCheckNonCompliantDevice	ENDP

;<AMI_PHDR_START>
;----------------------------------------------------------------------------
; Procedure:	USBIdentifyAndConfigureDevice
;
; Description:	This routine invokes the device drivers 'check device type'
;		routine and identifies the device type.
;
; Input: 	SI	HCStruc pointer
;		BX	Device information structure pointer
;		DI	Pointer to the descriptor structure
;		CX	End offset of the device descriptor
;
; Output: 	AX	New device info structure, 0 on error
;
; Modified:	AX
;
;----------------------------------------------------------------------------
;<AMI_PHDR_END>

USBIdentifyAndConfigureDevice	PROC NEAR SYSCALL PUBLIC USES BX CX EDX SI DI

	LOCAL	wRetValue:WORD

	xor	edx, edx
; Set return value
	mov	wRetValue, dx

; Check for non-compliant device. If non-compliant device found then
; the descriptor values will get updated depending on the need.
; SI - HCStruc, BX - DevInfo, DI - Pointer to InterfaceDescriptor,
; CX - Pointer to descriptor end
	call	USBCheckNonCompliantDevice

; Check whether to disable the device
	test	(DeviceInfo PTR [bx]).wIncompatFlags, USB_INCMPT_DISABLE_DEVICE
	jnz	UIACD_Exit

; Get the base, sub class & protocol values
	mov	dh, (InterfaceDescriptor PTR [di]).bBaseClass
	mov	dl, (InterfaceDescriptor PTR [di]).bSubClass
	shl	edx, 8
	mov	dl, (InterfaceDescriptor PTR [di]).bProtocol

; Invoke device drivers initialize routine
	mov	si, OFFSET DeviceDriverTable
UIACD_CheckNextDriver:
	push	si

; Check for driver validity
	mov	ax, WORD PTR cs:[si]
	or	ax, ax
	jz	UIACD_DriverInitDone

	mov	si, ax
; Check whether check device type routine is implemented
	cmp	(USB_DEV_HDR PTR cs:[si]).pChkDevType, 0
	je	UIACD_TryNextDriver

; Check whether configure device routine is implemented
	cmp	(USB_DEV_HDR PTR cs:[si]).pCfgDevice, 0
	je	UIACD_TryNextDriver

; Identify the device
; DL+ - Base class

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -