Rev 2 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed
Rev 2 | Rev 108 | ||
---|---|---|---|
1 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
1 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
2 | ;; ;; |
2 | ;; ;; |
3 | ;; ETHERNET.INC ;; |
3 | ;; ETHERNET.INC ;; |
4 | ;; ;; |
4 | ;; ;; |
5 | ;; Ethernet network layer for Menuet OS ;; |
5 | ;; Ethernet network layer for Menuet OS ;; |
6 | ;; ;; |
6 | ;; ;; |
7 | ;; Version 0.4 22 September 2003 ;; |
7 | ;; Version 0.4 22 September 2003 ;; |
8 | ;; ;; |
8 | ;; ;; |
9 | ;; This file contains the following: ;; |
9 | ;; This file contains the following: ;; |
10 | ;; PCI bus scanning for valid devices ;; |
10 | ;; PCI bus scanning for valid devices ;; |
11 | ;; Table of supported ethernet drivers ;; |
11 | ;; Table of supported ethernet drivers ;; |
12 | ;; Code to identify and activate a supported driver ;; |
12 | ;; Code to identify and activate a supported driver ;; |
13 | ;; ARP handler ;; |
13 | ;; ARP handler ;; |
14 | ;; Driver interface to the IP layer ;; |
14 | ;; Driver interface to the IP layer ;; |
15 | ;; Gateway support ;; |
15 | ;; Gateway support ;; |
16 | ;; ;; |
16 | ;; ;; |
17 | ;; Individual driver files are included here ;; |
17 | ;; Individual driver files are included here ;; |
18 | ;; ;; |
18 | ;; ;; |
19 | ;; The PCI bus scanning code was ported from the etherboot ;; |
19 | ;; The PCI bus scanning code was ported from the etherboot ;; |
20 | ;; 5.0.6 project. The copyright statement for that code is ;; |
20 | ;; 5.0.6 project. The copyright statement for that code is ;; |
21 | ;; ;; |
21 | ;; ;; |
22 | ;; GNU GENERAL PUBLIC LICENSE ;; |
22 | ;; GNU GENERAL PUBLIC LICENSE ;; |
23 | ;; Version 2, June 1991 ;; |
23 | ;; Version 2, June 1991 ;; |
24 | ;; ;; |
24 | ;; ;; |
25 | ;; remaining parts Copyright 2002 Mike Hibbett ;; |
25 | ;; remaining parts Copyright 2002 Mike Hibbett ;; |
26 | ;; mikeh@oceanfree.net ;; |
26 | ;; mikeh@oceanfree.net ;; |
27 | ;; ;; |
27 | ;; ;; |
28 | ;; See file COPYING for details ;; |
28 | ;; See file COPYING for details ;; |
29 | ;; ;; |
29 | ;; ;; |
30 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
30 | ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; |
31 | 31 | ||
32 | ;******************************************************************** |
32 | ;******************************************************************** |
33 | ; Interface |
33 | ; Interface |
34 | ; ethernet_driver called by stack_handler in stack.inc |
34 | ; ethernet_driver called by stack_handler in stack.inc |
35 | ; eth_probe called by app_stack_handler in stack.inc |
35 | ; eth_probe called by app_stack_handler in stack.inc |
36 | ; |
36 | ; |
37 | ;******************************************************************** |
37 | ;******************************************************************** |
38 | 38 | ||
39 | ; Some useful information on data structures |
39 | ; Some useful information on data structures |
40 | 40 | ||
41 | ; Ethernet Packet - ARP Request example |
41 | ; Ethernet Packet - ARP Request example |
42 | ; |
42 | ; |
43 | ; 0 1 2 3 |
43 | ; 0 1 2 3 |
44 | ; 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
44 | ; 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 |
45 | ; |
45 | ; |
46 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
46 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
47 | ; | Dest H/W Address | |
47 | ; | Dest H/W Address | |
48 | ; | ( 14 byte header ) | |
48 | ; | ( 14 byte header ) | |
49 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
49 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
50 | ; | | Source H/W Address | |
50 | ; | | Source H/W Address | |
51 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
51 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
52 | ; | | |
52 | ; | | |
53 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
53 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
54 | ; | Protocol - ARP 08 06 | |
54 | ; | Protocol - ARP 08 06 | |
55 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
55 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
56 | 56 | ||
57 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
57 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
58 | ; | H/W Type 00 01 | Protocol Type 08 00 | |
58 | ; | H/W Type 00 01 | Protocol Type 08 00 | |
59 | ; | ( ARP Request packet ) | |
59 | ; | ( ARP Request packet ) | |
60 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
60 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
61 | ; | HLen 0x06 | PLen 0x04 | OpCode 00 01 | |
61 | ; | HLen 0x06 | PLen 0x04 | OpCode 00 01 | |
62 | ; | ( 0001 for request, 0002 for reply ) | |
62 | ; | ( 0001 for request, 0002 for reply ) | |
63 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
63 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
64 | ; | Source Hardware Address ( MAC Address ) | |
64 | ; | Source Hardware Address ( MAC Address ) | |
65 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
65 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
66 | ; | | Source IP Address | |
66 | ; | | Source IP Address | |
67 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
67 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
68 | ; | | Destination Hardware Address | |
68 | ; | | Destination Hardware Address | |
69 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
69 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
70 | ; | | |
70 | ; | | |
71 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
71 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
72 | ; | Destination IP Address | |
72 | ; | Destination IP Address | |
73 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
73 | ; +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ |
74 | 74 | ||
75 | ; Include individual drivers source files at this point. |
75 | ; Include individual drivers source files at this point. |
76 | ; If you create a new driver, include it below. |
76 | ; If you create a new driver, include it below. |
77 | 77 | ||
78 | include "rtl8029.inc" |
78 | include "rtl8029.inc" |
79 | include "i8255x.inc" |
79 | include "i8255x.inc" |
80 | include "rtl8139.inc" |
80 | include "rtl8139.inc" |
81 | include "3c59x.inc" |
81 | include "3c59x.inc" |
82 | include "sis900.inc" |
82 | include "sis900.inc" |
83 | include "pcnet32.inc" |
83 | include "pcnet32.inc" |
84 | 84 | ||
85 | ; DEBUGGING_STATE enables or disables output of received and transmitted |
85 | ; DEBUGGING_STATE enables or disables output of received and transmitted |
86 | ; data over the serial port |
86 | ; data over the serial port |
87 | DEBUGGING_ENABLED equ 1 |
87 | DEBUGGING_ENABLED equ 1 |
88 | DEBUGGING_DISABLED equ 0 |
88 | DEBUGGING_DISABLED equ 0 |
89 | DEBUGGING_STATE equ DEBUGGING_DISABLED |
89 | DEBUGGING_STATE equ DEBUGGING_DISABLED |
90 | 90 | ||
91 | ; PCICards |
91 | ; PCICards |
92 | ; ======== |
92 | ; ======== |
93 | ; PCI vendor and hardware types for hardware supported by the above drivers |
93 | ; PCI vendor and hardware types for hardware supported by the above drivers |
94 | ; If you add a driver, ensure you update this datastructure, otherwise the |
94 | ; If you add a driver, ensure you update this datastructure, otherwise the |
95 | ; card will not be probed. |
95 | ; card will not be probed. |
96 | ; Each driver is defined by 4 double words. These are |
96 | ; Each driver is defined by 4 double words. These are |
97 | ; PCIVendorDevice probeFunction ResetFunction PollFunction transmitFunction |
97 | ; PCIVendorDevice probeFunction ResetFunction PollFunction transmitFunction |
98 | ; The last entry must be kept at all zeros, to indicate the end of the list |
98 | ; The last entry must be kept at all zeros, to indicate the end of the list |
99 | ; As a PCI driver may support more than one hardware implementation, there may |
99 | ; As a PCI driver may support more than one hardware implementation, there may |
100 | ; be several lines which refer to the same functions. |
100 | ; be several lines which refer to the same functions. |
101 | ; The first driver found on the PCI bus will be the one used. |
101 | ; The first driver found on the PCI bus will be the one used. |
102 | 102 | ||
103 | PCICARDS_ENTRY_SIZE equ 20 ; Size of each PCICARDS entry |
103 | PCICARDS_ENTRY_SIZE equ 20 ; Size of each PCICARDS entry |
104 | 104 | ||
105 | iglobal |
105 | iglobal |
106 | PCICards: |
106 | PCICards: |
107 | dd 0x12098086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
107 | dd 0x12098086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
108 | dd 0x10298086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
108 | dd 0x10298086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
109 | dd 0x12298086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
109 | dd 0x12298086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
110 | dd 0x10308086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
110 | dd 0x10308086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
111 | dd 0x24498086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
111 | dd 0x24498086, I8255x_probe, I8255x_reset, I8255x_poll, I8255x_transmit |
112 | dd 0x802910ec, rtl8029_probe, rtl8029_reset, rtl8029_poll, rtl8029_transmit |
112 | dd 0x802910ec, rtl8029_probe, rtl8029_reset, rtl8029_poll, rtl8029_transmit |
113 | dd 0x12111113, rtl8029_probe, rtl8029_reset, rtl8029_poll, rtl8029_transmit |
113 | dd 0x12111113, rtl8029_probe, rtl8029_reset, rtl8029_poll, rtl8029_transmit |
114 | dd 0x813910ec, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
114 | dd 0x813910ec, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
- | 115 | ; /+/ Íîâûå âåíäîðû ñåòåâûõ êàðò íà áàçå rtl8139 |
|
- | 116 | dd 0x813810ec, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 117 | dd 0x12111113, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 118 | dd 0x13601500, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 119 | dd 0x13604033, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 120 | dd 0x13001186, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 121 | dd 0x13401186, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 122 | dd 0xab0613d1, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 123 | dd 0xa1171259, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 124 | dd 0xa11e1259, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 125 | dd 0xab0614ea, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 126 | dd 0xab0714ea, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 127 | dd 0x123411db, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 128 | dd 0x91301432, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 129 | dd 0x101202ac, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 130 | dd 0x0106018a, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 131 | dd 0x1211126c, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 132 | dd 0x81391743, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 133 | dd 0x8139021b, rtl8139_probe, rtl8139_reset, rtl8139_poll, rtl8139_transmit |
|
- | 134 | ; /-/ |
|
115 | dd 0x590010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
135 | dd 0x590010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
116 | dd 0x592010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
136 | dd 0x592010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
117 | dd 0x597010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
137 | dd 0x597010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
118 | dd 0x595010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
138 | dd 0x595010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
119 | dd 0x595110b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
139 | dd 0x595110b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
120 | dd 0x595210b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
140 | dd 0x595210b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
121 | dd 0x900010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
141 | dd 0x900010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
122 | dd 0x900110b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
142 | dd 0x900110b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
123 | dd 0x900410b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
143 | dd 0x900410b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
124 | dd 0x900510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
144 | dd 0x900510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
125 | dd 0x900610b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
145 | dd 0x900610b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
126 | dd 0x900A10b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
146 | dd 0x900A10b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
127 | dd 0x905010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
147 | dd 0x905010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
128 | dd 0x905110b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
148 | dd 0x905110b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
129 | dd 0x905510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
149 | dd 0x905510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
130 | dd 0x905810b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
150 | dd 0x905810b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
131 | dd 0x905A10b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
151 | dd 0x905A10b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
132 | dd 0x920010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
152 | dd 0x920010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
133 | dd 0x980010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
153 | dd 0x980010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
134 | dd 0x980510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
154 | dd 0x980510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
135 | dd 0x764610b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
155 | dd 0x764610b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
136 | dd 0x505510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
156 | dd 0x505510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
137 | dd 0x605510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
157 | dd 0x605510b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
138 | dd 0x605610b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
158 | dd 0x605610b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
139 | dd 0x5b5710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
159 | dd 0x5b5710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
140 | dd 0x505710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
160 | dd 0x505710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
141 | dd 0x515710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
161 | dd 0x515710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
142 | dd 0x525710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
162 | dd 0x525710b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
143 | dd 0x656010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
163 | dd 0x656010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
144 | dd 0x656210b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
164 | dd 0x656210b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
145 | dd 0x656410b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
165 | dd 0x656410b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
146 | dd 0x450010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
166 | dd 0x450010b7, e3c59x_probe, e3c59x_reset, e3c59x_poll, e3c59x_transmit |
147 | dd 0x09001039, SIS900_probe, SIS900_reset, SIS900_poll, SIS900_transmit |
167 | dd 0x09001039, SIS900_probe, SIS900_reset, SIS900_poll, SIS900_transmit |
148 | dd 0x20001022, pcnet32_probe, pcnet32_reset, pcnet32_poll, pcnet32_xmit |
168 | dd 0x20001022, pcnet32_probe, pcnet32_reset, pcnet32_poll, pcnet32_xmit |
149 | dd 0x26251022, pcnet32_probe, pcnet32_reset, pcnet32_poll, pcnet32_xmit |
169 | dd 0x26251022, pcnet32_probe, pcnet32_reset, pcnet32_poll, pcnet32_xmit |
150 | dd 0x20011022, pcnet32_probe, pcnet32_reset, pcnet32_poll, pcnet32_xmit |
170 | dd 0x20011022, pcnet32_probe, pcnet32_reset, pcnet32_poll, pcnet32_xmit |
151 | ; following card is untested |
171 | ; following card is untested |
152 | dd 0x70161039, SIS900_probe, SIS900_reset, SIS900_poll, SIS900_transmit |
172 | dd 0x70161039, SIS900_probe, SIS900_reset, SIS900_poll, SIS900_transmit |
153 | dd 0,0,0,0,0 ; end of list marker, do not remove |
173 | dd 0,0,0,0,0 ; end of list marker, do not remove |
154 | endg |
174 | endg |
155 | 175 | ||
156 | ; PCI Bus defines |
176 | ; PCI Bus defines |
157 | PCI_HEADER_TYPE equ 0x0e ;8 bit |
177 | PCI_HEADER_TYPE equ 0x0e ;8 bit |
158 | PCI_BASE_ADDRESS_0 equ 0x10 ;32 bit |
178 | PCI_BASE_ADDRESS_0 equ 0x10 ;32 bit |
159 | PCI_BASE_ADDRESS_5 equ 0x24 ;32 bits |
179 | PCI_BASE_ADDRESS_5 equ 0x24 ;32 bits |
160 | PCI_BASE_ADDRESS_SPACE_IO equ 0x01 |
180 | PCI_BASE_ADDRESS_SPACE_IO equ 0x01 |
161 | PCI_VENDOR_ID equ 0x00 ;16 bit |
181 | PCI_VENDOR_ID equ 0x00 ;16 bit |
162 | PCI_BASE_ADDRESS_IO_MASK equ 0xFFFFFFFC |
182 | PCI_BASE_ADDRESS_IO_MASK equ 0xFFFFFFFC |
163 | 183 | ||
164 | ETHER_IP equ 0x0008 ; Reversed from 0800 for intel |
184 | ETHER_IP equ 0x0008 ; Reversed from 0800 for intel |
165 | ETHER_ARP equ 0x0608 ; Reversed from 0806 for intel |
185 | ETHER_ARP equ 0x0608 ; Reversed from 0806 for intel |
166 | ETHER_RARP equ 0x3580 |
186 | ETHER_RARP equ 0x3580 |
167 | ARP_REQ_OPCODE equ 0x0100 |
187 | ARP_REQ_OPCODE equ 0x0100 |
168 | ARP_REP_OPCODE equ 0x0200 |
188 | ARP_REP_OPCODE equ 0x0200 |
169 | 189 | ||
170 | uglobal |
190 | uglobal |
171 | arp_rx_count: dd 0 |
191 | arp_rx_count: dd 0 |
172 | ip_rx_count: dd 0 |
192 | ip_rx_count: dd 0 |
173 | dumped_rx_count: dd 0 |
193 | dumped_rx_count: dd 0 |
174 | ip_tx_count: dd 0 |
194 | ip_tx_count: dd 0 |
175 | node_addr: db 0,0,0,0,0,0 |
195 | node_addr: db 0,0,0,0,0,0 |
176 | eth_rx_data_len: dw 0 |
196 | eth_rx_data_len: dw 0 |
177 | eth_status: dd 0 |
197 | eth_status: dd 0 |
178 | io_addr: dd 0 |
198 | io_addr: dd 0 |
179 | hdrtype: db 0 |
199 | hdrtype: db 0 |
180 | vendor_device: dd 0 |
200 | vendor_device: dd 0 |
181 | pci_data: dd 0 |
201 | pci_data: dd 0 |
182 | pci_dev: dd 0 |
202 | pci_dev: dd 0 |
183 | pci_bus: dd 0 |
203 | pci_bus: dd 0 |
184 | 204 | ||
185 | ; These will hold pointers to the selected driver functions |
205 | ; These will hold pointers to the selected driver functions |
186 | drvr_probe: dd 0 |
206 | drvr_probe: dd 0 |
187 | drvr_reset: dd 0 |
207 | drvr_reset: dd 0 |
188 | drvr_poll: dd 0 |
208 | drvr_poll: dd 0 |
189 | drvr_transmit: dd 0 |
209 | drvr_transmit: dd 0 |
190 | 210 | ||
191 | ; These hold the destination Host identity for ARP responses |
211 | ; These hold the destination Host identity for ARP responses |
192 | remote_ip_add: dd 0 |
212 | remote_ip_add: dd 0 |
193 | remote_hw_add: db 0, 0, 0, 0, 0, 0 |
213 | remote_hw_add: db 0, 0, 0, 0, 0, 0 |
194 | endg |
214 | endg |
195 | 215 | ||
196 | iglobal |
216 | iglobal |
197 | broadcast_add: db 0xff,0xff,0xff,0xff,0xff,0xff |
217 | broadcast_add: db 0xff,0xff,0xff,0xff,0xff,0xff |
198 | subnet_mask: dd 0x00ffffff |
218 | subnet_mask: dd 0x00ffffff |
199 | endg |
219 | endg |
200 | 220 | ||
201 | uglobal |
221 | uglobal |
202 | ; This is used by getMACfromIP |
222 | ; This is used by getMACfromIP |
203 | MACAddress: db 0,0,0,0,0,0 |
223 | MACAddress: db 0,0,0,0,0,0 |
204 | gateway_ip: db 0, 0, 0, 0 |
224 | gateway_ip: db 0, 0, 0, 0 |
205 | dns_ip: dd 0 |
225 | dns_ip: dd 0 |
206 | endg |
226 | endg |
207 | 227 | ||
208 | ; The follow is the ARP Table. |
228 | ; The follow is the ARP Table. |
209 | ; This table must be manually updated and the kernel recompilied if |
229 | ; This table must be manually updated and the kernel recompilied if |
210 | ; changes are made to it. |
230 | ; changes are made to it. |
211 | ; ARP_TABLE_SIZE defines the size of the table |
231 | ; ARP_TABLE_SIZE defines the size of the table |
212 | ; ARP_TABLE_ENTRIES defines the number of entries in the table |
232 | ; ARP_TABLE_ENTRIES defines the number of entries in the table |
213 | ; Each entry is 10 bytes: 4 Byte IP address, 6 byte MAC Address, |
233 | ; Each entry is 10 bytes: 4 Byte IP address, 6 byte MAC Address, |
214 | ; 2 bytes status, 2 bytes TTL ( in seconds ) |
234 | ; 2 bytes status, 2 bytes TTL ( in seconds ) |
215 | ; Empty entries are filled with zeros |
235 | ; Empty entries are filled with zeros |
216 | ; The TTL field is decremented every second, and is deleted when it |
236 | ; The TTL field is decremented every second, and is deleted when it |
217 | ; reaches 0. It is refreshed every time a packet is received |
237 | ; reaches 0. It is refreshed every time a packet is received |
218 | ; If the TTL field is 0xFFFF it is a permanent entry and is never deleted |
238 | ; If the TTL field is 0xFFFF it is a permanent entry and is never deleted |
219 | ; The status field can be the following values |
239 | ; The status field can be the following values |
220 | ; 0x0000 entry not used |
240 | ; 0x0000 entry not used |
221 | ; 0x0001 entry holds a valid mapping |
241 | ; 0x0001 entry holds a valid mapping |
222 | ; 0x0002 entry contains an IP address, awaiting ARP response |
242 | ; 0x0002 entry contains an IP address, awaiting ARP response |
223 | ; 0x0003 No response received to ARP request. |
243 | ; 0x0003 No response received to ARP request. |
224 | ; The last status value is provided to allow the network layer to delete |
244 | ; The last status value is provided to allow the network layer to delete |
225 | ; a packet that is queued awaiting an ARP response |
245 | ; a packet that is queued awaiting an ARP response |
226 | 246 | ||
227 | ARP_NO_ENTRY equ 0 |
247 | ARP_NO_ENTRY equ 0 |
228 | ARP_VALID_MAPPING equ 1 |
248 | ARP_VALID_MAPPING equ 1 |
229 | ARP_AWAITING_RESPONSE equ 2 |
249 | ARP_AWAITING_RESPONSE equ 2 |
230 | ARP_RESPONSE_TIMEOUT equ 3 |
250 | ARP_RESPONSE_TIMEOUT equ 3 |
231 | 251 | ||
232 | ARP_ENTRY_SIZE equ 14 ; Number of bytes per entry |
252 | ARP_ENTRY_SIZE equ 14 ; Number of bytes per entry |
233 | ARP_TABLE_SIZE equ 20 ; Size of table |
253 | ARP_TABLE_SIZE equ 20 ; Size of table |
234 | ARP_TABLE_ENTRIES equ 0 ; Inital, hardcoded entries |
254 | ARP_TABLE_ENTRIES equ 0 ; Inital, hardcoded entries |
235 | 255 | ||
236 | uglobal |
256 | uglobal |
237 | ARPTable: |
257 | ARPTable: |
238 | times ( ARP_TABLE_SIZE - ARP_TABLE_ENTRIES ) * ARP_ENTRY_SIZE db 0 |
258 | times ( ARP_TABLE_SIZE - ARP_TABLE_ENTRIES ) * ARP_ENTRY_SIZE db 0 |
239 | endg |
259 | endg |
240 | 260 | ||
241 | iglobal |
261 | iglobal |
242 | NumARP: db ARP_TABLE_ENTRIES |
262 | NumARP: db ARP_TABLE_ENTRIES |
243 | endg |
263 | endg |
244 | 264 | ||
245 | ;*************************************************************************** |
265 | ;*************************************************************************** |
246 | ; Function |
266 | ; Function |
247 | ; eth_probe |
267 | ; eth_probe |
248 | ; Description |
268 | ; Description |
249 | ; Searches for an ethernet card. If found, the card is enabled and |
269 | ; Searches for an ethernet card. If found, the card is enabled and |
250 | ; the ethernet -> IP link established |
270 | ; the ethernet -> IP link established |
251 | ; |
271 | ; |
252 | ; This function scans the PCI bus looking for a supported device. |
272 | ; This function scans the PCI bus looking for a supported device. |
253 | ; ISA bus is currently not supported. |
273 | ; ISA bus is currently not supported. |
254 | ; |
274 | ; |
255 | ; eax is 0 if no hardware found |
275 | ; eax is 0 if no hardware found |
256 | ;*************************************************************************** |
276 | ;*************************************************************************** |
257 | eth_probe: |
277 | eth_probe: |
258 | ; Find a card on the PCI bus, and get it's address |
278 | ; Find a card on the PCI bus, and get it's address |
259 | call scan_bus ; Find the ethernet cards PIC address |
279 | call scan_bus ; Find the ethernet cards PIC address |
260 | xor eax, eax |
280 | xor eax, eax |
261 | cmp [io_addr], eax |
281 | cmp [io_addr], eax |
262 | je ep_00x ; Return 0 in eax if no cards found |
282 | je ep_00x ; Return 0 in eax if no cards found |
263 | 283 | ||
264 | call dword [drvr_probe] ; Call the drivers probe function |
284 | call dword [drvr_probe] ; Call the drivers probe function |
265 | 285 | ||
266 | mov eax, [io_addr] ; return a non zero value |
286 | mov eax, [io_addr] ; return a non zero value |
267 | 287 | ||
268 | ep_00x: |
288 | ep_00x: |
269 | ret |
289 | ret |
270 | 290 | ||
271 | ;*************************************************************************** |
291 | ;*************************************************************************** |
272 | ; Function |
292 | ; Function |
273 | ; ethernet_driver |
293 | ; ethernet_driver |
274 | ; |
294 | ; |
275 | ; Description |
295 | ; Description |
276 | ; The ethernet RX and TX handler |
296 | ; The ethernet RX and TX handler |
277 | ; This is a kernel function, called by stack_handler |
297 | ; This is a kernel function, called by stack_handler |
278 | ; |
298 | ; |
279 | ;*************************************************************************** |
299 | ;*************************************************************************** |
280 | ethernet_driver: |
300 | ethernet_driver: |
281 | ; Do nothing if the driver is inactive |
301 | ; Do nothing if the driver is inactive |
282 | cmp [ethernet_active], byte 0 |
302 | cmp [ethernet_active], byte 0 |
283 | je eth_exit |
303 | je eth_exit |
284 | 304 | ||
285 | call eth_rx |
305 | call eth_rx |
286 | call eth_tx |
306 | call eth_tx |
287 | 307 | ||
288 | eth_exit: |
308 | eth_exit: |
289 | ret |
309 | ret |
290 | 310 | ||
291 | ;*************************************************************************** |
311 | ;*************************************************************************** |
292 | ; Function |
312 | ; Function |
293 | ; eth_rx |
313 | ; eth_rx |
294 | ; |
314 | ; |
295 | ; Description |
315 | ; Description |
296 | ; Polls the ethernet card for received data. Extracts if present |
316 | ; Polls the ethernet card for received data. Extracts if present |
297 | ; Depending on the Protocol within the packet: |
317 | ; Depending on the Protocol within the packet: |
298 | ; ARP : Pass to ARP_handler. This may result in an ARP reply |
318 | ; ARP : Pass to ARP_handler. This may result in an ARP reply |
299 | ; being tx'ed |
319 | ; being tx'ed |
300 | ; IP : Store in an IP buffer |
320 | ; IP : Store in an IP buffer |
301 | ; |
321 | ; |
302 | ;*************************************************************************** |
322 | ;*************************************************************************** |
303 | eth_rx: |
323 | eth_rx: |
304 | xor ax, ax |
324 | xor ax, ax |
305 | mov [eth_rx_data_len], ax |
325 | mov [eth_rx_data_len], ax |
306 | call dword [drvr_poll] ; Call the drivers poll function |
326 | call dword [drvr_poll] ; Call the drivers poll function |
307 | 327 | ||
308 | mov ax, [eth_rx_data_len] |
328 | mov ax, [eth_rx_data_len] |
309 | cmp ax, 0 |
329 | cmp ax, 0 |
310 | je erx_exit |
330 | je erx_exit |
311 | 331 | ||
312 | if DEBUGGING_STATE = DEBUGGING_ENABLED |
332 | if DEBUGGING_STATE = DEBUGGING_ENABLED |
313 | pusha |
333 | pusha |
314 | mov eax, 0 ;Indicate that this is a received packet |
334 | mov eax, 0 ;Indicate that this is a received packet |
315 | mov cx, [eth_rx_data_len] |
335 | mov cx, [eth_rx_data_len] |
316 | mov esi, Ether_buffer |
336 | mov esi, Ether_buffer |
317 | cmp word [esi + 12], ETHER_IP |
337 | cmp word [esi + 12], ETHER_IP |
318 | jnz erxd_done |
338 | jnz erxd_done |
319 | ; cmp byte [esi + 14 + 9], 0x06 ; TCP |
339 | ; cmp byte [esi + 14 + 9], 0x06 ; TCP |
320 | ; jnz erxd_done |
340 | ; jnz erxd_done |
321 | call eth_dump |
341 | call eth_dump |
322 | erxd_done: |
342 | erxd_done: |
323 | popa |
343 | popa |
324 | end if |
344 | end if |
325 | 345 | ||
326 | ; Check the protocol. Call appropriate handler |
346 | ; Check the protocol. Call appropriate handler |
327 | mov eax, Ether_buffer |
347 | mov eax, Ether_buffer |
328 | add eax, 12 ; The address of the protocol word |
348 | add eax, 12 ; The address of the protocol word |
329 | 349 | ||
330 | mov ax, [eax] |
350 | mov ax, [eax] |
331 | 351 | ||
332 | cmp ax, ETHER_ARP |
352 | cmp ax, ETHER_ARP |
333 | je erx_001 ; It is ARP |
353 | je erx_001 ; It is ARP |
334 | 354 | ||
335 | cmp ax, ETHER_IP |
355 | cmp ax, ETHER_IP |
336 | je erx_002 ; It's IP |
356 | je erx_002 ; It's IP |
337 | 357 | ||
338 | ; inc dword [dumped_rx_count] |
358 | ; inc dword [dumped_rx_count] |
339 | 359 | ||
340 | jmp erx_exit ; If not IP or ARP, ignore |
360 | jmp erx_exit ; If not IP or ARP, ignore |
341 | 361 | ||
342 | erx_001: |
362 | erx_001: |
343 | mov eax, [arp_rx_count] |
363 | mov eax, [arp_rx_count] |
344 | inc eax |
364 | inc eax |
345 | mov [arp_rx_count], eax |
365 | mov [arp_rx_count], eax |
346 | 366 | ||
347 | ; At this point, the packet is still in the Ether_buffer |
367 | ; At this point, the packet is still in the Ether_buffer |
348 | call arp_handler |
368 | call arp_handler |
349 | 369 | ||
350 | jmp erx_exit |
370 | jmp erx_exit |
351 | 371 | ||
352 | erx_002: |
372 | erx_002: |
353 | mov eax, [ip_rx_count] |
373 | mov eax, [ip_rx_count] |
354 | inc eax |
374 | inc eax |
355 | mov [ip_rx_count], eax |
375 | mov [ip_rx_count], eax |
356 | 376 | ||
357 | ; Check to see if the MAC address is in our arp table |
377 | ; Check to see if the MAC address is in our arp table |
358 | ; refresh the arp ttl if so |
378 | ; refresh the arp ttl if so |
359 | 379 | ||
360 | mov esi, Ether_buffer |
380 | mov esi, Ether_buffer |
361 | add esi, 6 |
381 | add esi, 6 |
362 | 382 | ||
363 | call refreshARP |
383 | call refreshARP |
364 | 384 | ||
365 | call ether_IP_handler |
385 | call ether_IP_handler |
366 | 386 | ||
367 | jmp erx_exit |
387 | jmp erx_exit |
368 | 388 | ||
369 | erx_exit: |
389 | erx_exit: |
370 | ret |
390 | ret |
371 | 391 | ||
372 | ;*************************************************************************** |
392 | ;*************************************************************************** |
373 | ; Function |
393 | ; Function |
374 | ; eth_tx |
394 | ; eth_tx |
375 | ; |
395 | ; |
376 | ; Description |
396 | ; Description |
377 | ; Looks at the NET1OUT_QUEUE for data to send. |
397 | ; Looks at the NET1OUT_QUEUE for data to send. |
378 | ; Stores that destination IP in a location used by the tx routine |
398 | ; Stores that destination IP in a location used by the tx routine |
379 | ; Looks up the MAC address in the ARP table; stores that where |
399 | ; Looks up the MAC address in the ARP table; stores that where |
380 | ; the tx routine can get it |
400 | ; the tx routine can get it |
381 | ; Get the length of the data. Store that where the tx routine wants it |
401 | ; Get the length of the data. Store that where the tx routine wants it |
382 | ; Call tx |
402 | ; Call tx |
383 | ; Places buffer on empty queue when the tx routine finished |
403 | ; Places buffer on empty queue when the tx routine finished |
384 | ; |
404 | ; |
385 | ;*************************************************************************** |
405 | ;*************************************************************************** |
386 | eth_tx: |
406 | eth_tx: |
387 | ; Look for a buffer to tx |
407 | ; Look for a buffer to tx |
388 | mov eax, NET1OUT_QUEUE |
408 | mov eax, NET1OUT_QUEUE |
389 | call dequeue |
409 | call dequeue |
390 | cmp ax, NO_BUFFER |
410 | cmp ax, NO_BUFFER |
391 | je eth_exit ; Exit if no buffer available |
411 | je eth_exit ; Exit if no buffer available |
392 | 412 | ||
393 | push eax |
413 | push eax |
394 | 414 | ||
395 | ; convert buffer pointer eax to the absolute address |
415 | ; convert buffer pointer eax to the absolute address |
396 | mov ecx, IPBUFFSIZE |
416 | mov ecx, IPBUFFSIZE |
397 | mul ecx |
417 | mul ecx |
398 | add eax, IPbuffs |
418 | add eax, IPbuffs |
399 | 419 | ||
400 | ; Extract the destination IP |
420 | ; Extract the destination IP |
401 | ; find the destination IP in the ARP table, get MAC |
421 | ; find the destination IP in the ARP table, get MAC |
402 | ; store this MAC in 'MACAddress' |
422 | ; store this MAC in 'MACAddress' |
403 | mov ebx, eax ; Save buffer address |
423 | mov ebx, eax ; Save buffer address |
404 | mov edx, [ebx + 16] ; get destination address |
424 | mov edx, [ebx + 16] ; get destination address |
405 | 425 | ||
406 | ; If the destination address is 255.255.255.255, |
426 | ; If the destination address is 255.255.255.255, |
407 | ; set the MACAddress to all ones ( broadcast ) |
427 | ; set the MACAddress to all ones ( broadcast ) |
408 | mov [MACAddress], dword 0xffffffff |
428 | mov [MACAddress], dword 0xffffffff |
409 | mov [MACAddress + 4], word 0xffff |
429 | mov [MACAddress + 4], word 0xffff |
410 | cmp edx, 0xffffffff |
430 | cmp edx, 0xffffffff |
411 | je etx_send ; If it is broadcast, just send |
431 | je etx_send ; If it is broadcast, just send |
412 | 432 | ||
413 | call getMACfromIP ; Get the MAC address. |
433 | call getMACfromIP ; Get the MAC address. |
414 | 434 | ||
415 | cmp eax, ARP_VALID_MAPPING |
435 | cmp eax, ARP_VALID_MAPPING |
416 | jz etx_send |
436 | jz etx_send |
417 | 437 | ||
418 | ; No valid entry. Are we waiting for a response? |
438 | ; No valid entry. Are we waiting for a response? |
419 | cmp eax, ARP_AWAITING_RESPONSE |
439 | cmp eax, ARP_AWAITING_RESPONSE |
420 | jne etx_001 |
440 | jne etx_001 |
421 | 441 | ||
422 | ; Re-queue the packet, and exit |
442 | ; Re-queue the packet, and exit |
423 | pop ebx |
443 | pop ebx |
424 | mov eax, NET1OUT_QUEUE |
444 | mov eax, NET1OUT_QUEUE |
425 | call queue |
445 | call queue |
426 | jmp etx_exit |
446 | jmp etx_exit |
427 | 447 | ||
428 | etx_001: |
448 | etx_001: |
429 | ; HAs the request been sent, but timed out? |
449 | ; HAs the request been sent, but timed out? |
430 | cmp eax, ARP_RESPONSE_TIMEOUT |
450 | cmp eax, ARP_RESPONSE_TIMEOUT |
431 | jne etx_002 |
451 | jne etx_002 |
432 | 452 | ||
433 | pop eax |
453 | pop eax |
434 | call freeBuff |
454 | call freeBuff |
435 | jmp etx_exit |
455 | jmp etx_exit |
436 | 456 | ||
437 | etx_002: |
457 | etx_002: |
438 | ; There is no entry. Re queue the request, and ask ARP to send a request |
458 | ; There is no entry. Re queue the request, and ask ARP to send a request |
439 | 459 | ||
440 | ; IP address is in edx |
460 | ; IP address is in edx |
441 | push edx |
461 | push edx |
442 | call arp_request |
462 | call arp_request |
443 | pop ebx |
463 | pop ebx |
444 | 464 | ||
445 | ; Add an entry in the ARP table, awaiting response |
465 | ; Add an entry in the ARP table, awaiting response |
446 | 466 | ||
447 | cmp byte [NumARP], ARP_TABLE_SIZE |
467 | cmp byte [NumARP], ARP_TABLE_SIZE |
448 | je etx_003 ; We cannot add a new entry in the table |
468 | je etx_003 ; We cannot add a new entry in the table |
449 | 469 | ||
450 | inc byte [NumARP] |
470 | inc byte [NumARP] |
451 | 471 | ||
452 | movzx eax, byte [NumARP] |
472 | movzx eax, byte [NumARP] |
453 | mov ecx, ARP_ENTRY_SIZE |
473 | mov ecx, ARP_ENTRY_SIZE |
454 | mul ecx |
474 | mul ecx |
455 | sub eax, ARP_ENTRY_SIZE |
475 | sub eax, ARP_ENTRY_SIZE |
456 | 476 | ||
457 | mov [eax + ARPTable], ebx |
477 | mov [eax + ARPTable], ebx |
458 | xor ebx, ebx |
478 | xor ebx, ebx |
459 | mov [eax + ARPTable + 4], ebx |
479 | mov [eax + ARPTable + 4], ebx |
460 | mov [eax + ARPTable + 8], bx |
480 | mov [eax + ARPTable + 8], bx |
461 | 481 | ||
462 | ; set the status field up - awaiting response |
482 | ; set the status field up - awaiting response |
463 | mov cl, 0x00 |
483 | mov cl, 0x00 |
464 | mov [eax + ARPTable + 10], cl |
484 | mov [eax + ARPTable + 10], cl |
465 | mov cl, 0x02 |
485 | mov cl, 0x02 |
466 | mov [eax + ARPTable + 11], cl |
486 | mov [eax + ARPTable + 11], cl |
467 | 487 | ||
468 | ; Initialise the time to live field - 10s |
488 | ; Initialise the time to live field - 10s |
469 | mov cx, 0x000A |
489 | mov cx, 0x000A |
470 | mov [eax + ARPTable + 12], cx |
490 | mov [eax + ARPTable + 12], cx |
471 | 491 | ||
472 | etx_003: |
492 | etx_003: |
473 | pop ebx ; Get the buffer back |
493 | pop ebx ; Get the buffer back |
474 | mov eax, NET1OUT_QUEUE |
494 | mov eax, NET1OUT_QUEUE |
475 | call queue |
495 | call queue |
476 | jmp etx_exit |
496 | jmp etx_exit |
477 | 497 | ||
478 | etx_send: |
498 | etx_send: |
479 | xor ecx, ecx |
499 | xor ecx, ecx |
480 | mov ch, [ebx+2] |
500 | mov ch, [ebx+2] |
481 | mov cl, [ebx+3] ; ; Size of IP packet to send |
501 | mov cl, [ebx+3] ; ; Size of IP packet to send |
482 | 502 | ||
483 | mov esi, ebx |
503 | mov esi, ebx |
484 | 504 | ||
485 | mov edi, MACAddress |
505 | mov edi, MACAddress |
486 | 506 | ||
487 | if DEBUGGING_STATE = DEBUGGING_ENABLED |
507 | if DEBUGGING_STATE = DEBUGGING_ENABLED |
488 | pusha |
508 | pusha |
489 | mov cx, 42 |
509 | mov cx, 42 |
490 | mov eax, 1 ; Indicate that this is a tx packet |
510 | mov eax, 1 ; Indicate that this is a tx packet |
491 | call eth_dump |
511 | call eth_dump |
492 | popa |
512 | popa |
493 | end if |
513 | end if |
494 | 514 | ||
495 | mov bx, ETHER_IP |
515 | mov bx, ETHER_IP |
496 | call dword [drvr_transmit] ; Call the drivers transmit function |
516 | call dword [drvr_transmit] ; Call the drivers transmit function |
497 | 517 | ||
498 | ; OK, we have sent a packet, so increment the count |
518 | ; OK, we have sent a packet, so increment the count |
499 | inc dword [ip_tx_count] |
519 | inc dword [ip_tx_count] |
500 | 520 | ||
501 | ; And finally, return the buffer to the free queue |
521 | ; And finally, return the buffer to the free queue |
502 | pop eax |
522 | pop eax |
503 | call freeBuff |
523 | call freeBuff |
504 | 524 | ||
505 | etx_exit: |
525 | etx_exit: |
506 | ret |
526 | ret |
507 | 527 | ||
508 | ;*************************************************************************** |
528 | ;*************************************************************************** |
509 | ; Function |
529 | ; Function |
510 | ; ether_IP_handler |
530 | ; ether_IP_handler |
511 | ; |
531 | ; |
512 | ; Description |
532 | ; Description |
513 | ; Called when an IP ethernet packet is received on the ethernet |
533 | ; Called when an IP ethernet packet is received on the ethernet |
514 | ; Header + Data is in Ether_buffer[] |
534 | ; Header + Data is in Ether_buffer[] |
515 | ; We just need to get a buffer from the 'free' queue, and |
535 | ; We just need to get a buffer from the 'free' queue, and |
516 | ; store the packet in it, then insert the packet number into the |
536 | ; store the packet in it, then insert the packet number into the |
517 | ; IPRX queue. |
537 | ; IPRX queue. |
518 | ; If no queue entry is available, the packet is silently discarded |
538 | ; If no queue entry is available, the packet is silently discarded |
519 | ; All registers may be destroyed |
539 | ; All registers may be destroyed |
520 | ; |
540 | ; |
521 | ;*************************************************************************** |
541 | ;*************************************************************************** |
522 | ether_IP_handler: |
542 | ether_IP_handler: |
523 | mov eax, EMPTY_QUEUE |
543 | mov eax, EMPTY_QUEUE |
524 | call dequeue |
544 | call dequeue |
525 | cmp ax, NO_BUFFER |
545 | cmp ax, NO_BUFFER |
526 | je eiph00x |
546 | je eiph00x |
527 | 547 | ||
528 | ; convert buffer pointer eax to the absolute address |
548 | ; convert buffer pointer eax to the absolute address |
529 | push eax |
549 | push eax |
530 | mov ecx, IPBUFFSIZE |
550 | mov ecx, IPBUFFSIZE |
531 | mul ecx |
551 | mul ecx |
532 | add eax, IPbuffs |
552 | add eax, IPbuffs |
533 | 553 | ||
534 | mov edi, eax |
554 | mov edi, eax |
535 | 555 | ||
536 | ; get a pointer to the start of the DATA |
556 | ; get a pointer to the start of the DATA |
537 | mov esi, Ether_buffer + 14 |
557 | mov esi, Ether_buffer + 14 |
538 | 558 | ||
539 | ; Now store it all away |
559 | ; Now store it all away |
540 | mov ecx, IPBUFFSIZE / 4 ; Copy all of the available |
560 | mov ecx, IPBUFFSIZE / 4 ; Copy all of the available |
541 | ; data across - worse case |
561 | ; data across - worse case |
542 | cld |
562 | cld |
543 | rep movsd |
563 | rep movsd |
544 | 564 | ||
545 | ; And finally, place the buffer in the IPRX queue |
565 | ; And finally, place the buffer in the IPRX queue |
546 | pop ebx |
566 | pop ebx |
547 | mov eax, IPIN_QUEUE |
567 | mov eax, IPIN_QUEUE |
548 | call queue |
568 | call queue |
549 | 569 | ||
550 | eiph00x: |
570 | eiph00x: |
551 | ret |
571 | ret |
552 | 572 | ||
553 | ;*************************************************************************** |
573 | ;*************************************************************************** |
554 | ; |
574 | ; |
555 | ; ARP CODE FOLLOWS |
575 | ; ARP CODE FOLLOWS |
556 | ; |
576 | ; |
557 | ; The ARP code is used by ethernet drivers to translate an destination |
577 | ; The ARP code is used by ethernet drivers to translate an destination |
558 | ; IP address into an ethernet hardware address. Functions to broadcast |
578 | ; IP address into an ethernet hardware address. Functions to broadcast |
559 | ; requests and handle response are (or will be) here. |
579 | ; requests and handle response are (or will be) here. |
560 | ; The IP layer has no knowledge of ARP, as this is a network interface |
580 | ; The IP layer has no knowledge of ARP, as this is a network interface |
561 | ; issue |
581 | ; issue |
562 | ; |
582 | ; |
563 | ;*************************************************************************** |
583 | ;*************************************************************************** |
564 | 584 | ||
565 | ;*************************************************************************** |
585 | ;*************************************************************************** |
566 | ; Function |
586 | ; Function |
567 | ; arp_timer |
587 | ; arp_timer |
568 | ; |
588 | ; |
569 | ; Description |
589 | ; Description |
570 | ; Called every 1s |
590 | ; Called every 1s |
571 | ; It is responsible for removing expired routes |
591 | ; It is responsible for removing expired routes |
572 | ; All registers may be destroyed |
592 | ; All registers may be destroyed |
573 | ; |
593 | ; |
574 | ;*************************************************************************** |
594 | ;*************************************************************************** |
575 | arp_timer: |
595 | arp_timer: |
576 | ; loop through all the ARP entries, decrementing each one |
596 | ; loop through all the ARP entries, decrementing each one |
577 | ; that doesn't have a TTL of 0xFFFF |
597 | ; that doesn't have a TTL of 0xFFFF |
578 | movzx eax, byte [NumARP] |
598 | movzx eax, byte [NumARP] |
579 | 599 | ||
580 | arp_001: |
600 | arp_001: |
581 | cmp eax, 0 |
601 | cmp eax, 0 |
582 | je arp_003 |
602 | je arp_003 |
583 | 603 | ||
584 | push eax |
604 | push eax |
585 | dec eax |
605 | dec eax |
586 | mov ecx, ARP_ENTRY_SIZE |
606 | mov ecx, ARP_ENTRY_SIZE |
587 | mul ecx |
607 | mul ecx |
588 | cmp word [ eax + ARPTable + 12], 0xFFFF |
608 | cmp word [ eax + ARPTable + 12], 0xFFFF |
589 | je arp_002 |
609 | je arp_002 |
590 | 610 | ||
591 | cmp word [ eax + ARPTable + 12], 0 |
611 | cmp word [ eax + ARPTable + 12], 0 |
592 | je arp_002 |
612 | je arp_002 |
593 | 613 | ||
594 | dec word [eax + ARPTable + 12] |
614 | dec word [eax + ARPTable + 12] |
595 | 615 | ||
596 | arp_002: |
616 | arp_002: |
597 | pop eax |
617 | pop eax |
598 | dec eax |
618 | dec eax |
599 | jmp arp_001 |
619 | jmp arp_001 |
600 | 620 | ||
601 | ; Now, look for entries with a TTL of 0 |
621 | ; Now, look for entries with a TTL of 0 |
602 | ; Valid entries and response timeout entries get removed |
622 | ; Valid entries and response timeout entries get removed |
603 | ; awaiting response gets converted into a response timeout, with a |
623 | ; awaiting response gets converted into a response timeout, with a |
604 | ; short life time - this allows queued packets to be flushed |
624 | ; short life time - this allows queued packets to be flushed |
605 | arp_003: |
625 | arp_003: |
606 | movzx edx, byte [NumARP] |
626 | movzx edx, byte [NumARP] |
607 | cmp edx, 0 |
627 | cmp edx, 0 |
608 | je arp_exit |
628 | je arp_exit |
609 | 629 | ||
610 | ; EDX holds the # of entries to search through |
630 | ; EDX holds the # of entries to search through |
611 | mov eax, 0 |
631 | mov eax, 0 |
612 | 632 | ||
613 | arp_005: |
633 | arp_005: |
614 | cmp word [ eax + ARPTable + 12], 0 |
634 | cmp word [ eax + ARPTable + 12], 0 |
615 | jne arp_004 |
635 | jne arp_004 |
616 | 636 | ||
617 | ; If it's status code is 0001 or 0003, delete the entry |
637 | ; If it's status code is 0001 or 0003, delete the entry |
618 | cmp word [eax + ARPTable + 10], 0x0100 |
638 | cmp word [eax + ARPTable + 10], 0x0100 |
619 | je arp_007 |
639 | je arp_007 |
620 | cmp word [eax + ARPTable + 10], 0x0300 |
640 | cmp word [eax + ARPTable + 10], 0x0300 |
621 | je arp_007 |
641 | je arp_007 |
622 | 642 | ||
623 | ; The only other valid code is 0002 - indicating a |
643 | ; The only other valid code is 0002 - indicating a |
624 | ; timeout while waiting for a response. Change the |
644 | ; timeout while waiting for a response. Change the |
625 | ; entry to response timed out |
645 | ; entry to response timed out |
626 | 646 | ||
627 | mov [eax + ARPTable + 10], word 0x0300 |
647 | mov [eax + ARPTable + 10], word 0x0300 |
628 | mov [eax + ARPTable + 12], word 0x000A |
648 | mov [eax + ARPTable + 12], word 0x000A |
629 | jmp arp_004 |
649 | jmp arp_004 |
630 | 650 | ||
631 | arp_007: |
651 | arp_007: |
632 | ; Delete this entry |
652 | ; Delete this entry |
633 | mov edi, ARPTable |
653 | mov edi, ARPTable |
634 | add edi, eax |
654 | add edi, eax |
635 | mov esi, edi |
655 | mov esi, edi |
636 | add esi, ARP_ENTRY_SIZE |
656 | add esi, ARP_ENTRY_SIZE |
637 | 657 | ||
638 | mov ecx, (ARP_TABLE_SIZE - 1) * ARP_ENTRY_SIZE |
658 | mov ecx, (ARP_TABLE_SIZE - 1) * ARP_ENTRY_SIZE |
639 | sub ecx, eax |
659 | sub ecx, eax |
640 | 660 | ||
641 | rep movsb |
661 | rep movsb |
642 | 662 | ||
643 | dec byte [NumARP] |
663 | dec byte [NumARP] |
644 | jmp arp_006 |
664 | jmp arp_006 |
645 | 665 | ||
646 | arp_004: |
666 | arp_004: |
647 | add eax, ARP_ENTRY_SIZE |
667 | add eax, ARP_ENTRY_SIZE |
648 | arp_006: |
668 | arp_006: |
649 | dec edx |
669 | dec edx |
650 | cmp edx, 0 |
670 | cmp edx, 0 |
651 | jne arp_005 |
671 | jne arp_005 |
652 | 672 | ||
653 | arp_exit: |
673 | arp_exit: |
654 | ret |
674 | ret |
655 | 675 | ||
656 | ;*************************************************************************** |
676 | ;*************************************************************************** |
657 | ; Function |
677 | ; Function |
658 | ; arp_request |
678 | ; arp_request |
659 | ; |
679 | ; |
660 | ; Description |
680 | ; Description |
661 | ; Sends an ARP request on the ethernet |
681 | ; Sends an ARP request on the ethernet |
662 | ; The requested IP address is in edx |
682 | ; The requested IP address is in edx |
663 | ; All registers may be destroyed |
683 | ; All registers may be destroyed |
664 | ; |
684 | ; |
665 | ;*************************************************************************** |
685 | ;*************************************************************************** |
666 | arp_request: |
686 | arp_request: |
667 | mov ebx, Ether_buffer |
687 | mov ebx, Ether_buffer |
668 | mov ax, 0x0100 |
688 | mov ax, 0x0100 |
669 | mov [ebx], ax |
689 | mov [ebx], ax |
670 | add ebx, 2 |
690 | add ebx, 2 |
671 | 691 | ||
672 | mov ax, 0x0008 |
692 | mov ax, 0x0008 |
673 | mov [ebx], ax |
693 | mov [ebx], ax |
674 | add ebx, 2 |
694 | add ebx, 2 |
675 | 695 | ||
676 | mov ax, 0x0406 |
696 | mov ax, 0x0406 |
677 | mov [ebx], ax |
697 | mov [ebx], ax |
678 | add ebx, 2 |
698 | add ebx, 2 |
679 | 699 | ||
680 | mov ax, 0x0100 |
700 | mov ax, 0x0100 |
681 | mov [ebx], ax |
701 | mov [ebx], ax |
682 | add ebx, 2 |
702 | add ebx, 2 |
683 | 703 | ||
684 | mov ecx, node_addr |
704 | mov ecx, node_addr |
685 | mov eax, [ecx] |
705 | mov eax, [ecx] |
686 | mov [ebx], eax |
706 | mov [ebx], eax |
687 | add ecx, 4 |
707 | add ecx, 4 |
688 | add ebx, 4 |
708 | add ebx, 4 |
689 | mov ax, [ecx] |
709 | mov ax, [ecx] |
690 | mov [ebx], ax |
710 | mov [ebx], ax |
691 | add ebx, 2 |
711 | add ebx, 2 |
692 | mov eax, [stack_ip] |
712 | mov eax, [stack_ip] |
693 | mov [ebx], eax |
713 | mov [ebx], eax |
694 | add ebx, 4 |
714 | add ebx, 4 |
695 | 715 | ||
696 | xor eax, eax |
716 | xor eax, eax |
697 | mov [ebx], eax |
717 | mov [ebx], eax |
698 | add ebx, 4 |
718 | add ebx, 4 |
699 | mov [ebx], ax |
719 | mov [ebx], ax |
700 | 720 | ||
701 | add ebx, 2 |
721 | add ebx, 2 |
702 | mov [ebx], edx |
722 | mov [ebx], edx |
703 | 723 | ||
704 | ; Now, send it! |
724 | ; Now, send it! |
705 | 725 | ||
706 | ; Pointer to 48 bit destination address in edi |
726 | ; Pointer to 48 bit destination address in edi |
707 | ; Type of packet in bx |
727 | ; Type of packet in bx |
708 | ; size of packet in ecx |
728 | ; size of packet in ecx |
709 | ; pointer to packet data in esi |
729 | ; pointer to packet data in esi |
710 | mov edi, broadcast_add |
730 | mov edi, broadcast_add |
711 | 731 | ||
712 | ;if DEBUGGING_STATE = DEBUGGING_ENABLED |
732 | ;if DEBUGGING_STATE = DEBUGGING_ENABLED |
713 | ; pusha |
733 | ; pusha |
714 | ; mov eax, 1 ; Indicate that this is a tx packet |
734 | ; mov eax, 1 ; Indicate that this is a tx packet |
715 | ; mov ecx, 28 |
735 | ; mov ecx, 28 |
716 | ; mov esi, Ether_buffer |
736 | ; mov esi, Ether_buffer |
717 | ; call eth_dump |
737 | ; call eth_dump |
718 | ; popa |
738 | ; popa |
719 | ;end if |
739 | ;end if |
720 | 740 | ||
721 | mov bx, ETHER_ARP |
741 | mov bx, ETHER_ARP |
722 | mov ecx, 28 |
742 | mov ecx, 28 |
723 | mov esi, Ether_buffer |
743 | mov esi, Ether_buffer |
724 | call dword [drvr_transmit] ; Call the drivers transmit function |
744 | call dword [drvr_transmit] ; Call the drivers transmit function |
725 | ret |
745 | ret |
726 | 746 | ||
727 | ;*************************************************************************** |
747 | ;*************************************************************************** |
728 | ; Function |
748 | ; Function |
729 | ; arp_handler |
749 | ; arp_handler |
730 | ; |
750 | ; |
731 | ; Description |
751 | ; Description |
732 | ; Called when an ARP packet is received on the ethernet |
752 | ; Called when an ARP packet is received on the ethernet |
733 | ; Header + Data is in Ether_buffer[] |
753 | ; Header + Data is in Ether_buffer[] |
734 | ; It looks to see if the packet is a request to resolve this Hosts |
754 | ; It looks to see if the packet is a request to resolve this Hosts |
735 | ; IP address. If it is, send the ARP reply packet. |
755 | ; IP address. If it is, send the ARP reply packet. |
736 | ; This Hosts IP address is in dword [stack_ip] ( in network format ) |
756 | ; This Hosts IP address is in dword [stack_ip] ( in network format ) |
737 | ; This Hosts MAC address is in node_addr[6] |
757 | ; This Hosts MAC address is in node_addr[6] |
738 | ; All registers may be destroyed |
758 | ; All registers may be destroyed |
739 | ; |
759 | ; |
740 | ;*************************************************************************** |
760 | ;*************************************************************************** |
741 | arp_handler: |
761 | arp_handler: |
742 | ; Is this a REQUEST? |
762 | ; Is this a REQUEST? |
743 | ; Is this a request for My Host IP |
763 | ; Is this a request for My Host IP |
744 | ; Yes - So construct a response message. |
764 | ; Yes - So construct a response message. |
745 | ; Send this message to the ethernet card for transmission |
765 | ; Send this message to the ethernet card for transmission |
746 | 766 | ||
747 | mov ebx, Ether_buffer |
767 | mov ebx, Ether_buffer |
748 | 768 | ||
749 | mov edx, ebx |
769 | mov edx, ebx |
750 | add edx, 20 |
770 | add edx, 20 |
751 | mov ax, [edx] |
771 | mov ax, [edx] |
752 | cmp ax, ARP_REQ_OPCODE ; Is this a request packet? |
772 | cmp ax, ARP_REQ_OPCODE ; Is this a request packet? |
753 | jne arph_resp ; No - so test for response |
773 | jne arph_resp ; No - so test for response |
754 | 774 | ||
755 | mov edx, ebx |
775 | mov edx, ebx |
756 | add edx, 38 |
776 | add edx, 38 |
757 | mov eax, [edx] |
777 | mov eax, [edx] |
758 | 778 | ||
759 | cmp eax, [stack_ip] ; Is it looking for my IP address? |
779 | cmp eax, [stack_ip] ; Is it looking for my IP address? |
760 | jne arph_exit ; No - so quit now |
780 | jne arph_exit ; No - so quit now |
761 | 781 | ||
762 | ; OK, it is a request for my MAC address. Build the frame and send it |
782 | ; OK, it is a request for my MAC address. Build the frame and send it |
763 | 783 | ||
764 | ; Save the important data from the original packet |
784 | ; Save the important data from the original packet |
765 | ; remote MAC address first |
785 | ; remote MAC address first |
766 | mov ecx, remote_hw_add |
786 | mov ecx, remote_hw_add |
767 | mov edx, ebx |
787 | mov edx, ebx |
768 | add edx, 22 ; edx points to Source h/w address |
788 | add edx, 22 ; edx points to Source h/w address |
769 | mov eax, [edx] |
789 | mov eax, [edx] |
770 | mov [ecx], eax |
790 | mov [ecx], eax |
771 | add edx, 4 |
791 | add edx, 4 |
772 | add ecx, 4 |
792 | add ecx, 4 |
773 | mov ax, [edx] |
793 | mov ax, [edx] |
774 | mov [ecx],ax |
794 | mov [ecx],ax |
775 | 795 | ||
776 | ; and also the remote IP address |
796 | ; and also the remote IP address |
777 | add edx, 2 |
797 | add edx, 2 |
778 | mov eax,[edx] |
798 | mov eax,[edx] |
779 | mov [remote_ip_add], eax |
799 | mov [remote_ip_add], eax |
780 | 800 | ||
781 | ; So now we can reuse the packet. ebx still holds the address of |
801 | ; So now we can reuse the packet. ebx still holds the address of |
782 | ; the header + packet |
802 | ; the header + packet |
783 | ; We dont need the header ( first 14 bytes ) |
803 | ; We dont need the header ( first 14 bytes ) |
784 | 804 | ||
785 | mov edx, ebx |
805 | mov edx, ebx |
786 | add edx, 20 |
806 | add edx, 20 |
787 | mov ax, ARP_REP_OPCODE |
807 | mov ax, ARP_REP_OPCODE |
788 | mov [edx], ax |
808 | mov [edx], ax |
789 | add edx, 2 |
809 | add edx, 2 |
790 | 810 | ||
791 | mov ecx, node_addr |
811 | mov ecx, node_addr |
792 | mov eax, [ecx] |
812 | mov eax, [ecx] |
793 | mov [edx], eax |
813 | mov [edx], eax |
794 | add ecx, 4 |
814 | add ecx, 4 |
795 | add edx, 4 |
815 | add edx, 4 |
796 | mov ax, [ecx] |
816 | mov ax, [ecx] |
797 | mov [edx], ax |
817 | mov [edx], ax |
798 | add edx, 2 |
818 | add edx, 2 |
799 | mov eax, [stack_ip] |
819 | mov eax, [stack_ip] |
800 | mov [edx], eax |
820 | mov [edx], eax |
801 | add edx, 4 |
821 | add edx, 4 |
802 | mov ecx, remote_hw_add |
822 | mov ecx, remote_hw_add |
803 | mov eax, [ecx] |
823 | mov eax, [ecx] |
804 | mov [edx], eax |
824 | mov [edx], eax |
805 | add ecx, 4 |
825 | add ecx, 4 |
806 | add edx, 4 |
826 | add edx, 4 |
807 | mov ax, [ecx] |
827 | mov ax, [ecx] |
808 | mov [edx], ax |
828 | mov [edx], ax |
809 | 829 | ||
810 | add edx, 2 |
830 | add edx, 2 |
811 | mov eax, [remote_ip_add] |
831 | mov eax, [remote_ip_add] |
812 | mov [edx], eax |
832 | mov [edx], eax |
813 | 833 | ||
814 | ; Now, send it! |
834 | ; Now, send it! |
815 | 835 | ||
816 | ; Pointer to 48 bit destination address in edi |
836 | ; Pointer to 48 bit destination address in edi |
817 | ; Type of packet in bx |
837 | ; Type of packet in bx |
818 | ; size of packet in ecx |
838 | ; size of packet in ecx |
819 | ; pointer to packet data in esi |
839 | ; pointer to packet data in esi |
820 | mov edi, remote_hw_add |
840 | mov edi, remote_hw_add |
821 | 841 | ||
822 | ;if DEBUGGING_STATE = DEBUGGING_ENABLED |
842 | ;if DEBUGGING_STATE = DEBUGGING_ENABLED |
823 | ; pusha |
843 | ; pusha |
824 | ; mov eax, 1 ; Indicate that this is a tx packet |
844 | ; mov eax, 1 ; Indicate that this is a tx packet |
825 | ; mov ecx, 28 |
845 | ; mov ecx, 28 |
826 | ; mov esi, Ether_buffer + 14 |
846 | ; mov esi, Ether_buffer + 14 |
827 | ; call eth_dump |
847 | ; call eth_dump |
828 | ; popa |
848 | ; popa |
829 | ;end if |
849 | ;end if |
830 | 850 | ||
831 | mov bx, ETHER_ARP |
851 | mov bx, ETHER_ARP |
832 | mov ecx, 28 |
852 | mov ecx, 28 |
833 | mov esi, Ether_buffer + 14 |
853 | mov esi, Ether_buffer + 14 |
834 | call dword [drvr_transmit] ; Call the drivers transmit function |
854 | call dword [drvr_transmit] ; Call the drivers transmit function |
835 | jmp arph_exit |
855 | jmp arph_exit |
836 | 856 | ||
837 | arph_resp: |
857 | arph_resp: |
838 | cmp ax, ARP_REP_OPCODE ; Is this a replypacket? |
858 | cmp ax, ARP_REP_OPCODE ; Is this a replypacket? |
839 | jne arph_resp ; No - so quit |
859 | jne arph_resp ; No - so quit |
840 | 860 | ||
841 | ; This was a reply, probably directed at me. |
861 | ; This was a reply, probably directed at me. |
842 | ; save the remotes MAC & IP |
862 | ; save the remotes MAC & IP |
843 | mov ecx, remote_hw_add |
863 | mov ecx, remote_hw_add |
844 | mov edx, ebx |
864 | mov edx, ebx |
845 | add edx, 22 ; edx points to Source h/w address |
865 | add edx, 22 ; edx points to Source h/w address |
846 | mov eax, [edx] |
866 | mov eax, [edx] |
847 | mov [ecx], eax |
867 | mov [ecx], eax |
848 | add edx, 4 |
868 | add edx, 4 |
849 | add ecx, 4 |
869 | add ecx, 4 |
850 | mov ax, [edx] |
870 | mov ax, [edx] |
851 | mov [ecx],ax |
871 | mov [ecx],ax |
852 | 872 | ||
853 | ; and also the remote IP address |
873 | ; and also the remote IP address |
854 | add edx, 2 |
874 | add edx, 2 |
855 | mov eax,[edx] |
875 | mov eax,[edx] |
856 | mov [remote_ip_add], eax |
876 | mov [remote_ip_add], eax |
857 | 877 | ||
858 | ; Now, add an entry in the table for this IP address if it doesn't exist |
878 | ; Now, add an entry in the table for this IP address if it doesn't exist |
859 | 879 | ||
860 | push eax |
880 | push eax |
861 | movzx eax, byte [NumARP] |
881 | movzx eax, byte [NumARP] |
862 | mov ecx, ARP_ENTRY_SIZE |
882 | mov ecx, ARP_ENTRY_SIZE |
863 | mul ecx |
883 | mul ecx |
864 | pop edx |
884 | pop edx |
865 | movzx ecx, byte [NumARP] |
885 | movzx ecx, byte [NumARP] |
866 | cmp ecx, 0 |
886 | cmp ecx, 0 |
867 | je arph_002 |
887 | je arph_002 |
868 | 888 | ||
869 | arph_001: |
889 | arph_001: |
870 | sub eax, ARP_ENTRY_SIZE |
890 | sub eax, ARP_ENTRY_SIZE |
871 | cmp [eax + ARPTable], edx |
891 | cmp [eax + ARPTable], edx |
872 | loopnz arph_001 ; Return back if non match |
892 | loopnz arph_001 ; Return back if non match |
873 | 893 | ||
874 | jnz arph_002 ; None found, add to end |
894 | jnz arph_002 ; None found, add to end |
875 | 895 | ||
876 | mov ecx, [remote_hw_add] |
896 | mov ecx, [remote_hw_add] |
877 | mov [eax + ARPTable + 4], ecx |
897 | mov [eax + ARPTable + 4], ecx |
878 | mov cx, [remote_hw_add+4] |
898 | mov cx, [remote_hw_add+4] |
879 | mov [eax + ARPTable + 8], cx |
899 | mov [eax + ARPTable + 8], cx |
880 | 900 | ||
881 | ; specify the type - a valid entry |
901 | ; specify the type - a valid entry |
882 | mov cl, 0x00 |
902 | mov cl, 0x00 |
883 | mov [eax + ARPTable + 10], cl |
903 | mov [eax + ARPTable + 10], cl |
884 | mov cl, 0x01 |
904 | mov cl, 0x01 |
885 | mov [eax + ARPTable + 11], cl |
905 | mov [eax + ARPTable + 11], cl |
886 | 906 | ||
887 | ; Initialise the time to live field - 1 hour |
907 | ; Initialise the time to live field - 1 hour |
888 | mov cx, 0x0E10 |
908 | mov cx, 0x0E10 |
889 | mov [eax + ARPTable + 12], cx |
909 | mov [eax + ARPTable + 12], cx |
890 | jmp arph_exit |
910 | jmp arph_exit |
891 | 911 | ||
892 | arph_002: |
912 | arph_002: |
893 | 913 | ||
894 | cmp byte [NumARP], ARP_TABLE_SIZE |
914 | cmp byte [NumARP], ARP_TABLE_SIZE |
895 | je arph_exit |
915 | je arph_exit |
896 | 916 | ||
897 | inc byte [NumARP] |
917 | inc byte [NumARP] |
898 | 918 | ||
899 | movzx eax, byte [NumARP] |
919 | movzx eax, byte [NumARP] |
900 | mov ecx, ARP_ENTRY_SIZE |
920 | mov ecx, ARP_ENTRY_SIZE |
901 | mul ecx |
921 | mul ecx |
902 | sub eax, ARP_ENTRY_SIZE |
922 | sub eax, ARP_ENTRY_SIZE |
903 | 923 | ||
904 | mov ecx, [remote_ip_add] |
924 | mov ecx, [remote_ip_add] |
905 | mov [eax + ARPTable], ecx |
925 | mov [eax + ARPTable], ecx |
906 | mov ecx, [remote_hw_add] |
926 | mov ecx, [remote_hw_add] |
907 | mov [eax + ARPTable + 4], ecx |
927 | mov [eax + ARPTable + 4], ecx |
908 | mov cx, [remote_hw_add+4] |
928 | mov cx, [remote_hw_add+4] |
909 | mov [eax + ARPTable + 8], cx |
929 | mov [eax + ARPTable + 8], cx |
910 | 930 | ||
911 | mov cl, 0x00 |
931 | mov cl, 0x00 |
912 | mov [eax + ARPTable + 10], cl |
932 | mov [eax + ARPTable + 10], cl |
913 | mov cl, 0x01 |
933 | mov cl, 0x01 |
914 | mov [eax + ARPTable + 11], cl |
934 | mov [eax + ARPTable + 11], cl |
915 | 935 | ||
916 | ; Initialise the time to live field - 1 hour |
936 | ; Initialise the time to live field - 1 hour |
917 | mov cx, 0x0E10 |
937 | mov cx, 0x0E10 |
918 | mov [eax + ARPTable + 12], cx |
938 | mov [eax + ARPTable + 12], cx |
919 | 939 | ||
920 | arph_exit: |
940 | arph_exit: |
921 | ret |
941 | ret |
922 | 942 | ||
923 | ; pointer to MAC in esi |
943 | ; pointer to MAC in esi |
924 | refreshARP: |
944 | refreshARP: |
925 | mov ebx, [esi] |
945 | mov ebx, [esi] |
926 | mov dx, [esi+4] |
946 | mov dx, [esi+4] |
927 | push edx |
947 | push edx |
928 | movzx eax, byte [NumARP] |
948 | movzx eax, byte [NumARP] |
929 | mov ecx, ARP_ENTRY_SIZE |
949 | mov ecx, ARP_ENTRY_SIZE |
930 | mul ecx |
950 | mul ecx |
931 | pop edx |
951 | pop edx |
932 | movzx ecx, byte [NumARP] |
952 | movzx ecx, byte [NumARP] |
933 | cmp ecx, 0 |
953 | cmp ecx, 0 |
934 | je rf_exit |
954 | je rf_exit |
935 | 955 | ||
936 | rf_001: |
956 | rf_001: |
937 | sub eax, ARP_ENTRY_SIZE |
957 | sub eax, ARP_ENTRY_SIZE |
938 | cmp [eax + ARPTable+4], ebx |
958 | cmp [eax + ARPTable+4], ebx |
939 | 959 | ||
940 | je rf_002 |
960 | je rf_002 |
941 | loop rf_001 |
961 | loop rf_001 |
942 | jmp rf_exit |
962 | jmp rf_exit |
943 | 963 | ||
944 | rf_002: |
964 | rf_002: |
945 | cmp [eax + ARPTable+8], dx |
965 | cmp [eax + ARPTable+8], dx |
946 | je rf_gotone |
966 | je rf_gotone |
947 | loop rf_001 |
967 | loop rf_001 |
948 | jmp rf_exit |
968 | jmp rf_exit |
949 | 969 | ||
950 | rf_gotone: |
970 | rf_gotone: |
951 | ; Initialise the time to live field - 1 hour |
971 | ; Initialise the time to live field - 1 hour |
952 | mov cx, 0x0E10 |
972 | mov cx, 0x0E10 |
953 | mov [eax + ARPTable + 12], cx |
973 | mov [eax + ARPTable + 12], cx |
954 | 974 | ||
955 | rf_exit: |
975 | rf_exit: |
956 | ret |
976 | ret |
957 | 977 | ||
958 | ;*************************************************************************** |
978 | ;*************************************************************************** |
959 | ; Function |
979 | ; Function |
960 | ; getMACfromIP |
980 | ; getMACfromIP |
961 | ; |
981 | ; |
962 | ; Description |
982 | ; Description |
963 | ; Takes an IP address in edx and scans the ARP table for |
983 | ; Takes an IP address in edx and scans the ARP table for |
964 | ; a matching entry |
984 | ; a matching entry |
965 | ; If a match is found, it's MAC address is stored in MACAddress. |
985 | ; If a match is found, it's MAC address is stored in MACAddress. |
966 | ; Otherwise the value 0 is writen to MACAddress |
986 | ; Otherwise the value 0 is writen to MACAddress |
967 | ; eax holds ARP table entry status code ( ARP_ ) |
987 | ; eax holds ARP table entry status code ( ARP_ ) |
968 | ; ebx unchanged |
988 | ; ebx unchanged |
969 | ; |
989 | ; |
970 | ;*************************************************************************** |
990 | ;*************************************************************************** |
971 | getMACfromIP: |
991 | getMACfromIP: |
972 | ; first, check destination IP to see if it is on 'this' network. |
992 | ; first, check destination IP to see if it is on 'this' network. |
973 | ; The test is: |
993 | ; The test is: |
974 | ; if ( destIP & subnet_mask == stack_ip & subnet_mask ) |
994 | ; if ( destIP & subnet_mask == stack_ip & subnet_mask ) |
975 | ; desitnation is local |
995 | ; desitnation is local |
976 | ; else |
996 | ; else |
977 | ; destination is remote, so pass to gateway |
997 | ; destination is remote, so pass to gateway |
978 | 998 | ||
979 | mov eax, edx |
999 | mov eax, edx |
980 | and eax, [subnet_mask] |
1000 | and eax, [subnet_mask] |
981 | mov ecx, [stack_ip] |
1001 | mov ecx, [stack_ip] |
982 | and ecx, [subnet_mask] |
1002 | and ecx, [subnet_mask] |
983 | cmp eax, ecx |
1003 | cmp eax, ecx |
984 | je gm0 |
1004 | je gm0 |
985 | 1005 | ||
986 | mov edx, [gateway_ip] |
1006 | mov edx, [gateway_ip] |
987 | gm0: |
1007 | gm0: |
988 | push edx |
1008 | push edx |
989 | xor eax, eax |
1009 | xor eax, eax |
990 | mov [MACAddress], eax |
1010 | mov [MACAddress], eax |
991 | mov [MACAddress + 4], ax |
1011 | mov [MACAddress + 4], ax |
992 | 1012 | ||
993 | movzx eax, byte [NumARP] |
1013 | movzx eax, byte [NumARP] |
994 | mov ecx, ARP_ENTRY_SIZE |
1014 | mov ecx, ARP_ENTRY_SIZE |
995 | mul ecx |
1015 | mul ecx |
996 | 1016 | ||
997 | pop edx |
1017 | pop edx |
998 | 1018 | ||
999 | movzx ecx, byte [NumARP] |
1019 | movzx ecx, byte [NumARP] |
1000 | cmp ecx, 0 |
1020 | cmp ecx, 0 |
1001 | je gm_none |
1021 | je gm_none |
1002 | gm1: |
1022 | gm1: |
1003 | sub eax, ARP_ENTRY_SIZE |
1023 | sub eax, ARP_ENTRY_SIZE |
1004 | cmp [eax + ARPTable], edx |
1024 | cmp [eax + ARPTable], edx |
1005 | loopnz gm1 ; Return back if non match |
1025 | loopnz gm1 ; Return back if non match |
1006 | jnz gm_none ; Quit if none found |
1026 | jnz gm_none ; Quit if none found |
1007 | 1027 | ||
1008 | ; eax holds index |
1028 | ; eax holds index |
1009 | mov ecx, [eax + ARPTable + 4] |
1029 | mov ecx, [eax + ARPTable + 4] |
1010 | mov [MACAddress], ecx |
1030 | mov [MACAddress], ecx |
1011 | mov cx, [eax + ARPTable + 8] |
1031 | mov cx, [eax + ARPTable + 8] |
1012 | mov [MACAddress+4], cx |
1032 | mov [MACAddress+4], cx |
1013 | 1033 | ||
1014 | ; Return the entry status in eax |
1034 | ; Return the entry status in eax |
1015 | mov ch, [eax + ARPTable + 10] |
1035 | mov ch, [eax + ARPTable + 10] |
1016 | mov cl, [eax + ARPTable + 11] |
1036 | mov cl, [eax + ARPTable + 11] |
1017 | movzx eax, cx |
1037 | movzx eax, cx |
1018 | jmp gm_exit |
1038 | jmp gm_exit |
1019 | 1039 | ||
1020 | gm_none: |
1040 | gm_none: |
1021 | mov eax, ARP_NO_ENTRY |
1041 | mov eax, ARP_NO_ENTRY |
1022 | 1042 | ||
1023 | gm_exit: |
1043 | gm_exit: |
1024 | ret |
1044 | ret |
1025 | 1045 | ||
1026 | ;*************************************************************************** |
1046 | ;*************************************************************************** |
1027 | ; |
1047 | ; |
1028 | ; PCI CODE FOLLOWS |
1048 | ; PCI CODE FOLLOWS |
1029 | ; |
1049 | ; |
1030 | ; the following functions provide access to the PCI interface. |
1050 | ; the following functions provide access to the PCI interface. |
1031 | ; These functions are used by scan_bus, and also some ethernet drivers |
1051 | ; These functions are used by scan_bus, and also some ethernet drivers |
1032 | ; |
1052 | ; |
1033 | ;*************************************************************************** |
1053 | ;*************************************************************************** |
1034 | 1054 | ||
1035 | ;*************************************************************************** |
1055 | ;*************************************************************************** |
1036 | ; Function |
1056 | ; Function |
1037 | ; config_cmd |
1057 | ; config_cmd |
1038 | ; |
1058 | ; |
1039 | ; Description |
1059 | ; Description |
1040 | ; creates a command dword for use with the PCI bus |
1060 | ; creates a command dword for use with the PCI bus |
1041 | ; bus # in ebx |
1061 | ; bus # in ebx |
1042 | ; devfn in ecx |
1062 | ; devfn in ecx |
1043 | ; where in edx |
1063 | ; where in edx |
1044 | ; |
1064 | ; |
1045 | ; command dword returned in eax |
1065 | ; command dword returned in eax |
1046 | ; Only eax destroyed |
1066 | ; Only eax destroyed |
1047 | ;*************************************************************************** |
1067 | ;*************************************************************************** |
1048 | config_cmd: |
1068 | config_cmd: |
1049 | push ecx |
1069 | push ecx |
1050 | mov eax, ebx |
1070 | mov eax, ebx |
1051 | shl eax, 16 |
1071 | shl eax, 16 |
1052 | or eax, 0x80000000 |
1072 | or eax, 0x80000000 |
1053 | shl ecx, 8 |
1073 | shl ecx, 8 |
1054 | or eax, ecx |
1074 | or eax, ecx |
1055 | pop ecx |
1075 | pop ecx |
1056 | or eax, edx |
1076 | or eax, edx |
1057 | and eax, 0xFFFFFFFC |
1077 | and eax, 0xFFFFFFFC |
1058 | ret |
1078 | ret |
1059 | 1079 | ||
1060 | ;*************************************************************************** |
1080 | ;*************************************************************************** |
1061 | ; Function |
1081 | ; Function |
1062 | ; pcibios_read_config_byte |
1082 | ; pcibios_read_config_byte |
1063 | ; |
1083 | ; |
1064 | ; Description |
1084 | ; Description |
1065 | ; reads a byte from the PCI config space |
1085 | ; reads a byte from the PCI config space |
1066 | ; bus # in ebx |
1086 | ; bus # in ebx |
1067 | ; devfn in ecx |
1087 | ; devfn in ecx |
1068 | ; where in edx ( ls 16 bits significant ) |
1088 | ; where in edx ( ls 16 bits significant ) |
1069 | ; |
1089 | ; |
1070 | ; byte returned in al ( rest of eax zero ) |
1090 | ; byte returned in al ( rest of eax zero ) |
1071 | ; Only eax/edx destroyed |
1091 | ; Only eax/edx destroyed |
1072 | ;*************************************************************************** |
1092 | ;*************************************************************************** |
1073 | pcibios_read_config_byte: |
1093 | pcibios_read_config_byte: |
1074 | call config_cmd |
1094 | call config_cmd |
1075 | push dx |
1095 | push dx |
1076 | mov dx, 0xCF8 |
1096 | mov dx, 0xCF8 |
1077 | out dx, eax |
1097 | out dx, eax |
1078 | pop dx |
1098 | pop dx |
1079 | 1099 | ||
1080 | xor eax, eax |
1100 | xor eax, eax |
1081 | and dx, 0x03 |
1101 | and dx, 0x03 |
1082 | add dx, 0xCFC |
1102 | add dx, 0xCFC |
1083 | ; and dx, 0xFFC |
1103 | ; and dx, 0xFFC |
1084 | in al, dx |
1104 | in al, dx |
1085 | ret |
1105 | ret |
1086 | 1106 | ||
1087 | ;*************************************************************************** |
1107 | ;*************************************************************************** |
1088 | ; Function |
1108 | ; Function |
1089 | ; pcibios_read_config_word |
1109 | ; pcibios_read_config_word |
1090 | ; |
1110 | ; |
1091 | ; Description |
1111 | ; Description |
1092 | ; reads a word from the PCI config space |
1112 | ; reads a word from the PCI config space |
1093 | ; bus # in ebx |
1113 | ; bus # in ebx |
1094 | ; devfn in ecx |
1114 | ; devfn in ecx |
1095 | ; where in edx ( ls 16 bits significant ) |
1115 | ; where in edx ( ls 16 bits significant ) |
1096 | ; |
1116 | ; |
1097 | ; word returned in ax ( rest of eax zero ) |
1117 | ; word returned in ax ( rest of eax zero ) |
1098 | ; Only eax/edx destroyed |
1118 | ; Only eax/edx destroyed |
1099 | ;*************************************************************************** |
1119 | ;*************************************************************************** |
1100 | pcibios_read_config_word: |
1120 | pcibios_read_config_word: |
1101 | call config_cmd |
1121 | call config_cmd |
1102 | push dx |
1122 | push dx |
1103 | mov dx, 0xCF8 |
1123 | mov dx, 0xCF8 |
1104 | out dx, eax |
1124 | out dx, eax |
1105 | pop dx |
1125 | pop dx |
1106 | 1126 | ||
1107 | xor eax, eax |
1127 | xor eax, eax |
1108 | and dx, 0x02 |
1128 | and dx, 0x02 |
1109 | add dx, 0xCFC |
1129 | add dx, 0xCFC |
1110 | ; and dx, 0xFFC |
1130 | ; and dx, 0xFFC |
1111 | in ax, dx |
1131 | in ax, dx |
1112 | ret |
1132 | ret |
1113 | 1133 | ||
1114 | ;*************************************************************************** |
1134 | ;*************************************************************************** |
1115 | ; Function |
1135 | ; Function |
1116 | ; pcibios_read_config_dword |
1136 | ; pcibios_read_config_dword |
1117 | ; |
1137 | ; |
1118 | ; Description |
1138 | ; Description |
1119 | ; reads a dword from the PCI config space |
1139 | ; reads a dword from the PCI config space |
1120 | ; bus # in ebx |
1140 | ; bus # in ebx |
1121 | ; devfn in ecx |
1141 | ; devfn in ecx |
1122 | ; where in edx ( ls 16 bits significant ) |
1142 | ; where in edx ( ls 16 bits significant ) |
1123 | ; |
1143 | ; |
1124 | ; dword returned in eax |
1144 | ; dword returned in eax |
1125 | ; Only eax/edx destroyed |
1145 | ; Only eax/edx destroyed |
1126 | ;*************************************************************************** |
1146 | ;*************************************************************************** |
1127 | pcibios_read_config_dword: |
1147 | pcibios_read_config_dword: |
1128 | push edx |
1148 | push edx |
1129 | call config_cmd |
1149 | call config_cmd |
1130 | push dx |
1150 | push dx |
1131 | mov dx, 0xCF8 |
1151 | mov dx, 0xCF8 |
1132 | out dx, eax |
1152 | out dx, eax |
1133 | pop dx |
1153 | pop dx |
1134 | xor eax, eax |
1154 | xor eax, eax |
1135 | mov dx, 0xCFC |
1155 | mov dx, 0xCFC |
1136 | in eax, dx |
1156 | in eax, dx |
1137 | pop edx |
1157 | pop edx |
1138 | ret |
1158 | ret |
1139 | 1159 | ||
1140 | ;*************************************************************************** |
1160 | ;*************************************************************************** |
1141 | ; Function |
1161 | ; Function |
1142 | ; pcibios_write_config_byte |
1162 | ; pcibios_write_config_byte |
1143 | ; |
1163 | ; |
1144 | ; Description |
1164 | ; Description |
1145 | ; write a byte in al to the PCI config space |
1165 | ; write a byte in al to the PCI config space |
1146 | ; bus # in ebx |
1166 | ; bus # in ebx |
1147 | ; devfn in ecx |
1167 | ; devfn in ecx |
1148 | ; where in edx ( ls 16 bits significant ) |
1168 | ; where in edx ( ls 16 bits significant ) |
1149 | ; |
1169 | ; |
1150 | ; Only eax/edx destroyed |
1170 | ; Only eax/edx destroyed |
1151 | ;*************************************************************************** |
1171 | ;*************************************************************************** |
1152 | pcibios_write_config_byte: |
1172 | pcibios_write_config_byte: |
1153 | push ax |
1173 | push ax |
1154 | call config_cmd |
1174 | call config_cmd |
1155 | push dx |
1175 | push dx |
1156 | mov dx, 0xCF8 |
1176 | mov dx, 0xCF8 |
1157 | out dx, eax |
1177 | out dx, eax |
1158 | pop dx |
1178 | pop dx |
1159 | pop ax |
1179 | pop ax |
1160 | 1180 | ||
1161 | and dx, 0x03 |
1181 | and dx, 0x03 |
1162 | add dx, 0xCFC |
1182 | add dx, 0xCFC |
1163 | out dx, al |
1183 | out dx, al |
1164 | ret |
1184 | ret |
1165 | 1185 | ||
1166 | ;*************************************************************************** |
1186 | ;*************************************************************************** |
1167 | ; Function |
1187 | ; Function |
1168 | ; pcibios_write_config_word |
1188 | ; pcibios_write_config_word |
1169 | ; |
1189 | ; |
1170 | ; Description |
1190 | ; Description |
1171 | ; write a word in ax to the PCI config space |
1191 | ; write a word in ax to the PCI config space |
1172 | ; bus # in ebx |
1192 | ; bus # in ebx |
1173 | ; devfn in ecx |
1193 | ; devfn in ecx |
1174 | ; where in edx ( ls 16 bits significant ) |
1194 | ; where in edx ( ls 16 bits significant ) |
1175 | ; |
1195 | ; |
1176 | ; Only eax/edx destroyed |
1196 | ; Only eax/edx destroyed |
1177 | ;*************************************************************************** |
1197 | ;*************************************************************************** |
1178 | pcibios_write_config_word: |
1198 | pcibios_write_config_word: |
1179 | push ax |
1199 | push ax |
1180 | call config_cmd |
1200 | call config_cmd |
1181 | push dx |
1201 | push dx |
1182 | mov dx, 0xCF8 |
1202 | mov dx, 0xCF8 |
1183 | out dx, eax |
1203 | out dx, eax |
1184 | pop dx |
1204 | pop dx |
1185 | pop ax |
1205 | pop ax |
1186 | 1206 | ||
1187 | and dx, 0x02 |
1207 | and dx, 0x02 |
1188 | add dx, 0xCFC |
1208 | add dx, 0xCFC |
1189 | out dx, ax |
1209 | out dx, ax |
1190 | ret |
1210 | ret |
1191 | 1211 | ||
1192 | ;*************************************************************************** |
1212 | ;*************************************************************************** |
1193 | ; Function |
1213 | ; Function |
1194 | ; delay_us |
1214 | ; delay_us |
1195 | ; |
1215 | ; |
1196 | ; Description |
1216 | ; Description |
1197 | ; delays for 30 to 60 us |
1217 | ; delays for 30 to 60 us |
1198 | ; |
1218 | ; |
1199 | ; I would prefer this routine to be able to delay for |
1219 | ; I would prefer this routine to be able to delay for |
1200 | ; a selectable number of microseconds, but this works for now. |
1220 | ; a selectable number of microseconds, but this works for now. |
1201 | ; |
1221 | ; |
1202 | ; If you know a better way to do 2us delay, pleae tell me! |
1222 | ; If you know a better way to do 2us delay, pleae tell me! |
1203 | ;*************************************************************************** |
1223 | ;*************************************************************************** |
1204 | delay_us: |
1224 | delay_us: |
1205 | push eax |
1225 | push eax |
1206 | push ecx |
1226 | push ecx |
1207 | 1227 | ||
1208 | mov ecx,2 |
1228 | mov ecx,2 |
1209 | 1229 | ||
1210 | in al,0x61 |
1230 | in al,0x61 |
1211 | and al,0x10 |
1231 | and al,0x10 |
1212 | mov ah,al |
1232 | mov ah,al |
1213 | cld |
1233 | cld |
1214 | 1234 | ||
1215 | dcnt1: |
1235 | dcnt1: |
1216 | in al,0x61 |
1236 | in al,0x61 |
1217 | and al,0x10 |
1237 | and al,0x10 |
1218 | cmp al,ah |
1238 | cmp al,ah |
1219 | jz dcnt1 |
1239 | jz dcnt1 |
1220 | 1240 | ||
1221 | mov ah,al |
1241 | mov ah,al |
1222 | loop dcnt1 |
1242 | loop dcnt1 |
1223 | 1243 | ||
1224 | pop ecx |
1244 | pop ecx |
1225 | pop eax |
1245 | pop eax |
1226 | 1246 | ||
1227 | ret |
1247 | ret |
1228 | 1248 | ||
1229 | ;*************************************************************************** |
1249 | ;*************************************************************************** |
1230 | ; Function |
1250 | ; Function |
1231 | ; scan_bus |
1251 | ; scan_bus |
1232 | ; |
1252 | ; |
1233 | ; Description |
1253 | ; Description |
1234 | ; Scans the PCI bus for a supported device |
1254 | ; Scans the PCI bus for a supported device |
1235 | ; If a supported device is found, the drvr_ variables are initialised |
1255 | ; If a supported device is found, the drvr_ variables are initialised |
1236 | ; to that drivers functions ( as defined in the PCICards table) |
1256 | ; to that drivers functions ( as defined in the PCICards table) |
1237 | ; |
1257 | ; |
1238 | ; io_addr holds card I/O space. 32 bit, but only LS 16 bits valid |
1258 | ; io_addr holds card I/O space. 32 bit, but only LS 16 bits valid |
1239 | ; pci_data holds the PCI vendor + device code |
1259 | ; pci_data holds the PCI vendor + device code |
1240 | ; pci_dev holds PCI bus dev # |
1260 | ; pci_dev holds PCI bus dev # |
1241 | ; pci_bus holds PCI bus # |
1261 | ; pci_bus holds PCI bus # |
1242 | ; |
1262 | ; |
1243 | ; io_addr will be zero if no card found |
1263 | ; io_addr will be zero if no card found |
1244 | ; |
1264 | ; |
1245 | ;*************************************************************************** |
1265 | ;*************************************************************************** |
1246 | scan_bus: |
1266 | scan_bus: |
1247 | xor eax, eax |
1267 | xor eax, eax |
1248 | mov [hdrtype], al |
1268 | mov [hdrtype], al |
1249 | mov [pci_data], eax |
1269 | mov [pci_data], eax |
1250 | 1270 | ||
1251 | xor ebx, ebx ; ebx = bus# 0 .. 255 |
1271 | xor ebx, ebx ; ebx = bus# 0 .. 255 |
1252 | 1272 | ||
1253 | sb_bus_loop: |
1273 | sb_bus_loop: |
1254 | xor ecx, ecx ; ecx = devfn# 0 .. 254 ( not 255? ) |
1274 | xor ecx, ecx ; ecx = devfn# 0 .. 254 ( not 255? ) |
1255 | 1275 | ||
1256 | sb_devf_loop: |
1276 | sb_devf_loop: |
1257 | mov eax, ecx |
1277 | mov eax, ecx |
1258 | and eax, 0x07 |
1278 | and eax, 0x07 |
1259 | 1279 | ||
1260 | cmp eax, 0 |
1280 | cmp eax, 0 |
1261 | jne sb_001 |
1281 | jne sb_001 |
1262 | 1282 | ||
1263 | mov edx, PCI_HEADER_TYPE |
1283 | mov edx, PCI_HEADER_TYPE |
1264 | call pcibios_read_config_byte |
1284 | call pcibios_read_config_byte |
1265 | mov [hdrtype], al |
1285 | mov [hdrtype], al |
1266 | jmp sb_002 |
1286 | jmp sb_002 |
1267 | 1287 | ||
1268 | sb_001: |
1288 | sb_001: |
1269 | mov al, [hdrtype] |
1289 | mov al, [hdrtype] |
1270 | and al, 0x80 |
1290 | and al, 0x80 |
1271 | cmp al, 0x80 |
1291 | cmp al, 0x80 |
1272 | jne sb_inc_devf |
1292 | jne sb_inc_devf |
1273 | 1293 | ||
1274 | sb_002: |
1294 | sb_002: |
1275 | mov edx, PCI_VENDOR_ID |
1295 | mov edx, PCI_VENDOR_ID |
1276 | call pcibios_read_config_dword |
1296 | call pcibios_read_config_dword |
1277 | mov [vendor_device], eax |
1297 | mov [vendor_device], eax |
1278 | cmp eax, 0xffffffff |
1298 | cmp eax, 0xffffffff |
1279 | je sb_empty |
1299 | je sb_empty |
1280 | cmp eax, 0 |
1300 | cmp eax, 0 |
1281 | jne sb_check_vendor |
1301 | jne sb_check_vendor |
1282 | 1302 | ||
1283 | sb_empty: |
1303 | sb_empty: |
1284 | mov [hdrtype], byte 0 |
1304 | mov [hdrtype], byte 0 |
1285 | jmp sb_inc_devf |
1305 | jmp sb_inc_devf |
1286 | 1306 | ||
1287 | sb_check_vendor: |
1307 | sb_check_vendor: |
1288 | ; iterate though PCICards until end or match found |
1308 | ; iterate though PCICards until end or match found |
1289 | mov esi, PCICards |
1309 | mov esi, PCICards |
1290 | 1310 | ||
1291 | sb_check: |
1311 | sb_check: |
1292 | cmp [esi], dword 0 |
1312 | cmp [esi], dword 0 |
1293 | je sb_inc_devf ; Quit if at last entry |
1313 | je sb_inc_devf ; Quit if at last entry |
1294 | cmp eax, [esi] |
1314 | cmp eax, [esi] |
1295 | je sb_got_card |
1315 | je sb_got_card |
1296 | add esi, PCICARDS_ENTRY_SIZE |
1316 | add esi, PCICARDS_ENTRY_SIZE |
1297 | jmp sb_check |
1317 | jmp sb_check |
1298 | 1318 | ||
1299 | sb_got_card: |
1319 | sb_got_card: |
1300 | ; indicate that we have found the card |
1320 | ; indicate that we have found the card |
1301 | mov [pci_data], eax |
1321 | mov [pci_data], eax |
1302 | mov [pci_dev], ecx |
1322 | mov [pci_dev], ecx |
1303 | mov [pci_bus], ebx |
1323 | mov [pci_bus], ebx |
1304 | 1324 | ||
1305 | ; Define the driver functions |
1325 | ; Define the driver functions |
1306 | push eax |
1326 | push eax |
1307 | mov eax, [esi+4] |
1327 | mov eax, [esi+4] |
1308 | mov [drvr_probe], eax |
1328 | mov [drvr_probe], eax |
1309 | mov eax, [esi+8] |
1329 | mov eax, [esi+8] |
1310 | mov [drvr_reset], eax |
1330 | mov [drvr_reset], eax |
1311 | mov eax, [esi+12] |
1331 | mov eax, [esi+12] |
1312 | mov [drvr_poll], eax |
1332 | mov [drvr_poll], eax |
1313 | mov eax, [esi+16] |
1333 | mov eax, [esi+16] |
1314 | mov [drvr_transmit], eax |
1334 | mov [drvr_transmit], eax |
1315 | pop eax |
1335 | pop eax |
1316 | 1336 | ||
1317 | mov edx, PCI_BASE_ADDRESS_0 |
1337 | mov edx, PCI_BASE_ADDRESS_0 |
1318 | 1338 | ||
1319 | sb_reg_check: |
1339 | sb_reg_check: |
1320 | call pcibios_read_config_dword |
1340 | call pcibios_read_config_dword |
1321 | mov [io_addr], eax |
1341 | mov [io_addr], eax |
1322 | and eax, PCI_BASE_ADDRESS_IO_MASK |
1342 | and eax, PCI_BASE_ADDRESS_IO_MASK |
1323 | cmp eax, 0 |
1343 | cmp eax, 0 |
1324 | je sb_inc_reg |
1344 | je sb_inc_reg |
1325 | mov eax, [io_addr] |
1345 | mov eax, [io_addr] |
1326 | and eax, PCI_BASE_ADDRESS_SPACE_IO |
1346 | and eax, PCI_BASE_ADDRESS_SPACE_IO |
1327 | cmp eax, 0 |
1347 | cmp eax, 0 |
1328 | je sb_inc_reg |
1348 | je sb_inc_reg |
1329 | 1349 | ||
1330 | mov eax, [io_addr] |
1350 | mov eax, [io_addr] |
1331 | and eax, PCI_BASE_ADDRESS_IO_MASK |
1351 | and eax, PCI_BASE_ADDRESS_IO_MASK |
1332 | mov [io_addr], eax |
1352 | mov [io_addr], eax |
1333 | 1353 | ||
1334 | sb_exit1: |
1354 | sb_exit1: |
1335 | ret |
1355 | ret |
1336 | 1356 | ||
1337 | sb_inc_reg: |
1357 | sb_inc_reg: |
1338 | add edx, 4 |
1358 | add edx, 4 |
1339 | cmp edx, PCI_BASE_ADDRESS_5 |
1359 | cmp edx, PCI_BASE_ADDRESS_5 |
1340 | jbe sb_reg_check |
1360 | jbe sb_reg_check |
1341 | 1361 | ||
1342 | sb_inc_devf: |
1362 | sb_inc_devf: |
1343 | inc ecx |
1363 | inc ecx |
1344 | cmp ecx, 255 |
1364 | cmp ecx, 255 |
1345 | jb sb_devf_loop |
1365 | jb sb_devf_loop |
1346 | inc ebx |
1366 | inc ebx |
1347 | cmp ebx, 256 |
1367 | cmp ebx, 256 |
1348 | jb sb_bus_loop |
1368 | jb sb_bus_loop |
1349 | 1369 | ||
1350 | ; We get here if we didn't find our card |
1370 | ; We get here if we didn't find our card |
1351 | ; set io_addr to 0 as an indication |
1371 | ; set io_addr to 0 as an indication |
1352 | xor eax, eax |
1372 | xor eax, eax |
1353 | mov [io_addr], eax |
1373 | mov [io_addr], eax |
1354 | 1374 | ||
1355 | sb_exit2: |
1375 | sb_exit2: |
1356 | ret |
1376 | ret |
1357 | 1377 | ||
1358 | ;*************************************************************************** |
1378 | ;*************************************************************************** |
1359 | ; |
1379 | ; |
1360 | ; DEBUGGING CODE FOLLOWS |
1380 | ; DEBUGGING CODE FOLLOWS |
1361 | ; |
1381 | ; |
1362 | ; If debugging data output is not required, ALL code & data below may |
1382 | ; If debugging data output is not required, ALL code & data below may |
1363 | ; be removed. |
1383 | ; be removed. |
1364 | ; |
1384 | ; |
1365 | ;*************************************************************************** |
1385 | ;*************************************************************************** |
1366 | 1386 | ||
1367 | if DEBUGGING_STATE = DEBUGGING_ENABLED |
1387 | if DEBUGGING_STATE = DEBUGGING_ENABLED |
1368 | 1388 | ||
1369 | ;*************************************************************************** |
1389 | ;*************************************************************************** |
1370 | ; Function |
1390 | ; Function |
1371 | ; eth_dump |
1391 | ; eth_dump |
1372 | ; |
1392 | ; |
1373 | ; Description |
1393 | ; Description |
1374 | ; Dumps a tx or rx ethernet packet over the rs232 link |
1394 | ; Dumps a tx or rx ethernet packet over the rs232 link |
1375 | ; This is a debugging routine that seriously slows down the stack. |
1395 | ; This is a debugging routine that seriously slows down the stack. |
1376 | ; Use with caution. |
1396 | ; Use with caution. |
1377 | ; |
1397 | ; |
1378 | ; Baud rate is 57600, 8n1 com1 |
1398 | ; Baud rate is 57600, 8n1 com1 |
1379 | ; eax : type (0 == rx, 1 == tx ) |
1399 | ; eax : type (0 == rx, 1 == tx ) |
1380 | ; cx : # of bytes in buffer |
1400 | ; cx : # of bytes in buffer |
1381 | ; esi : address of buffer start |
1401 | ; esi : address of buffer start |
1382 | ; edi : pointer to MACAddress ( tx only ) |
1402 | ; edi : pointer to MACAddress ( tx only ) |
1383 | ; |
1403 | ; |
1384 | ;*************************************************************************** |
1404 | ;*************************************************************************** |
1385 | eth_dump: |
1405 | eth_dump: |
1386 | pusha |
1406 | pusha |
1387 | 1407 | ||
1388 | ; Set the port to the desired speed |
1408 | ; Set the port to the desired speed |
1389 | mov ebx, 0x3f8 ; combase |
1409 | mov ebx, 0x3f8 ; combase |
1390 | 1410 | ||
1391 | mov edx, ebx |
1411 | mov edx, ebx |
1392 | add edx, 3 ; data format register |
1412 | add edx, 3 ; data format register |
1393 | mov al, 0x80 ; enable access to divisor latch |
1413 | mov al, 0x80 ; enable access to divisor latch |
1394 | out dx, al |
1414 | out dx, al |
1395 | 1415 | ||
1396 | mov edx, ebx |
1416 | mov edx, ebx |
1397 | add edx, 1 ; interrupt enable register |
1417 | add edx, 1 ; interrupt enable register |
1398 | mov al, 0x00 ; No interruts enabled |
1418 | mov al, 0x00 ; No interruts enabled |
1399 | out dx, al |
1419 | out dx, al |
1400 | 1420 | ||
1401 | mov edx, ebx |
1421 | mov edx, ebx |
1402 | mov al, 0x20 / 16 ; set baud rate to 57600 0x10 =115200 |
1422 | mov al, 0x20 / 16 ; set baud rate to 57600 0x10 =115200 |
1403 | out dx, al |
1423 | out dx, al |
1404 | 1424 | ||
1405 | mov edx, ebx |
1425 | mov edx, ebx |
1406 | add edx, 3 ; data format register |
1426 | add edx, 3 ; data format register |
1407 | mov al, 0x03 ; 8 data bits |
1427 | mov al, 0x03 ; 8 data bits |
1408 | out dx, al |
1428 | out dx, al |
1409 | 1429 | ||
1410 | mov edx, ebx |
1430 | mov edx, ebx |
1411 | add edx, 4 ; Modem control register |
1431 | add edx, 4 ; Modem control register |
1412 | mov al, 0x08 ; out2 enabled. No handshaking. |
1432 | mov al, 0x08 ; out2 enabled. No handshaking. |
1413 | out dx, al |
1433 | out dx, al |
1414 | 1434 | ||
1415 | mov edx, ebx |
1435 | mov edx, ebx |
1416 | add edx, 1 ; interrupt enable register |
1436 | add edx, 1 ; interrupt enable register |
1417 | mov al, 0x01 ; Receive data interrupt enabled, |
1437 | mov al, 0x01 ; Receive data interrupt enabled, |
1418 | out dx, al |
1438 | out dx, al |
1419 | 1439 | ||
1420 | popa |
1440 | popa |
1421 | 1441 | ||
1422 | ; First, display the type of the buffer. |
1442 | ; First, display the type of the buffer. |
1423 | ; If it is a tx buffer, display the macaddress |
1443 | ; If it is a tx buffer, display the macaddress |
1424 | 1444 | ||
1425 | pusha |
1445 | pusha |
1426 | 1446 | ||
1427 | cmp eax, 0 |
1447 | cmp eax, 0 |
1428 | jne dd001 |
1448 | jne dd001 |
1429 | 1449 | ||
1430 | mov bl, 0x0a |
1450 | mov bl, 0x0a |
1431 | call tx_byted |
1451 | call tx_byted |
1432 | mov bl, 0x0d |
1452 | mov bl, 0x0d |
1433 | call tx_byted |
1453 | call tx_byted |
1434 | 1454 | ||
1435 | ; Output "RX:" |
1455 | ; Output "RX:" |
1436 | mov bl, 'R' |
1456 | mov bl, 'R' |
1437 | call tx_byted |
1457 | call tx_byted |
1438 | mov bl, 'X' |
1458 | mov bl, 'X' |
1439 | call tx_byted |
1459 | call tx_byted |
1440 | mov bl, ':' |
1460 | mov bl, ':' |
1441 | call tx_byted |
1461 | call tx_byted |
1442 | jmp dump_data |
1462 | jmp dump_data |
1443 | 1463 | ||
1444 | dd001: |
1464 | dd001: |
1445 | mov bl, 0x0a |
1465 | mov bl, 0x0a |
1446 | call tx_byted |
1466 | call tx_byted |
1447 | mov bl, 0x0d |
1467 | mov bl, 0x0d |
1448 | call tx_byted |
1468 | call tx_byted |
1449 | 1469 | ||
1450 | ; Output TX: xxxxxxxxxxxx |
1470 | ; Output TX: xxxxxxxxxxxx |
1451 | mov bl, 'T' |
1471 | mov bl, 'T' |
1452 | call tx_byted |
1472 | call tx_byted |
1453 | mov bl, 'X' |
1473 | mov bl, 'X' |
1454 | call tx_byted |
1474 | call tx_byted |
1455 | mov bl, ':' |
1475 | mov bl, ':' |
1456 | call tx_byted |
1476 | call tx_byted |
1457 | mov bl, ' ' |
1477 | mov bl, ' ' |
1458 | call tx_byted |
1478 | call tx_byted |
1459 | 1479 | ||
1460 | ; Display MAC address |
1480 | ; Display MAC address |
1461 | xor eax, eax |
1481 | xor eax, eax |
1462 | mov al, [edi] |
1482 | mov al, [edi] |
1463 | shr al, 4 |
1483 | shr al, 4 |
1464 | mov bl, [eax + hexchars] |
1484 | mov bl, [eax + hexchars] |
1465 | call tx_byted ; byte in bl eax ebx edx destroyed |
1485 | call tx_byted ; byte in bl eax ebx edx destroyed |
1466 | 1486 | ||
1467 | xor eax, eax |
1487 | xor eax, eax |
1468 | mov al, [edi] |
1488 | mov al, [edi] |
1469 | and al, 0x0f |
1489 | and al, 0x0f |
1470 | mov bl, [eax + hexchars] |
1490 | mov bl, [eax + hexchars] |
1471 | call tx_byted ; byte in bl eax ebx edx destroyed |
1491 | call tx_byted ; byte in bl eax ebx edx destroyed |
1472 | 1492 | ||
1473 | inc edi |
1493 | inc edi |
1474 | xor eax, eax |
1494 | xor eax, eax |
1475 | mov al, [edi] |
1495 | mov al, [edi] |
1476 | shr al, 4 |
1496 | shr al, 4 |
1477 | mov bl, [eax + hexchars] |
1497 | mov bl, [eax + hexchars] |
1478 | call tx_byted ; byte in bl eax ebx edx destroyed |
1498 | call tx_byted ; byte in bl eax ebx edx destroyed |
1479 | 1499 | ||
1480 | xor eax, eax |
1500 | xor eax, eax |
1481 | mov al, [edi] |
1501 | mov al, [edi] |
1482 | and al, 0x0f |
1502 | and al, 0x0f |
1483 | mov bl, [eax + hexchars] |
1503 | mov bl, [eax + hexchars] |
1484 | call tx_byted ; byte in bl eax ebx edx destroyed |
1504 | call tx_byted ; byte in bl eax ebx edx destroyed |
1485 | 1505 | ||
1486 | inc edi |
1506 | inc edi |
1487 | xor eax, eax |
1507 | xor eax, eax |
1488 | mov al, [edi] |
1508 | mov al, [edi] |
1489 | shr al, 4 |
1509 | shr al, 4 |
1490 | mov bl, [eax + hexchars] |
1510 | mov bl, [eax + hexchars] |
1491 | call tx_byted ; byte in bl eax ebx edx destroyed |
1511 | call tx_byted ; byte in bl eax ebx edx destroyed |
1492 | 1512 | ||
1493 | xor eax, eax |
1513 | xor eax, eax |
1494 | mov al, [edi] |
1514 | mov al, [edi] |
1495 | and al, 0x0f |
1515 | and al, 0x0f |
1496 | mov bl, [eax + hexchars] |
1516 | mov bl, [eax + hexchars] |
1497 | call tx_byted ; byte in bl eax ebx edx destroyed |
1517 | call tx_byted ; byte in bl eax ebx edx destroyed |
1498 | 1518 | ||
1499 | inc edi |
1519 | inc edi |
1500 | xor eax, eax |
1520 | xor eax, eax |
1501 | mov al, [edi] |
1521 | mov al, [edi] |
1502 | shr al, 4 |
1522 | shr al, 4 |
1503 | mov bl, [eax + hexchars] |
1523 | mov bl, [eax + hexchars] |
1504 | call tx_byted ; byte in bl eax ebx edx destroyed |
1524 | call tx_byted ; byte in bl eax ebx edx destroyed |
1505 | 1525 | ||
1506 | xor eax, eax |
1526 | xor eax, eax |
1507 | mov al, [edi] |
1527 | mov al, [edi] |
1508 | and al, 0x0f |
1528 | and al, 0x0f |
1509 | mov bl, [eax + hexchars] |
1529 | mov bl, [eax + hexchars] |
1510 | call tx_byted ; byte in bl eax ebx edx destroyed |
1530 | call tx_byted ; byte in bl eax ebx edx destroyed |
1511 | 1531 | ||
1512 | inc edi |
1532 | inc edi |
1513 | xor eax, eax |
1533 | xor eax, eax |
1514 | mov al, [edi] |
1534 | mov al, [edi] |
1515 | shr al, 4 |
1535 | shr al, 4 |
1516 | mov bl, [eax + hexchars] |
1536 | mov bl, [eax + hexchars] |
1517 | call tx_byted ; byte in bl eax ebx edx destroyed |
1537 | call tx_byted ; byte in bl eax ebx edx destroyed |
1518 | 1538 | ||
1519 | xor eax, eax |
1539 | xor eax, eax |
1520 | mov al, [edi] |
1540 | mov al, [edi] |
1521 | and al, 0x0f |
1541 | and al, 0x0f |
1522 | mov bl, [eax + hexchars] |
1542 | mov bl, [eax + hexchars] |
1523 | call tx_byted ; byte in bl eax ebx edx destroyed |
1543 | call tx_byted ; byte in bl eax ebx edx destroyed |
1524 | 1544 | ||
1525 | inc edi |
1545 | inc edi |
1526 | xor eax, eax |
1546 | xor eax, eax |
1527 | mov al, [edi] |
1547 | mov al, [edi] |
1528 | shr al, 4 |
1548 | shr al, 4 |
1529 | mov bl, [eax + hexchars] |
1549 | mov bl, [eax + hexchars] |
1530 | call tx_byted ; byte in bl eax ebx edx destroyed |
1550 | call tx_byted ; byte in bl eax ebx edx destroyed |
1531 | 1551 | ||
1532 | xor eax, eax |
1552 | xor eax, eax |
1533 | mov al, [edi] |
1553 | mov al, [edi] |
1534 | and al, 0x0f |
1554 | and al, 0x0f |
1535 | mov bl, [eax + hexchars] |
1555 | mov bl, [eax + hexchars] |
1536 | call tx_byted ; byte in bl eax ebx edx destroyed |
1556 | call tx_byted ; byte in bl eax ebx edx destroyed |
1537 | 1557 | ||
1538 | dump_data: |
1558 | dump_data: |
1539 | popa |
1559 | popa |
1540 | 1560 | ||
1541 | ; OK, we come in here with |
1561 | ; OK, we come in here with |
1542 | ; cx == number of byte to send |
1562 | ; cx == number of byte to send |
1543 | ; esi == buffer start |
1563 | ; esi == buffer start |
1544 | ; |
1564 | ; |
1545 | dd_000: |
1565 | dd_000: |
1546 | mov bl, 0x0a |
1566 | mov bl, 0x0a |
1547 | call tx_byted |
1567 | call tx_byted |
1548 | mov bl, 0x0d |
1568 | mov bl, 0x0d |
1549 | call tx_byted |
1569 | call tx_byted |
1550 | 1570 | ||
1551 | mov eax, 16 ; Number of characters on the line |
1571 | mov eax, 16 ; Number of characters on the line |
1552 | mov edi, esi ; Save first byte position for later |
1572 | mov edi, esi ; Save first byte position for later |
1553 | 1573 | ||
1554 | push ecx |
1574 | push ecx |
1555 | 1575 | ||
1556 | dd_001: |
1576 | dd_001: |
1557 | push eax |
1577 | push eax |
1558 | 1578 | ||
1559 | ; Print a byte, and a space |
1579 | ; Print a byte, and a space |
1560 | xor eax, eax |
1580 | xor eax, eax |
1561 | mov al, [esi] |
1581 | mov al, [esi] |
1562 | shr al, 4 |
1582 | shr al, 4 |
1563 | mov bl, [eax + hexchars] |
1583 | mov bl, [eax + hexchars] |
1564 | call tx_byted ; byte in bl eax ebx edx destroyed |
1584 | call tx_byted ; byte in bl eax ebx edx destroyed |
1565 | 1585 | ||
1566 | xor eax, eax |
1586 | xor eax, eax |
1567 | mov al, [esi] |
1587 | mov al, [esi] |
1568 | and al, 0x0f |
1588 | and al, 0x0f |
1569 | mov bl, [eax + hexchars] |
1589 | mov bl, [eax + hexchars] |
1570 | call tx_byted ; byte in bl eax ebx edx destroyed |
1590 | call tx_byted ; byte in bl eax ebx edx destroyed |
1571 | 1591 | ||
1572 | mov bl, ' ' |
1592 | mov bl, ' ' |
1573 | call tx_byted |
1593 | call tx_byted |
1574 | 1594 | ||
1575 | pop eax |
1595 | pop eax |
1576 | 1596 | ||
1577 | inc esi |
1597 | inc esi |
1578 | dec ecx |
1598 | dec ecx |
1579 | cmp ecx, 0 |
1599 | cmp ecx, 0 |
1580 | je dd_0011 ; Print the ASCII format |
1600 | je dd_0011 ; Print the ASCII format |
1581 | 1601 | ||
1582 | dec eax |
1602 | dec eax |
1583 | 1603 | ||
1584 | cmp eax, 0 |
1604 | cmp eax, 0 |
1585 | je dd_002 ; Print the ASCII format |
1605 | je dd_002 ; Print the ASCII format |
1586 | jmp dd_001 ; Print rest of line |
1606 | jmp dd_001 ; Print rest of line |
1587 | 1607 | ||
1588 | dd_0011: |
1608 | dd_0011: |
1589 | ; First, complete the 16 bytes of data, by printing spaces |
1609 | ; First, complete the 16 bytes of data, by printing spaces |
1590 | dec eax |
1610 | dec eax |
1591 | cmp eax, 0 |
1611 | cmp eax, 0 |
1592 | je dd_002 |
1612 | je dd_002 |
1593 | 1613 | ||
1594 | push eax |
1614 | push eax |
1595 | mov bl, ' ' |
1615 | mov bl, ' ' |
1596 | call tx_byted |
1616 | call tx_byted |
1597 | mov bl, ' ' |
1617 | mov bl, ' ' |
1598 | call tx_byted |
1618 | call tx_byted |
1599 | mov bl, ' ' |
1619 | mov bl, ' ' |
1600 | call tx_byted |
1620 | call tx_byted |
1601 | pop eax |
1621 | pop eax |
1602 | jmp dd_0011 |
1622 | jmp dd_0011 |
1603 | 1623 | ||
1604 | dd_002: |
1624 | dd_002: |
1605 | pop ecx |
1625 | pop ecx |
1606 | mov esi, edi ; Go back to the start of the line data |
1626 | mov esi, edi ; Go back to the start of the line data |
1607 | 1627 | ||
1608 | mov eax, 16 |
1628 | mov eax, 16 |
1609 | 1629 | ||
1610 | outLineAscii: |
1630 | outLineAscii: |
1611 | push eax |
1631 | push eax |
1612 | 1632 | ||
1613 | xor eax, eax |
1633 | xor eax, eax |
1614 | mov al, [esi] |
1634 | mov al, [esi] |
1615 | mov bl, '.' |
1635 | mov bl, '.' |
1616 | 1636 | ||
1617 | cmp al, 0x1F |
1637 | cmp al, 0x1F |
1618 | jle outAscii |
1638 | jle outAscii |
1619 | cmp al, 0x7e |
1639 | cmp al, 0x7e |
1620 | jge outAscii |
1640 | jge outAscii |
1621 | 1641 | ||
1622 | mov bl, al |
1642 | mov bl, al |
1623 | 1643 | ||
1624 | outAscii: |
1644 | outAscii: |
1625 | call tx_byted ; byte in bl eax ebx edx destroyed |
1645 | call tx_byted ; byte in bl eax ebx edx destroyed |
1626 | 1646 | ||
1627 | pop eax |
1647 | pop eax |
1628 | dec ecx |
1648 | dec ecx |
1629 | inc esi |
1649 | inc esi |
1630 | cmp ecx, 0 |
1650 | cmp ecx, 0 |
1631 | je dd_003 |
1651 | je dd_003 |
1632 | 1652 | ||
1633 | dec eax |
1653 | dec eax |
1634 | cmp eax, 0 |
1654 | cmp eax, 0 |
1635 | je dd_003 |
1655 | je dd_003 |
1636 | jmp outLineAscii |
1656 | jmp outLineAscii |
1637 | 1657 | ||
1638 | dd_003: |
1658 | dd_003: |
1639 | cmp ecx, 0 |
1659 | cmp ecx, 0 |
1640 | je dd_004 |
1660 | je dd_004 |
1641 | jmp dd_000 |
1661 | jmp dd_000 |
1642 | 1662 | ||
1643 | dd_004: |
1663 | dd_004: |
1644 | ret |
1664 | ret |
1645 | 1665 | ||
1646 | ;*************************************************************************** |
1666 | ;*************************************************************************** |
1647 | ; Function |
1667 | ; Function |
1648 | ; tx_byte |
1668 | ; tx_byte |
1649 | ; |
1669 | ; |
1650 | ; Description |
1670 | ; Description |
1651 | ; Send a byte in bl out of the com port 1 |
1671 | ; Send a byte in bl out of the com port 1 |
1652 | ; destroys eax, edx |
1672 | ; destroys eax, edx |
1653 | ; |
1673 | ; |
1654 | ;*************************************************************************** |
1674 | ;*************************************************************************** |
1655 | tx_byted: |
1675 | tx_byted: |
1656 | push ebx ; Save the byte |
1676 | push ebx ; Save the byte |
1657 | 1677 | ||
1658 | mov ebx, 0x3f8 ; get the com port address |
1678 | mov ebx, 0x3f8 ; get the com port address |
1659 | 1679 | ||
1660 | ; Wait for transmit buffer to empty. This could take 1ms @ 9600baud |
1680 | ; Wait for transmit buffer to empty. This could take 1ms @ 9600baud |
1661 | 1681 | ||
1662 | mov edx, ebx |
1682 | mov edx, ebx |
1663 | add edx, 5 |
1683 | add edx, 5 |
1664 | 1684 | ||
1665 | wait_txd: |
1685 | wait_txd: |
1666 | in al, dx ; read uart serialisation status |
1686 | in al, dx ; read uart serialisation status |
1667 | and al, 0x40 |
1687 | and al, 0x40 |
1668 | cmp al, 0 |
1688 | cmp al, 0 |
1669 | jz wait_txd ; loop until free |
1689 | jz wait_txd ; loop until free |
1670 | 1690 | ||
1671 | mov edx, ebx |
1691 | mov edx, ebx |
1672 | pop eax ; restore the byte to send |
1692 | pop eax ; restore the byte to send |
1673 | out dx, al |
1693 | out dx, al |
1674 | ret |
1694 | ret |
1675 | 1695 | ||
1676 | iglobal |
1696 | iglobal |
1677 | ; This is used for translating hex to ASCII for display or output |
1697 | ; This is used for translating hex to ASCII for display or output |
1678 | hexchars db '0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F' |
1698 | hexchars db '0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F' |
1679 | endg |
1699 | endg |
1680 | end if |
1700 | end if |