1,6 → 1,6 |
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
;; ;; |
;; Copyright (C) KolibriOS team 2010-2015. All rights reserved. ;; |
;; Copyright (C) KolibriOS team 2010-2021. All rights reserved. ;; |
;; Distributed under terms of the GNU General Public License ;; |
;; ;; |
;; rhine.asm ;; |
21,6 → 21,8 |
;; ;; |
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
|
; TODO: test for RX-overrun |
|
format PE DLL native |
entry START |
|
33,8 → 35,8 |
__DEBUG__ = 1 |
__DEBUG_LEVEL__ = 2 ; 1 = all, 2 = errors only |
|
TX_RING_SIZE = 4 |
RX_RING_SIZE = 4 |
TX_RING_SIZE = 32 |
RX_RING_SIZE = 32 |
|
; max time out delay time |
W_MAX_TIMEOUT = 0x0FFF |
1405,13 → 1407,13 |
;; ;; |
;; In: buffer pointer in [esp+4] ;; |
;; pointer to device structure in ebx ;; |
;; Out: eax = 0 on success ;; |
;; ;; |
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
align 4 |
align 16 |
proc transmit stdcall bufferptr |
|
pushf |
cli |
spin_lock_irqsave |
|
mov esi, [bufferptr] |
DEBUGF 1,"Transmitting packet, buffer:%x, size:%u\n", [bufferptr], [esi + NET_BUFF.length] |
1422,10 → 1424,11 |
[eax+13]:2,[eax+12]:2 |
|
cmp [esi + NET_BUFF.length], 1514 |
ja .fail |
ja .error |
cmp [esi + NET_BUFF.length], 60 |
jb .fail |
jb .error |
|
; Program the descriptor |
movzx eax, [ebx + device.cur_tx] |
mov ecx, sizeof.tx_head |
mul ecx |
1433,7 → 1436,7 |
add edi, eax |
|
cmp [edi + tx_head.buff_addr_virt], 0 |
jne .fail |
jne .overrun |
|
mov eax, esi |
mov [edi + tx_head.buff_addr_virt], eax |
1463,18 → 1466,29 |
add dword [ebx + device.bytes_tx], ecx |
adc dword [ebx + device.bytes_tx + 4], 0 |
|
DEBUGF 1,"Transmit OK\n" |
popf |
spin_unlock_irqrestore |
xor eax, eax |
ret |
|
.fail: |
DEBUGF 2,"Transmit failed\n" |
.error: |
DEBUGF 2, "TX packet error\n" |
inc [ebx + device.packets_tx_err] |
invoke NetFree, [bufferptr] |
popf |
|
spin_unlock_irqrestore |
or eax, -1 |
ret |
|
.overrun: |
DEBUGF 2, "TX overrun\n" |
inc [ebx + device.packets_tx_ovr] |
invoke NetFree, [bufferptr] |
|
spin_unlock_irqrestore |
or eax, -1 |
ret |
|
|
endp |
|
|
1484,42 → 1498,23 |
;; Interrupt handler ;; |
;; ;; |
;;;;;;;;;;;;;;;;;;;;;;; |
|
align 4 |
align 16 |
int_handler: |
|
push ebx esi edi |
|
DEBUGF 1,"INT\n" |
mov ebx, [esp+4*4] |
DEBUGF 1,"INT for 0x%x\n", ebx |
|
; Find pointer of device which made IRQ occur |
mov ecx, [devices] |
test ecx, ecx |
jz .nothing |
mov esi, device_list |
.nextdevice: |
mov ebx, [esi] |
|
set_io [ebx + device.io_addr], 0 |
set_io [ebx + device.io_addr], IntrStatus |
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: |
pop edi esi ebx |
xor eax, eax |
jz .nothing |
|
ret ; If no device was found, abort (The irq was probably for a device, not registered to this driver) |
out dx, ax ; ACK interrupt |
DEBUGF 1, "Status=0x%x\n", ax |
|
|
.got_it: |
DEBUGF 1, "status=0x%x\n", ax |
|
push ax |
|
test ax, IntrRxDone |
1652,10 → 1647,15 |
|
ret |
|
.nothing: |
pop edi esi ebx |
xor eax, eax |
|
ret |
|
|
|
|
; End of code |
|
data fixups |