1 ; =============================================================================
2 ; BareMetal -- a 64-bit OS written in Assembly for x86-64 systems
3 ; Copyright (C) 2008-2012 Return Infinity -- see LICENSE.TXT
6 ; =============================================================================
13 ; Ethernet Type II Frame (64 - 1518 bytes)
14 ; MAC Header (14 bytes)
15 ; Destination MAC Address (6 bytes)
16 ; Source MAC Address (6 bytes)
17 ; EtherType/Length (2 bytes)
18 ; Payload (46 - 1500 bytes)
20 ; Network card handles the Preamble (7 bytes), Start-of-Frame-Delimiter (1 byte), and Interframe Gap (12 bytes)
23 ; -----------------------------------------------------------------------------
24 ; os_ethernet_avail -- Check if Ethernet is available
26 ; OUT: RAX = MAC Address if Ethernet is enabled, otherwise 0
33 cmp byte [os_NetEnabled
], 0
34 je os_ethernet_avail_end
38 os_ethernet_avail_loadMAC:
43 jnz os_ethernet_avail_loadMAC
45 os_ethernet_avail_end:
49 ; -----------------------------------------------------------------------------
52 ; -----------------------------------------------------------------------------
53 ; os_ethernet_tx -- Transmit a packet via Ethernet
54 ; IN: RSI = Memory location where data is stored
55 ; RDI = Pointer to 48 bit destination address
56 ; BX = Type of packet (If set to 0 then the EtherType will be set to the length of data)
58 ; OUT: Nothing. All registers preserved
67 cmp byte [os_NetEnabled
], 1
68 jne os_ethernet_tx_fail
69 cmp cx, 1500 ; Fail if more then 1500 bytes
70 jg os_ethernet_tx_fail
72 mov rax
, os_EthernetBusyLock
; Lock the Ethernet so only one send can happen at a time
77 mov rdi
, os_ethernet_tx_buffer
; Build the packet to transfer at this location
78 ; TODO: Ask the driver where in memory the packet should be assembled.
80 ; Copy destination MAC address
84 ; Copy source MAC address
89 ; Set the EtherType/Length
91 jne os_ethernet_tx_typeset
; If EtherType is not set then use the Data Length instead
92 mov bx, cx ; Length of data (Does not include header)
93 os_ethernet_tx_typeset:
94 xchg bl, bh ; x86 is Little-endian but packets use Big-endian
98 ; Copy the packet data
100 mov rax
, 0x000000000000FFFF
101 and rcx
, rax
; Clear the top 48 bits
106 ; Add padding to the packet data if needed
107 cmp cx, 46 ; Data needs to be at least 46 bytes (if not it needs to be padded)
108 jge os_ethernet_tx_nopadding
110 sub ax, cx ; Padding needed = 46 - CX
113 rep stosb ; Store 0x00 CX times
115 os_ethernet_tx_nopadding:
118 stosd ; Store a blank CRC value
120 ; Call the send function of the ethernet card driver
121 add cx, 14 ; Add 14 for the header bytes
122 mov rsi
, os_ethernet_tx_buffer
123 call qword [os_net_transmit
]
125 mov rax
, os_EthernetBusyLock
137 ; -----------------------------------------------------------------------------
140 ; -----------------------------------------------------------------------------
141 ; os_ethernet_tx_raw -- Transmit a raw frame via Ethernet
142 ; IN: RSI = Memory location where raw frame is stored
143 ; CX = Length of frame
144 ; OUT: Nothing. All registers preserved
153 cmp byte [os_NetEnabled
], 1
154 jne os_ethernet_tx_raw_fail
155 cmp cx, 1500 ; Fail if more then 1500 bytes
156 jg os_ethernet_tx_raw_fail
158 mov rax
, os_EthernetBusyLock
; Lock the Ethernet so only one send can happen at a time
161 ; Copy the packet data
162 mov rdi
, os_ethernet_tx_buffer
; Build the packet to transfer at this location
163 mov rax
, 0x000000000000FFFF
164 and rcx
, rax
; Clear the top 48 bits
169 ; Add padding to the packet data if needed
170 cmp cx, 46 ; Data needs to be at least 46 bytes (if not it needs to be padded)
171 jge os_ethernet_tx_raw_nopadding
173 sub ax, cx ; Padding needed = 46 - CX
176 rep stosb ; Store 0x00 CX times
178 os_ethernet_tx_raw_nopadding:
181 stosd ; Store a blank CRC value
183 ; Call the send function of the ethernet card driver
184 mov rsi
, os_ethernet_tx_buffer
185 call qword [os_net_transmit
]
187 mov rax
, os_EthernetBusyLock
190 os_ethernet_tx_raw_fail:
199 ; -----------------------------------------------------------------------------
202 ; -----------------------------------------------------------------------------
203 ; os_ethernet_rx -- Polls the Ethernet card for received data
204 ; IN: RDI = Memory location where packet will be stored
205 ; OUT: RCX = Length of packet
206 ; All other registers preserved
215 cmp byte [os_NetEnabled
], 1
216 jne os_ethernet_rx_fail
218 ; Is there anything in the ring buffer?
219 mov al, byte [os_EthernetBuffer_C1
]
220 mov dl, byte [os_EthernetBuffer_C2
]
221 cmp al, dl ; If both counters are equal then the buffer is empty
222 je os_ethernet_rx_fail
224 ; Read the packet from the ring buffer to RDI
225 mov rsi
, os_EthernetBuffer
227 mov al, byte [os_EthernetBuffer_C1
]
228 push rax
; Save the ring element value
229 shl rax
, 11 ; Quickly multiply RAX by 2048
230 add rsi
, rax
; RSI points to the packet in the ring buffer
231 lodsw ; Load the packet length
232 mov cx, ax ; Copy the packet length to RCX
234 rep movsb ; Copy the packet to RDI
236 pop rax
; Restore the ring element value
238 cmp al, 128 ; Max element number is 127
239 jne os_ethernet_rx_buffer_nowrap
241 os_ethernet_rx_buffer_nowrap:
242 mov byte [os_EthernetBuffer_C1
], al
251 ; -----------------------------------------------------------------------------
254 ; -----------------------------------------------------------------------------
255 ; os_ethernet_ack_int -- Acknowledge an interrupt within the NIC
257 ; OUT: RAX = Type of interrupt trigger
258 ; All other registers preserved
262 call qword [os_net_ack_int
]
266 ; -----------------------------------------------------------------------------
269 ; -----------------------------------------------------------------------------
270 ; os_ethernet_rx_from_interrupt -- Polls the Ethernet card for received data
271 ; IN: RDI = Memory location where packet will be stored
272 ; OUT: RCX = Length of packet
273 ; All other registers preserved
274 os_ethernet_rx_from_interrupt:
282 ; Call the poll function of the ethernet card driver
283 call qword [os_net_poll
]
290 ; -----------------------------------------------------------------------------
293 ; =============================================================================