forked from KolibriOS/kolibrios
Fixed bug in network drivers irq handler.
Updated netdrv.inc and pci.inc git-svn-id: svn://kolibrios.org@2935 a494cfbc-eb01-0410-851d-a64ba20cac60
This commit is contained in:
parent
c575a498b5
commit
3e0a804c48
@ -2658,39 +2658,34 @@ int_vortex:
|
||||
align 4
|
||||
int_boomerang:
|
||||
|
||||
DEBUGF 1,"\nIRQ %x Boomerang\n",eax:2
|
||||
DEBUGF 1,"\nBoomerang int\n"
|
||||
|
||||
; find pointer of device wich made IRQ occur
|
||||
|
||||
mov esi, BOOMERANG_LIST
|
||||
mov ecx, [BOOMERANG_DEVICES]
|
||||
|
||||
test ecx, ecx
|
||||
jz .fail
|
||||
jz .nothing
|
||||
mov esi, BOOMERANG_LIST
|
||||
.nextdevice:
|
||||
mov ebx, dword[esi]
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io REG_INT_STATUS
|
||||
in ax, dx
|
||||
test ax, IntLatch
|
||||
test ax, ax
|
||||
jnz .got_it
|
||||
|
||||
.continue:
|
||||
add esi, 4
|
||||
|
||||
test ax , ax
|
||||
jnz .got_it
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
|
||||
.fail:
|
||||
DEBUGF 1,"Failed!\n"
|
||||
.nothing:
|
||||
ret
|
||||
|
||||
.got_it:
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, eax
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, ax
|
||||
push ax
|
||||
|
||||
; disable all INTS
|
||||
|
||||
set_io REG_COMMAND
|
||||
|
@ -831,46 +831,40 @@ transmit:
|
||||
;; Interrupt handler ;;
|
||||
;; ;;
|
||||
;;;;;;;;;;;;;;;;;;;;;;;
|
||||
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
DEBUGF 2,"\nIRQ %x ", eax:2 ; no, you cant replace 'eax:2' with 'al', this must be a bug in FDO
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; Find pointer of device wich made IRQ occur
|
||||
|
||||
mov esi, device_list
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .fail
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, dword [esi]
|
||||
|
||||
; Find reason for IRQ
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io MISR
|
||||
in ax, dx
|
||||
out dx, ax ; send it back to ACK
|
||||
|
||||
DEBUGF 2,"MISR=%x\n", eax:4
|
||||
|
||||
; Check if we are interessed in some of the reasons
|
||||
|
||||
test ax, INT_MASK
|
||||
out dx, ax ; send it back to ACK
|
||||
test ax, ax
|
||||
jnz .got_it
|
||||
|
||||
; If not, try next device
|
||||
|
||||
.continue:
|
||||
add esi, 4
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
|
||||
.fail: ; If no device was found, abort (The irq was probably for a device, not registered to this driver)
|
||||
.nothing: ; If no device was found, abort (The irq was probably for a device, not registered to this driver)
|
||||
ret
|
||||
|
||||
; At this point, test for all possible reasons, and handle accordingly
|
||||
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, ax
|
||||
|
||||
push ax
|
||||
|
||||
test word [esp], RX_FINISH
|
||||
|
@ -735,34 +735,42 @@ transmit:
|
||||
; Interrupt handler
|
||||
;
|
||||
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
DEBUGF 2,"IRQ %x ",eax:2
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; find pointer of device wich made INT occur
|
||||
mov esi, device_list
|
||||
|
||||
mov ecx, [devices]
|
||||
.nextdevice:
|
||||
test ecx, ecx
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io P0_ISR
|
||||
in al, dx
|
||||
|
||||
DEBUGF 2,"isr %x ",eax:2
|
||||
|
||||
test al, ISR_PRX ; packet received ok ?
|
||||
jnz .rx
|
||||
|
||||
test al, al
|
||||
jnz .got_it
|
||||
.continue:
|
||||
add esi, 4
|
||||
|
||||
loop .nextdevice
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
.nothing:
|
||||
ret
|
||||
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, eax:2
|
||||
|
||||
test al, ISR_PRX ; packet received ok ?
|
||||
jz .no_rx
|
||||
|
||||
; looks like we've found a device wich received a packet..
|
||||
.rx:
|
||||
|
||||
stdcall KernelAlloc, ETH_FRAME_LEN ; size doesnt really matter as packet size is smaller then kernel's page size
|
||||
test eax, eax
|
||||
jz .fail_2
|
||||
@ -937,7 +945,10 @@ int_handler:
|
||||
add esp, 14+8
|
||||
.fail_2:
|
||||
DEBUGF 2,"done\n"
|
||||
ret
|
||||
|
||||
.no_rx:
|
||||
|
||||
ret
|
||||
|
||||
|
||||
|
||||
|
@ -739,43 +739,41 @@ transmit:
|
||||
;; Interrupt handler ;;
|
||||
;; ;;
|
||||
;;;;;;;;;;;;;;;;;;;;;;;
|
||||
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
DEBUGF 1,"\nIRQ %x\n", eax:2 ; no, you cant replace 'eax:2' with 'al', this must be a bug in FDO
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; find pointer of device wich made IRQ occur
|
||||
|
||||
mov esi, device_list
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .fail
|
||||
.nextdevice:
|
||||
mov ebx, dword [esi]
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io REG_ISR
|
||||
in ax , dx
|
||||
out dx , ax ; send it back to ACK
|
||||
|
||||
add esi, 4
|
||||
|
||||
test ax , ax
|
||||
in ax, dx
|
||||
out dx, ax ; send it back to ACK
|
||||
test ax, ax
|
||||
jnz .got_it
|
||||
|
||||
.continue:
|
||||
add esi, 4
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
|
||||
.nothing:
|
||||
ret ; If no device was found, abort (The irq was probably for a device, not registered to this driver)
|
||||
|
||||
.got_it:
|
||||
|
||||
; looks like we've found it!
|
||||
|
||||
; Lets found out why the irq occured then..
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, ax
|
||||
|
||||
;----------------------------------------------------
|
||||
; Received packet ok?
|
||||
|
||||
test ax, ISR_ROK
|
||||
jz @f
|
||||
push ax
|
||||
|
@ -1113,33 +1113,32 @@ transmit:
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
DEBUGF 1,"IRQ %x ",eax:2
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; find pointer of device wich made IRQ occur
|
||||
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .fail
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, dword [esi]
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io REG_IntrStatus
|
||||
in ax, dx
|
||||
|
||||
test ax, ax
|
||||
jnz .got_it
|
||||
|
||||
.continue:
|
||||
add esi, 4
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
|
||||
.nothing:
|
||||
ret ; If no device was found, abort (The irq was probably for a device, not registered to this driver)
|
||||
|
||||
.got_it:
|
||||
DEBUGF 1,"IntrStatus = 0x%x\n",ax
|
||||
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, ax
|
||||
|
||||
cmp ax, 0xFFFF ; if so, hardware is no longer present
|
||||
je .fail
|
||||
|
@ -13,17 +13,25 @@
|
||||
|
||||
PCI_HEADER_TYPE = 0x0e ; 8 bit
|
||||
PCI_BASE_ADDRESS_0 = 0x10 ; 32 bit
|
||||
PCI_BASE_ADDRESS_1 = 0x14 ; 32 bits
|
||||
PCI_BASE_ADDRESS_2 = 0x18 ; 32 bits
|
||||
PCI_BASE_ADDRESS_3 = 0x1c ; 32 bits
|
||||
PCI_BASE_ADDRESS_4 = 0x20 ; 32 bits
|
||||
PCI_BASE_ADDRESS_5 = 0x24 ; 32 bits
|
||||
PCI_BASE_ADDRESS_SPACE_IO = 0x01
|
||||
PCI_VENDOR_ID = 0x00 ; 16 bit
|
||||
PCI_BASE_ADDRESS_IO_MASK = 0xFFFFFFFC
|
||||
PCI_BASE_ADDRESS_MEM_MASK = 0xFFFFFFF0
|
||||
|
||||
; PCI programming
|
||||
|
||||
PCI_VENDOR_ID = 0x00 ; 16 bit
|
||||
PCI_DEVICE_ID = 0x02 ; 16 bits
|
||||
PCI_REG_COMMAND = 0x4 ; command register
|
||||
PCI_REG_STATUS = 0x6 ; status register
|
||||
PCI_REVISION_ID = 0x08 ; 8 bits
|
||||
PCI_REG_LATENCY = 0xd ; latency timer register
|
||||
PCI_REG_CAP_PTR = 0x34 ; capabilities pointer
|
||||
PCI_REG_IRQ = 0x3c
|
||||
PCI_REG_CAPABILITY_ID = 0x0 ; capapility ID in pm register block
|
||||
PCI_REG_PM_STATUS = 0x4 ; power management status register
|
||||
PCI_REG_PM_CTRL = 0x4 ; power management control register
|
||||
@ -90,7 +98,6 @@ macro find_mmio32 bus, dev, io {
|
||||
|
||||
.got:
|
||||
mov io, eax
|
||||
|
||||
}
|
||||
|
||||
macro find_irq bus, dev, irq {
|
||||
@ -98,7 +105,7 @@ macro find_irq bus, dev, irq {
|
||||
push eax edx ecx
|
||||
movzx ecx, bus
|
||||
movzx edx, dev
|
||||
stdcall PciRead8, ecx ,edx ,0x3c ; 0x3c is the offset where irq can be found
|
||||
stdcall PciRead8, ecx, edx, PCI_REG_IRQ
|
||||
mov irq, al
|
||||
pop ecx edx eax
|
||||
|
||||
|
@ -1012,40 +1012,33 @@ transmit:
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
DEBUGF 1,"IRQ %x ",eax:2 ; no, you cant replace 'eax:2' with 'al', this must be a bug in FDO
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; find pointer of device wich made IRQ occur
|
||||
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .fail
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, dword [esi]
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io CSR5
|
||||
in eax, dx
|
||||
out dx , eax ; send it back to ACK
|
||||
|
||||
and eax, CSR7_DEFAULT ; int mask
|
||||
out dx, eax ; send it back to ACK
|
||||
test eax, eax
|
||||
jnz .got_it
|
||||
|
||||
.continue:
|
||||
add esi, 4
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
|
||||
.nothing:
|
||||
ret ; If no device was found, abort (The irq was probably for a device, not registered to this driver)
|
||||
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"CSR7: %x ", eax
|
||||
|
||||
; looks like we've found it!
|
||||
|
||||
; Lets found out why the irq occured then..
|
||||
DEBUGF 1,"Device: %x CSR5: %x ", ebx, ax
|
||||
|
||||
;----------------------------------
|
||||
; TX ok?
|
||||
|
@ -682,29 +682,35 @@ transmit:
|
||||
;; Interrupt handler ;;
|
||||
;; ;;
|
||||
;;;;;;;;;;;;;;;;;;;;;;;
|
||||
|
||||
align 4
|
||||
int_handler:
|
||||
DEBUGF 2,"\nIRQ %x\n", eax:2 ; no, you cant replace 'eax:2' with 'al', this must be a bug in FDO
|
||||
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
;-------------------------------------------
|
||||
; Find pointer of device wich made IRQ occur
|
||||
|
||||
mov esi, device_list
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .fail
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, dword [esi]
|
||||
mov ebx, [esi]
|
||||
|
||||
mov edi, [device.mmio_addr]
|
||||
test edi, edi
|
||||
jz .nextdevice
|
||||
|
||||
;--------------------
|
||||
; Get interrupt cause
|
||||
|
||||
mov eax, [edi + REG_ICR]
|
||||
DEBUGF 2,"interrupt cause=%x\n", eax
|
||||
test eax, eax
|
||||
jnz .got_it
|
||||
.continue:
|
||||
add esi, 4
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
.nothing:
|
||||
ret
|
||||
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, eax
|
||||
|
||||
;---------
|
||||
; RX done?
|
||||
|
@ -1099,35 +1099,33 @@ write_mac:
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
DEBUGF 1,"\nIRQ %x\n",eax:2 ; no, you cant replace 'eax:2' with 'al', this must be a bug in FDO
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; find pointer of device wich made IRQ occur
|
||||
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .fail
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, dword [esi]
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io ISR
|
||||
in eax, dx
|
||||
out dx , eax ; send it back to ACK
|
||||
; and eax, ; int mask
|
||||
out dx, eax ; send it back to ACK
|
||||
test eax, eax
|
||||
jnz .got_it
|
||||
|
||||
.continue:
|
||||
add esi, 4
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
|
||||
.nothing:
|
||||
ret ; If no device was found, abort (The irq was probably for a device, not registered to this driver)
|
||||
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"Status=%x\n", eax
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, ax
|
||||
|
||||
test ax, RI ; receive interrupt
|
||||
jz .no_rx
|
||||
|
@ -14,6 +14,7 @@ include 'bus/pci.inc'
|
||||
|
||||
PAGESIZE = 4096
|
||||
PG_SW = 0x003
|
||||
PG_NOCACHE = 0x018
|
||||
|
||||
|
||||
; network driver types
|
||||
|
@ -1025,32 +1025,35 @@ transmit:
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
; DEBUGF 1,"IRQ %x ",eax:2 ; no, you cant replace 'eax:2' with 'al', this must be a bug in FDO
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; find pointer of device wich made IRQ occur
|
||||
|
||||
mov esi, device_list
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .abort
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, dword [esi]
|
||||
mov edx, [device.io_addr] ; get IRQ reason
|
||||
mov ebx, [esi]
|
||||
|
||||
mov edx, [device.io_addr] ; get IRQ reason
|
||||
push ecx
|
||||
xor ecx, ecx ; CSR0
|
||||
call [device.access_read_csr]
|
||||
pop ecx
|
||||
|
||||
test al , al
|
||||
test al, al
|
||||
js .got_it
|
||||
|
||||
.continue:
|
||||
add esi, 4
|
||||
loop .nextdevice
|
||||
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
.nothing:
|
||||
ret ; If no device was found, abort (The irq was probably for a device, not registered to this driver
|
||||
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, eax:2
|
||||
|
||||
;-------------------------------------------------------
|
||||
; Possible reasons:
|
||||
; initialization done - ignore
|
||||
|
@ -1042,27 +1042,36 @@ transmit:
|
||||
; between multiple descriptors you will lose part of the packet
|
||||
;
|
||||
;***************************************************************************
|
||||
|
||||
align 4
|
||||
int_handler:
|
||||
|
||||
DEBUGF 1,"\n%s int\n", my_service
|
||||
|
||||
; find pointer of device which made IRQ occur
|
||||
mov esi, device_list
|
||||
|
||||
mov ecx, [devices]
|
||||
test ecx, ecx
|
||||
jz .nothing
|
||||
mov esi, device_list
|
||||
.nextdevice:
|
||||
mov ebx, [esi]
|
||||
|
||||
set_io 0
|
||||
set_io isr
|
||||
in eax, dx ; note that this clears all interrupts
|
||||
test ax, IE
|
||||
jnz .got_it
|
||||
loop .nextdevice
|
||||
.continue:
|
||||
add esi, 4
|
||||
dec ecx
|
||||
jnz .nextdevice
|
||||
.nothing:
|
||||
ret
|
||||
|
||||
.got_it:
|
||||
|
||||
DEBUGF 1,"IRQ! status=%x\n", ax
|
||||
DEBUGF 1,"Device: %x Status: %x ", ebx, ax
|
||||
|
||||
test ax, RxOK
|
||||
jz .no_rx_
|
||||
|
Loading…
Reference in New Issue
Block a user