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

📄 ns36x.asm

📁 X86 GX1 BOOTLOAD代码 ,支持WINCE操作系统!
💻 ASM
字号:
;**************************************************************************
;*
;*  NS36X.ASM
;*
;*  Copyright (c) 1999 National Semiconductor Corporation.
;*  All Rights Reserved.
;*
;*  Function:
;*    LPC 36X family Super I/O configuration
;*
;*  $Revision:: 2   $
;*
;**************************************************************************

	.486P

	INCLUDE DEF.INC
	INCLUDE MACROS.INC
	INCLUDE PORT80.INC
	INCLUDE MPC.inc
	INCLUDE NSSIO.inc
	INCLUDE OPTIONS.inc
	INCLUDE strings.inc
	INCLUDE BDCFG.INC
	INCLUDE	NVRAMTOK.INC

INSTALL_NSSIO NS36X

NSSIO_INIT_S	STRUCT	1
index	db	?			; index
token	dw	?			; token or 0 
val	db	?			; shift factor or value if token = 0
					; this is number of bytes to shift
NSSIO_INIT_S	ends


_TEXT SEGMENT PUBLIC use16 'CODE'

	EXTERN	GetTransNVRAM:NEAR

;************************************************************
; translate table for translating
; mvram entries into real working values
;************************************************************
LPCSIOTransTable	LABEL NVRAMTransStruct
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_DIS,0h>  ; disabled
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_378,01000378h>	; 378
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_278,01000278h>	; 278
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_3BC,010003BCh>	; 3BC
	
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_MODE,TVALUE_LPT_MODE_SPP,  00000002h>	; SPP
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_MODE,TVALUE_LPT_MODE_PS2,  00000022h>	; PS/2 BI-DIR
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_MODE,TVALUE_LPT_MODE_EPP17,00000042h>	; EPP 1.7
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_MODE,TVALUE_LPT_MODE_EPP19,00000062h>	; EPP 1.9
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_MODE,TVALUE_LPT_MODE_ECP,  000000F2h>	; ECP
	
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_DIS,0>  ; disabled
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_3F8,010403f8h>  ; 3f8,4
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_2F8,010302f8h>  ; 2f8,3
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_3E8,010703e8h>  ; 3e8,4
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_2E8,010a02e8h>  ; 2e8,3
	
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_DIS,0>  ; disabled
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_3F8,010403f8h>  ; 3f8,4
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_2F8,010302f8h>  ; 2f8,3
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_3E8,010703e8h>  ; 3e8,4
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_2E8,010a02e8h>  ; 2e8,3

	NVRAMTransStruct	<0,0,0,0>  ; end of table

LPCBAR1TransTable	LABEL NVRAMTransStruct
;									mask is reg 1 0 10 14 values	
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_DIS,0>  ; disabled
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_3F8,00100200h>  ; irq 4,serial 0,3f8
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_2F8,00080204h>  ; 2f8,3
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_3E8,0080021Ch>  ; 3e8,7
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART1,TVALUE_UART_CONFIG_2E8,04000214h>  ; 2e8,10
	
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_DIS,0>  ; disabled
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_3F8,00100400h>  ; 3f8,4
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_2F8,00080420h>  ; 2f8,3
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_3E8,008004e0h>  ; 3e8,7
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_UART2,TVALUE_UART_CONFIG_2E8,040004a0h>  ; 2e8,10
	
;									mask is reg  10 14 values	
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_DIS,0h>  ; disabled
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_378,00000100h>	; 378
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_278,00000101h>	; 278
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_PORT,TVALUE_LPT_PORT_3BC,00000102h>	; 3BC
	
; lpt irq 								mask reg is reg 1/0 bits
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_IRQ,0,00000000h>  ; disabled
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_IRQ,5,00000020h>  ; 5
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_IRQ,7,00000080h>  ; 7
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_IRQ,9,00000200h>  ; 9
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_IRQ,10,00000400h>  ; 10
	NVRAMTransStruct	<MEDIA_ANY,TOKEN_LPC_LPT_IRQ,11,00000800h>  ; 11
	
	NVRAMTransStruct	<0,0,0,0>  ; end of table



NSLPCSIO_INIT_TABLE:
	NSSIO_INIT_S	<NSSIO_CFG3,0, 03h>	; Enable SCL/SDA, GA20, KBRST pins

	NSSIO_INIT_S	<NSSIO_LOGICAL_DEVICE_NUMBER,0, NSSIO_FDD_DEVICE>	; Select the FDC device
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 0>				; Disable it
	NSSIO_INIT_S	<NSSIO_OPTION_REG0,0, 24h>			; Set DENSEL & PC-AT mode
	NSSIO_INIT_S	<NSSIO_INTERRUPT_MODE,0, 6>			; Set the interrupt mode
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 1>				; Enable it
	
	NSSIO_INIT_S	<NSSIO_LOGICAL_DEVICE_NUMBER,0, NSSIO_KEYBOARD_DEVICE>	; Select the KBC device
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 0>				; Disable it
	NSSIO_INIT_S	<NSSIO_PRIMARY_INTERRUPT_SELECT,0, 1>		; Set the keyboard interrupt
	NSSIO_INIT_S	<NSSIO_INTERRUPT_MODE,0, 3>			; Set the interrupt mode
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 1>				; Enable it

	NSSIO_INIT_S	<NSSIO_LOGICAL_DEVICE_NUMBER,0, NSSIO_AUX_IO_DEVICE>	; Select the mouse device
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 0>				; Disable it
	NSSIO_INIT_S	<NSSIO_PRIMARY_INTERRUPT_SELECT,0, 0Ch>		; Set the mouse interrupt
	NSSIO_INIT_S	<NSSIO_INTERRUPT_MODE,0, 2>			; Set the interrupt mode
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 1>				; Enable it
	
; LPT port on LPC
	NSSIO_INIT_S	<NSSIO_LOGICAL_DEVICE_NUMBER,0, NSSIO_LPT_DEVICE>	; parallel port
	NSSIO_INIT_S	<NSSIO_ACTIVATE, 0, 0>					; Disable it
	NSSIO_INIT_S	<NSSIO_PRIMARY_BASE_IO_ADDR_HI,TOKEN_LPC_LPT_PORT,1>  	; base address high
	NSSIO_INIT_S	<NSSIO_PRIMARY_BASE_IO_ADDR_LOW,TOKEN_LPC_LPT_PORT,0>	; base address low
	NSSIO_INIT_S	<NSSIO_PRIMARY_INTERRUPT_SELECT,TOKEN_LPC_LPT_IRQ,0>  	; irq
	NSSIO_INIT_S	<NSSIO_DMA_CHANNEL_SELECT,TOKEN_LPC_LPT_DMA,0>  	; dma port
	NSSIO_INIT_S	<NSSIO_OPTION_REG0,TOKEN_LPC_LPT_MODE,0>	    	; mode
; if dowser force lpt to output only regardless of what CMOS contains
IF DOWSER_ON
    ; code to set to output only for dowser
	NSSIO_INIT_S	<NSSIO_OPTION_REG0,0,02h>			; output only
ENDIF
	NSSIO_INIT_S	<NSSIO_ACTIVATE,TOKEN_LPC_LPT_PORT, 3> 		; Enable it

	NSSIO_INIT_S	<NSSIO_LOGICAL_DEVICE_NUMBER,0, NSSIO_UART1_DEVICE>	; Select the UART 1 device
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 0>				; Disable it
	NSSIO_INIT_S	<NSSIO_PRIMARY_BASE_IO_ADDR_HI,TOKEN_LPC_UART1,1>
	NSSIO_INIT_S	<NSSIO_PRIMARY_BASE_IO_ADDR_LOW,TOKEN_LPC_UART1,0>
	NSSIO_INIT_S	<NSSIO_PRIMARY_INTERRUPT_SELECT,TOKEN_LPC_UART1,2>
	NSSIO_INIT_S	<NSSIO_OPTION_REG0,0, 82h>			; Enable bank switching and normal power mode
	NSSIO_INIT_S	<NSSIO_ACTIVATE,TOKEN_LPC_UART1, 3> 		; Enable it

	NSSIO_INIT_S	<NSSIO_LOGICAL_DEVICE_NUMBER,0, NSSIO_UART2_DEVICE>	; Select the UART 2 device
	NSSIO_INIT_S	<NSSIO_ACTIVATE,0, 0>				; Disable it
	NSSIO_INIT_S	<NSSIO_PRIMARY_BASE_IO_ADDR_HI,TOKEN_LPC_UART2,1>
	NSSIO_INIT_S	<NSSIO_PRIMARY_BASE_IO_ADDR_LOW,TOKEN_LPC_UART2,0>
	NSSIO_INIT_S	<NSSIO_PRIMARY_INTERRUPT_SELECT,TOKEN_LPC_UART2,2>
	NSSIO_INIT_S	<NSSIO_OPTION_REG0,0, 82h>			; Enable bank switching and normal power mode
	NSSIO_INIT_S	<NSSIO_ACTIVATE,TOKEN_LPC_UART2, 3> 		; Enable it

	
NSLPCSIO_INIT_COUNT EQU ($ - NSLPCSIO_INIT_TABLE)


NSLPCBAR1_INIT_TABLE:
	NSSIO_INIT_S	<GEODE_REG14,TOKEN_LPC_UART1,0>		; reg 14 - addressing
	NSSIO_INIT_S	<GEODE_REG10,TOKEN_LPC_UART1,1>		; reg 10 - addr enable
	NSSIO_INIT_S	<GEODE_REG00,TOKEN_LPC_UART1,2>  	; reg 0 - irq 0-7
	NSSIO_INIT_S	<GEODE_REG01,TOKEN_LPC_UART1,3>  	; reg 1 - irq 8-15
	
	NSSIO_INIT_S	<GEODE_REG14,TOKEN_LPC_UART2,0>		; reg 14 - addressing
	NSSIO_INIT_S	<GEODE_REG10,TOKEN_LPC_UART2,1>		; reg 10 - addr enable
	NSSIO_INIT_S	<GEODE_REG00,TOKEN_LPC_UART2,2>  	; reg 0 - irq 0-7
	NSSIO_INIT_S	<GEODE_REG01,TOKEN_LPC_UART2,3>  	; reg 1 - irq 8-15

	NSSIO_INIT_S	<GEODE_REG14,TOKEN_LPC_LPT_PORT,0>		; reg 14 - addressing
	NSSIO_INIT_S	<GEODE_REG10,TOKEN_LPC_LPT_PORT,1>		; reg 10 - addr enable
	
	NSSIO_INIT_S	<GEODE_REG00,TOKEN_LPC_LPT_IRQ,0>  	; reg 0 - irq 0-7
	NSSIO_INIT_S	<GEODE_REG01,TOKEN_LPC_LPT_IRQ,1>  	; reg 1 - irq 8-15
	
NSLPCBAR1_INIT_COUNT EQU ($ - NSLPCBAR1_INIT_TABLE)
	
;**************************************************************
; 	killLPC
; 
; 	code to disable the lpc if an lpc sio is not
;	detected
;
;	we do this so things that LPC interferes with
;	(such as legacy USB and fasta20) will work
;
;**************************************************************
KillLPC	PROC	NEAR PUBLIC
; 1st clear all the LPC registers in f0bar1
	mov	cx, 23h			; number of registers
	mov	dx, GEODE_LPC_BASE	; base of f0bar1

LPCbusloop:
	mov	al, 0			; Get value
	out	dx, al			; Write the value to register
	inc	dl			; next one
	loop LPCbusloop

; now clear lpc enable in pmr
	mov	dx, GEODE_CONFIG_BASE	; config registers
	add	dx, GEODE_PMR		; pint to pmr
IF (SCx1xx_PROCESSOR NE 1)
	mov	ebx,NOT ((1 shl 14) or (1 shl 22)) ; mask off 14 & 22
ELSE
	mov	ebx,NOT (1 shl 14)	   	; mask off 14 & 22
ENDIF	
	in	eax,dx			; get pmr
	and	eax,ebx			; mask off lpc
	out	dx,eax
	
	ret
KillLPC	ENDP

;**************************************************************************
;*
;*	LPCsioTest
;*
;*	LPC 36x SuperI/O test and configuration
;*
;*	Entry:
;*	  BX - return address
;*
;*	Exit:
;*	  None
;*
;*	Destroys:
;*	  AX, DX, SI, CX
;*
;**************************************************************************
LPCsioTest PROC NEAR PUBLIC
	push	ebx			; save return address

	mov	ax, LPC
	cmp	ax, 0
	je	noLPCBus		; neither installed, get out.

	mov	cx,3			; try 3 times
tryagain:
	; Attempt to id the SIO and if not identified then put out post code and stop
	mov	dx, NSLPC_SIO_BASE
	mov	al, NSSIO_DEVICE_ID_REG
	out	dx, al
	xor	dx, 1
	in	al, dx
	and	al, 0F0h
	cmp	al, NSSIO_36X_ID
	je	lpcsioPresent
	PORT80	P80_SIO+0Dh	; Indicate invalid SIO response
	loop	tryagain	; trysome more incase it was a fluke

IFDEF LPC_ROM
	; LPC_ROM should be defined in BDCFG.INC if required.
	; See \XPRESS\CPU\SCx2xx\include\BDCFG.INC for an example of how to define
	; LPC_ROM and its associated EQUs.  This is setup this way so that this 
	; code isn't compiled in if the EQU isn't in the system.  It also allows 
	; the EQU to only be defined in the systems that actually need it.
IF LPC_ROM
	; If we have an LPC ROM/DOC in the system we need to leave LPC alive even
	; if we don't find an SIO.  Since we didn't find and SIO we don't need to
	; try and configure it.
	jmp	noLPCBus		; Skip the "kill" no matter what
ENDIF
ENDIF
	call	KillLPC		; disable LPC interface
	jmp	noLPCBus		; done
	
lpcsioPresent:	
 	mov	cx, NSLPCSIO_INIT_COUNT
	lea	si, NSLPCSIO_INIT_TABLE
  
nsloop:
	push	cx			; save count
	mov	cx,cs:[si].NSSIO_INIT_S.token  ; get token
	or	cx,cx			; see if have token
	jz	litvalue		; no - have literal value
; go get the value for the token
	push	si			; save pointer
	lea	si,LPCSIOTransTable
	call	GetTransNVRAM		; get translated NVRAM value
	pop	si			; restore pointer
	jc	point_next		; error *****************
ok:
	mov	cl,cs:[si].NSSIO_INIT_S.val  ; get shift factor
	shl	cl,3			; *8
	jz	writevalue		; don't need shift
	shr	eax,cl			; shift down
	jmp	short writevalue
litvalue:
	mov	al,cs:[si].NSSIO_INIT_S.val	  ; get literal value

writevalue:
	mov	dx, NSLPC_SIO_BASE	; point to base IO address
	mov	ah,cs:[si].NSSIO_INIT_S.index  ; get index
	xchg	al,ah			; save value in ah index to al
	out	dx,al			; write index
	xchg	al,ah			; get value back
	inc	dx			; point to data reg
	out	dx,al			; write data value
point_next:
	add	si,size NSSIO_INIT_S	; point to next table entry
	pop	cx			; restore count
	loop	nsloop			; go do another if we have one

;********************************************************************
; now we have to setup the registers pointer to by f0bar1
; for the lpc this includes irq & address decoding
;********************************************************************
 	mov	cx, NSLPCBAR1_INIT_COUNT
	lea	si, NSLPCBAR1_INIT_TABLE

barloop:
	push	cx			; save count
	mov	cx,cs:[si].NSSIO_INIT_S.token  ; get token
	or	cx,cx			; see if have token
	jz	litvalue_bar		; no - have literal value
; go get the value for the token
	push	si			; save pointer
	lea	si,LPCBAR1TransTable
	call	GetTransNVRAM		; get translated NVRAM value
	pop	si			; restore pointer
	jc	point_next_bar		; error *****************
ok_bar:
	mov	cl,cs:[si].NSSIO_INIT_S.val  ; get shift factor
	shl	cl,3			; *8
	jz	writevalue_bar		; don't need shift
	shr	eax,cl			; shift down
	jmp	short writevalue_bar
litvalue_bar:
	mov	al,cs:[si].NSSIO_INIT_S.val	  ; get literal value

writevalue_bar:
	mov	bl,al			; move value to bl
	mov	dx, GEODE_LPC_BASE	; base port
	add	dl,cs:[si].NSSIO_INIT_S.index  ; get index
	in	al,dx			; read old value
	or	al,bl			; or in new value
	out	dx,al			; write data value
point_next_bar:
	add	si,size NSSIO_INIT_S	; point to next table entry
	pop	cx			; restore count
	loop	barloop			; go do another if we have one

noLPCBus:
	pop	ebx			; restore return address
	jmp	bx
LPCsioTest ENDP




_TEXT ENDS

	END

⌨️ 快捷键说明

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