]>
git.ipfire.org Git - people/ms/u-boot.git/blob - board/evb64260/eth_addrtbl.c
3 #include <galileo/gt64260R.h>
4 #include <galileo/core.h>
7 #include "eth_addrtbl.h"
11 #ifdef CONFIG_GT_USE_MAC_HASH_TABLE
13 static u32 addressTableHashMode
[GAL_ETH_DEVS
] = { 0, };
14 static u32 addressTableHashSize
[GAL_ETH_DEVS
] = { 0, };
15 static addrTblEntry
*addressTableBase
[GAL_ETH_DEVS
] = { 0, };
16 static void *realAddrTableBase
[GAL_ETH_DEVS
] = { 0, };
18 static const u32 hashLength
[2] = {
19 (0x8000), /* 8K * 4 entries */
20 (0x8000 / 16), /* 512 * 4 entries */
23 /* Initialize the address table for a port, if needed */
24 unsigned int initAddressTable (u32 port
, u32 hashMode
, u32 hashSizeSelector
)
26 unsigned int tableBase
;
28 if (port
< 0 || port
>= GAL_ETH_DEVS
) {
29 printf ("%s: Invalid port number %d\n", __FUNCTION__
, port
);
34 printf ("%s: Invalid Hash Mode %d\n", __FUNCTION__
, port
);
38 if (realAddrTableBase
[port
] &&
39 (addressTableHashSize
[port
] != hashSizeSelector
)) {
40 /* we have been here before,
41 * but now we want a different sized table
43 free (realAddrTableBase
[port
]);
44 realAddrTableBase
[port
] = 0;
45 addressTableBase
[port
] = 0;
49 tableBase
= (unsigned int) addressTableBase
[port
];
50 /* we get called for every probe, so only do this once */
53 hashLength
[hashSizeSelector
] * sizeof (addrTblEntry
);
55 realAddrTableBase
[port
] =
57 tableBase
= (unsigned int)realAddrTableBase
;
60 printf ("%s: alloc memory failed \n", __FUNCTION__
);
64 /* align to octal byte */
66 tableBase
= (tableBase
+ 63) & ~63;
68 addressTableHashMode
[port
] = hashMode
;
69 addressTableHashSize
[port
] = hashSizeSelector
;
70 addressTableBase
[port
] = (addrTblEntry
*) tableBase
;
72 memset ((void *) tableBase
, 0, bytes
);
79 * ----------------------------------------------------------------------------
80 * This function will calculate the hash function of the address.
81 * depends on the hash mode and hash size.
83 * macH - the 2 most significant bytes of the MAC address.
84 * macL - the 4 least significant bytes of the MAC address.
85 * hashMode - hash mode 0 or hash mode 1.
86 * hashSizeSelector - indicates number of hash table entries (0=0x8000,1=0x800)
88 * return the calculated entry.
90 u32
hashTableFunction (u32 macH
, u32 macL
, u32 HashSize
, u32 hash_mode
)
103 addrH
= NIBBLE_SWAPPING_16_BIT (macH
);
104 addrL
= NIBBLE_SWAPPING_32_BIT (macL
);
106 addrHSwapped
= FLIP_4_BITS (addrH
& 0xf)
107 + ((FLIP_4_BITS ((addrH
>> 4) & 0xf)) << 4)
108 + ((FLIP_4_BITS ((addrH
>> 8) & 0xf)) << 8)
109 + ((FLIP_4_BITS ((addrH
>> 12) & 0xf)) << 12);
111 addrLSwapped
= FLIP_4_BITS (addrL
& 0xf)
112 + ((FLIP_4_BITS ((addrL
>> 4) & 0xf)) << 4)
113 + ((FLIP_4_BITS ((addrL
>> 8) & 0xf)) << 8)
114 + ((FLIP_4_BITS ((addrL
>> 12) & 0xf)) << 12)
115 + ((FLIP_4_BITS ((addrL
>> 16) & 0xf)) << 16)
116 + ((FLIP_4_BITS ((addrL
>> 20) & 0xf)) << 20)
117 + ((FLIP_4_BITS ((addrL
>> 24) & 0xf)) << 24)
118 + ((FLIP_4_BITS ((addrL
>> 28) & 0xf)) << 28);
120 addrH
= addrHSwapped
;
121 addrL
= addrLSwapped
;
123 if (hash_mode
== 0) {
124 addr0
= (addrL
>> 2) & 0x03f;
125 addr1
= (addrL
& 0x003) | ((addrL
>> 8) & 0x7f) << 2;
126 addr2
= (addrL
>> 15) & 0x1ff;
127 addr3
= ((addrL
>> 24) & 0x0ff) | ((addrH
& 1) << 8);
129 addr0
= FLIP_6_BITS (addrL
& 0x03f);
130 addr1
= FLIP_9_BITS (((addrL
>> 6) & 0x1ff));
131 addr2
= FLIP_9_BITS ((addrL
>> 15) & 0x1ff);
132 addr3
= FLIP_9_BITS ((((addrL
>> 24) & 0x0ff) |
133 ((addrH
& 0x1) << 8)));
136 hashResult
= (addr0
<< 9) | (addr1
^ addr2
^ addr3
);
138 if (HashSize
== _8K_TABLE
) {
139 hashResult
= hashResult
& 0xffff;
141 hashResult
= hashResult
& 0x07ff;
149 * ----------------------------------------------------------------------------
150 * This function will add an entry to the address table.
151 * depends on the hash mode and hash size that was initialized.
153 * port - ETHERNET port number.
154 * macH - the 2 most significant bytes of the MAC address.
155 * macL - the 4 least significant bytes of the MAC address.
156 * skip - if 1, skip this address.
157 * rd - the RD field in the address table.
159 * address table entry is added.
161 * false if table full
163 int addAddressTableEntry (u32 port
, u32 macH
, u32 macL
, u32 rd
, u32 skip
)
170 newLo
= (((macH
>> 4) & 0xf) << 15)
171 | (((macH
>> 0) & 0xf) << 11)
172 | (((macH
>> 12) & 0xf) << 7)
173 | (((macH
>> 8) & 0xf) << 3)
174 | (((macL
>> 20) & 0x1) << 31)
175 | (((macL
>> 16) & 0xf) << 27)
176 | (((macL
>> 28) & 0xf) << 23)
177 | (((macL
>> 24) & 0xf) << 19)
178 | (skip
<< SKIP_BIT
) | (rd
<< 2) | VALID
;
180 newHi
= (((macL
>> 4) & 0xf) << 15)
181 | (((macL
>> 0) & 0xf) << 11)
182 | (((macL
>> 12) & 0xf) << 7)
183 | (((macL
>> 8) & 0xf) << 3)
184 | (((macL
>> 21) & 0x7) << 0);
187 * Pick the appropriate table, start scanning for free/reusable
188 * entries at the index obtained by hashing the specified MAC address
190 entry
= addressTableBase
[port
];
191 entry
+= hashTableFunction (macH
, macL
, addressTableHashSize
[port
],
192 addressTableHashMode
[port
]);
193 for (i
= 0; i
< HOP_NUMBER
; i
++, entry
++) {
194 if (!(entry
->lo
& VALID
) /*|| (entry->lo & SKIP) */ ) {
196 } else { /* if same address put in same position */
197 if (((entry
->lo
& 0xfffffff8) == (newLo
& 0xfffffff8))
198 && (entry
->hi
== newHi
)) {
204 if (i
== HOP_NUMBER
) {
205 PRINTF ("addGT64260addressTableEntry: table section is full\n");
210 * Update the selected entry
214 DCACHE_FLUSH_N_SYNC ((u32
) entry
, MAC_ENTRY_SIZE
);
218 #endif /* CONFIG_GT_USE_MAC_HASH_TABLE */