1 --- a/driver/nvram_stub.c
2 +++ b/driver/nvram_stub.c
7 +#include <proto/ethernet.h>
8 +#include <linux/errno.h>
11 #define NVR_MSG(x) printf x
12 @@ -24,6 +26,7 @@ typedef struct _vars {
13 static vars_t *vars = NULL;
14 static int nvram_init_done = 0;
15 extern char *nvram_buf[];
16 +static void fixup_mac_addr(vars_t *new);
19 BCMATTACHFN(nvram_init)(void *si)
20 @@ -55,6 +58,7 @@ BCMATTACHFN(nvram_init)(void *si)
23 bcopy((char *)(&nvh[1]), new->vars, nvs);
24 + fixup_mac_addr(new);
28 @@ -164,3 +168,65 @@ nvram_getall(char *buf, int count)
33 +static bool nvram_is_valid_mac(struct ether_addr *mac)
35 + return mac && !(mac->octet[0] == 0x00 && mac->octet[1] == 0x90 && mac->octet[2] == 0x4c);
38 +static int nvram_increase_mac_addr(struct ether_addr *mac, u8 num)
40 + u8 *oui = mac->octet + ETHER_ADDR_LEN/2 - 1;
41 + u8 *p = mac->octet + ETHER_ADDR_LEN - 1;
52 + pr_err("unable to fetch mac address\n");
58 +static void nvram_change_mac_addr(vars_t *new, struct ether_addr *valid, const char *name)
61 + struct ether_addr macaddr;
63 + macaddr_c = findvar(new->vars, new->vars + new->size, name);
67 + bcm_ether_atoe(macaddr_c, &macaddr);
68 + if (nvram_is_valid_mac(&macaddr))
70 + nvram_increase_mac_addr(valid, 1);
71 + bcm_ether_ntoa(valid, macaddr_c);
74 +static void fixup_mac_addr(vars_t *new)
76 + char *macaddr_base_c;
77 + struct ether_addr macaddr_base;
79 + macaddr_base_c = findvar(new->vars, new->vars + new->size, "et0macaddr");
80 + if (!macaddr_base_c)
83 + bcm_ether_atoe(macaddr_base_c, &macaddr_base);
84 + if (!nvram_is_valid_mac(&macaddr_base))
87 + /* jump over the first free address so it can be used for wan */
88 + nvram_increase_mac_addr(&macaddr_base, 1);
89 + nvram_change_mac_addr(new, &macaddr_base, "sb/1/macaddr");
90 + nvram_change_mac_addr(new, &macaddr_base, "pci/1/1/macaddr");
91 + nvram_change_mac_addr(new, &macaddr_base, "pci/1/2/macaddr");
92 + nvram_change_mac_addr(new, &macaddr_base, "pci/2/1/macaddr");