Rev 1514 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
1159 | hidnplayr | 1 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
2 | ;; ;; |
||
1514 | hidnplayr | 3 | ;; Copyright (C) KolibriOS team 2004-2010. All rights reserved. ;; |
1159 | hidnplayr | 4 | ;; Distributed under terms of the GNU General Public License ;; |
5 | ;; ;; |
||
6 | ;; ETHERNET.INC ;; |
||
7 | ;; ;; |
||
8 | ;; Ethernet network layer for KolibriOS ;; |
||
9 | ;; ;; |
||
10 | ;; Written by hidnplayr@kolibrios.org ;; |
||
11 | ;; ;; |
||
12 | ;; GNU GENERAL PUBLIC LICENSE ;; |
||
13 | ;; Version 2, June 1991 ;; |
||
14 | ;; ;; |
||
15 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
||
16 | |||
1206 | hidnplayr | 17 | $Revision: 1519 $ |
1159 | hidnplayr | 18 | |
19 | struct ETH_FRAME |
||
1514 | hidnplayr | 20 | .DstMAC dp ? ; destination MAC-address |
21 | .SrcMAC dp ? ; source MAC-address |
||
22 | .Type dw ? ; type of the upper-layer protocol |
||
23 | .Data: ; data (46-1500 bytes for a normal packet) |
||
1159 | hidnplayr | 24 | ends |
25 | |||
1514 | hidnplayr | 26 | virtual at NET_DEVICE.end |
27 | |||
28 | ETH_DEVICE: |
||
1519 | hidnplayr | 29 | |
1159 | hidnplayr | 30 | .set_mode dd ? |
31 | .get_mode dd ? |
||
32 | |||
1519 | hidnplayr | 33 | .set_MAC dd ? |
34 | .get_MAC dd ? |
||
35 | |||
1514 | hidnplayr | 36 | .mode dd ? |
1159 | hidnplayr | 37 | .mac dp ? |
38 | |||
1514 | hidnplayr | 39 | end virtual |
1159 | hidnplayr | 40 | |
41 | align 4 |
||
1196 | hidnplayr | 42 | iglobal |
43 | |||
44 | ETH_BROADCAST dp 0xffffffffffff |
||
45 | endg |
||
46 | |||
47 | align 4 |
||
1159 | hidnplayr | 48 | uglobal |
49 | ETH_RUNNING dd ? |
||
50 | endg |
||
51 | |||
52 | |||
1257 | hidnplayr | 53 | ;----------------------------------------------------------------- |
1159 | hidnplayr | 54 | ; |
55 | ; ETH_init |
||
56 | ; |
||
57 | ; This function resets all ethernet variables |
||
58 | ; |
||
59 | ; IN: / |
||
60 | ; OUT: / |
||
61 | ; |
||
1257 | hidnplayr | 62 | ;----------------------------------------------------------------- |
1159 | hidnplayr | 63 | align 4 |
64 | ETH_init: |
||
65 | |||
1514 | hidnplayr | 66 | mov [ETH_RUNNING], 0 |
1159 | hidnplayr | 67 | |
68 | ret |
||
69 | |||
70 | |||
1257 | hidnplayr | 71 | ;----------------------------------------------------------------- |
1159 | hidnplayr | 72 | ; |
73 | ; ETH_Receiver: |
||
74 | ; |
||
75 | ; This function is called by ethernet drivers, |
||
76 | ; It pushes the received ethernet packets onto the eth_in_queue |
||
77 | ; |
||
1514 | hidnplayr | 78 | ; IN: [esp] = Pointer to buffer |
1257 | hidnplayr | 79 | ; [esp-4] = size of buffer |
1514 | hidnplayr | 80 | ; ebx = pointer to eth_device |
1159 | hidnplayr | 81 | ; OUT: / |
82 | ; |
||
1257 | hidnplayr | 83 | ;----------------------------------------------------------------- |
1159 | hidnplayr | 84 | align 4 |
1249 | hidnplayr | 85 | ETH_receiver: |
1473 | hidnplayr | 86 | mov eax, [esp] |
87 | mov ecx, [esp+4] |
||
1249 | hidnplayr | 88 | |
1159 | hidnplayr | 89 | DEBUGF 1,"ETH_Handler - size: %u\n", ecx |
90 | cmp ecx, 60 ; check packet length |
||
91 | jl .dump |
||
92 | sub ecx, ETH_FRAME.Data |
||
93 | |||
94 | lea edx, [eax + ETH_FRAME.Data] |
||
95 | mov ax , [eax + ETH_FRAME.Type] |
||
96 | |||
97 | cmp ax, ETHER_IPv4 |
||
1196 | hidnplayr | 98 | je IPv4_handler |
1159 | hidnplayr | 99 | |
100 | cmp ax, ETHER_ARP |
||
1196 | hidnplayr | 101 | je ARP_handler |
1159 | hidnplayr | 102 | |
1519 | hidnplayr | 103 | ; cmp ax, ETHER_PPP_DISCOVERY |
104 | ; je PPPOE_discovery |
||
105 | |||
1473 | hidnplayr | 106 | DEBUGF 2,"Unknown ethernet packet type %x\n", ax |
1159 | hidnplayr | 107 | |
108 | .dump: |
||
1473 | hidnplayr | 109 | DEBUGF 2,"ETH_Handler - dumping\n" |
1159 | hidnplayr | 110 | call kernel_free |
111 | add esp, 4 |
||
1249 | hidnplayr | 112 | ret |
1159 | hidnplayr | 113 | |
1249 | hidnplayr | 114 | ;----------------------------------------------------------------- |
115 | ; |
||
1257 | hidnplayr | 116 | ; ETH_create_packet |
1159 | hidnplayr | 117 | ; |
1514 | hidnplayr | 118 | ; IN: eax = pointer to source mac |
119 | ; ebx = pointer to destination mac |
||
120 | ; ecx = packet size |
||
121 | ; edx = device number |
||
122 | ; di = protocol |
||
1159 | hidnplayr | 123 | ; |
1514 | hidnplayr | 124 | ; OUT: edi = 0 on error, pointer to buffer otherwise |
125 | ; eax = buffer start |
||
126 | ; ebx = to device structure |
||
127 | ; ecx = unchanged (packet size of embedded data) |
||
128 | ; edx = size of complete buffer |
||
1159 | hidnplayr | 129 | ; |
1257 | hidnplayr | 130 | ;----------------------------------------------------------------- |
1159 | hidnplayr | 131 | align 4 |
1249 | hidnplayr | 132 | ETH_create_packet: |
1159 | hidnplayr | 133 | |
1473 | hidnplayr | 134 | DEBUGF 1,"Creating Ethernet Packet (size=%u): \n", ecx |
1159 | hidnplayr | 135 | |
1519 | hidnplayr | 136 | push esi |
137 | mov esi, [NET_DRV_LIST] ;;; TODO: FIXME |
||
138 | cmp ecx, [esi + NET_DEVICE.mtu] |
||
139 | pop esi |
||
1159 | hidnplayr | 140 | jg .exit |
141 | |||
142 | push ecx di eax ebx edx |
||
143 | |||
144 | add ecx, ETH_FRAME.Data |
||
145 | push ecx |
||
146 | push ecx |
||
147 | call kernel_alloc |
||
1514 | hidnplayr | 148 | mov edi, eax |
149 | test edi, edi |
||
1159 | hidnplayr | 150 | jz .pop_exit |
151 | |||
152 | pop ecx |
||
153 | pop edx |
||
154 | |||
155 | pop esi |
||
156 | movsd |
||
157 | movsw |
||
158 | pop esi |
||
159 | movsd |
||
160 | movsw |
||
161 | pop ax |
||
162 | stosw |
||
163 | |||
164 | lea eax, [edi - ETH_FRAME.Data] ; Set eax to buffer start |
||
1206 | hidnplayr | 165 | mov edx, ecx ; Set ebx to complete buffer size |
1159 | hidnplayr | 166 | pop ecx |
167 | |||
1206 | hidnplayr | 168 | xor ebx, ebx ;;;; TODO: Fixme |
1514 | hidnplayr | 169 | mov ebx, [NET_DRV_LIST + ebx] |
1159 | hidnplayr | 170 | |
1206 | hidnplayr | 171 | cmp edx, 46 + ETH_FRAME.Data ; If data size is less then 46, add padding bytes |
1519 | hidnplayr | 172 | jge .continue |
1206 | hidnplayr | 173 | mov edx, 46 + ETH_FRAME.Data |
174 | .continue: |
||
175 | |||
1473 | hidnplayr | 176 | DEBUGF 1,"done: %x size:%u device:%x\n", eax, edx, ebx |
1159 | hidnplayr | 177 | ret |
178 | |||
179 | .pop_exit: |
||
1473 | hidnplayr | 180 | DEBUGF 2,"Out of ram space!!\n" |
1159 | hidnplayr | 181 | add esp, 18 |
1514 | hidnplayr | 182 | and edi, 0 |
1206 | hidnplayr | 183 | ret |
184 | |||
1159 | hidnplayr | 185 | .exit: |
1473 | hidnplayr | 186 | DEBUGF 2,"Packet too large!\n" |
1514 | hidnplayr | 187 | and edi, 0 |
1159 | hidnplayr | 188 | ret |
189 | |||
190 | |||
191 | |||
1257 | hidnplayr | 192 | ;----------------------------------------------------------------- |
1159 | hidnplayr | 193 | ; |
194 | ; ETH_API |
||
195 | ; |
||
196 | ; This function is called by system function 75 |
||
197 | ; |
||
198 | ; IN: subfunction number in bl |
||
199 | ; device number in bh |
||
200 | ; ecx, edx, .. depends on subfunction |
||
201 | ; |
||
202 | ; OUT: |
||
203 | ; |
||
1257 | hidnplayr | 204 | ;----------------------------------------------------------------- |
1159 | hidnplayr | 205 | align 4 |
206 | ETH_API: |
||
207 | |||
1514 | hidnplayr | 208 | cmp bh, MAX_NET_DEVICES |
209 | jg .error |
||
1159 | hidnplayr | 210 | movzx eax, bh |
211 | shl eax, 2 |
||
212 | |||
1514 | hidnplayr | 213 | cmp bl, 7 |
214 | jz .out_queue |
||
215 | cmp bl, 6 |
||
216 | jz .in_queue |
||
217 | |||
218 | mov eax, dword [NET_DRV_LIST + eax] |
||
219 | cmp [eax + NET_DEVICE.type], NET_TYPE_ETH |
||
220 | jne .error |
||
221 | |||
1159 | hidnplayr | 222 | test bl, bl |
223 | jz .packets_tx ; 0 |
||
224 | dec bl |
||
225 | jz .packets_rx ; 1 |
||
226 | dec bl |
||
227 | jz .bytes_tx ; 2 |
||
228 | dec bl |
||
229 | jz .bytes_rx ; 3 |
||
230 | dec bl |
||
231 | jz .read_mac ; 4 |
||
232 | dec bl |
||
233 | jz .write_mac ; 5 |
||
234 | |||
1514 | hidnplayr | 235 | .error: |
236 | DEBUGF 2,"Device is not ethernet type\n" |
||
237 | or eax, -1 |
||
1159 | hidnplayr | 238 | ret |
239 | |||
240 | .packets_tx: |
||
1519 | hidnplayr | 241 | mov eax, dword [eax + NET_DEVICE.packets_tx] |
1171 | hidnplayr | 242 | |
1159 | hidnplayr | 243 | ret |
244 | |||
245 | .packets_rx: |
||
1519 | hidnplayr | 246 | mov eax, dword [eax + NET_DEVICE.packets_rx] |
1159 | hidnplayr | 247 | ret |
248 | |||
249 | .bytes_tx: |
||
1519 | hidnplayr | 250 | mov ebx, dword [eax + NET_DEVICE.bytes_tx + 4] |
251 | mov eax, dword [eax + NET_DEVICE.bytes_tx] |
||
1174 | hidnplayr | 252 | mov [esp+20+4], ebx ; TODO: fix this ugly code |
1159 | hidnplayr | 253 | ret |
254 | |||
255 | .bytes_rx: |
||
1519 | hidnplayr | 256 | mov ebx, dword [eax + NET_DEVICE.bytes_rx + 4] |
257 | mov eax, dword [eax + NET_DEVICE.bytes_rx] |
||
1174 | hidnplayr | 258 | mov [esp+20+4], ebx ; TODO: fix this ugly code |
1159 | hidnplayr | 259 | ret |
260 | |||
1174 | hidnplayr | 261 | |
1159 | hidnplayr | 262 | .read_mac: |
263 | movzx ebx, word [eax + ETH_DEVICE.mac] |
||
264 | mov eax, dword [eax + ETH_DEVICE.mac + 2] |
||
1171 | hidnplayr | 265 | mov [esp+20+4], ebx ; TODO: fix this ugly code |
1159 | hidnplayr | 266 | ret |
267 | |||
268 | .write_mac: |
||
269 | push ecx |
||
270 | push dx |
||
1519 | hidnplayr | 271 | call [eax + ETH_DEVICE.set_MAC] |
1159 | hidnplayr | 272 | ret |
273 | |||
274 | .in_queue: |
||
1514 | hidnplayr | 275 | if ETH_QUEUE |
1159 | hidnplayr | 276 | add eax, ETH_IN_QUEUE |
277 | mov eax, [eax + queue.size] |
||
1514 | hidnplayr | 278 | else |
279 | or eax, -1 |
||
280 | end if |
||
1159 | hidnplayr | 281 | ret |
282 | |||
283 | .out_queue: |
||
1514 | hidnplayr | 284 | if ETH_QUEUE |
1159 | hidnplayr | 285 | add eax, ETH_OUT_QUEUE |
286 | mov eax, [eax + queue.size] |
||
1514 | hidnplayr | 287 | else |
288 | or eax, -1 |
||
289 | end if |
||
1159 | hidnplayr | 290 | ret |