Module Name: src Committed By: phx Date: Sun May 16 11:27:50 UTC 2010
Modified Files: src/sys/arch/sandpoint/include: bootinfo.h src/sys/arch/sandpoint/sandpoint: autoconf.c src/sys/arch/sandpoint/stand/netboot: brdsetup.c globals.h main.c skg.c src/sys/dev/pci: if_sk.c Log Message: Make netboot generate a BTINFO_NET bootinfo node for the Synology sk(4) NIC. It will pass the MAC address, which is read from Flash ROM, into the kernel. The kernel creates a "mac-address" device-property, which is used by sk(4), when given, before reading the MAC from its EEPROM. To generate a diff of this commit: cvs rdiff -u -r1.4 -r1.5 src/sys/arch/sandpoint/include/bootinfo.h cvs rdiff -u -r1.19 -r1.20 src/sys/arch/sandpoint/sandpoint/autoconf.c cvs rdiff -u -r1.13 -r1.14 src/sys/arch/sandpoint/stand/netboot/brdsetup.c cvs rdiff -u -r1.14 -r1.15 src/sys/arch/sandpoint/stand/netboot/globals.h cvs rdiff -u -r1.28 -r1.29 src/sys/arch/sandpoint/stand/netboot/main.c cvs rdiff -u -r1.2 -r1.3 src/sys/arch/sandpoint/stand/netboot/skg.c cvs rdiff -u -r1.66 -r1.67 src/sys/dev/pci/if_sk.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/arch/sandpoint/include/bootinfo.h diff -u src/sys/arch/sandpoint/include/bootinfo.h:1.4 src/sys/arch/sandpoint/include/bootinfo.h:1.5 --- src/sys/arch/sandpoint/include/bootinfo.h:1.4 Wed Oct 17 19:56:56 2007 +++ src/sys/arch/sandpoint/include/bootinfo.h Sun May 16 11:27:49 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: bootinfo.h,v 1.4 2007/10/17 19:56:56 garbled Exp $ */ +/* $NetBSD: bootinfo.h,v 1.5 2010/05/16 11:27:49 phx Exp $ */ /* * Copyright (c) 1997 @@ -42,6 +42,7 @@ #define BTINFO_CLOCK 4 #define BTINFO_BOOTPATH 5 #define BTINFO_ROOTDEVICE 6 +#define BTINFO_NET 7 struct btinfo_magic { struct btinfo_common common; @@ -76,6 +77,12 @@ unsigned cookie; }; +struct btinfo_net { + struct btinfo_common common; + char devname[16]; + uint8_t mac_address[6]; +}; + #define BOOTINFO_MAXSIZE 4096 #ifdef _KERNEL Index: src/sys/arch/sandpoint/sandpoint/autoconf.c diff -u src/sys/arch/sandpoint/sandpoint/autoconf.c:1.19 src/sys/arch/sandpoint/sandpoint/autoconf.c:1.20 --- src/sys/arch/sandpoint/sandpoint/autoconf.c:1.19 Wed Mar 18 10:22:35 2009 +++ src/sys/arch/sandpoint/sandpoint/autoconf.c Sun May 16 11:27:49 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: autoconf.c,v 1.19 2009/03/18 10:22:35 cegger Exp $ */ +/* $NetBSD: autoconf.c,v 1.20 2010/05/16 11:27:49 phx Exp $ */ /*- * Copyright (c) 1990 The Regents of the University of California. @@ -35,22 +35,25 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: autoconf.c,v 1.19 2009/03/18 10:22:35 cegger Exp $"); +__KERNEL_RCSID(0, "$NetBSD: autoconf.c,v 1.20 2010/05/16 11:27:49 phx Exp $"); #include <sys/param.h> #include <sys/systm.h> #include <sys/conf.h> #include <sys/device.h> + +#include <dev/cons.h> #include <dev/pci/pcivar.h> +#include <net/if.h> +#include <net/if_ether.h> + #include <machine/bootinfo.h> +#include <machine/pio.h> static struct btinfo_rootdevice *bi_rdev; static struct btinfo_bootpath *bi_path; - -#include <dev/cons.h> -#include <machine/pio.h> - +static struct btinfo_net *bi_net; /* * Determine i/o configuration for a machine. @@ -61,6 +64,7 @@ bi_rdev = lookup_bootinfo(BTINFO_ROOTDEVICE); bi_path = lookup_bootinfo(BTINFO_BOOTPATH); + bi_net = lookup_bootinfo(BTINFO_NET); if (config_rootfound("mainbus", NULL) == NULL) panic("configure: mainbus not configured"); @@ -85,18 +89,28 @@ void device_register(struct device *dev, void *aux) { + struct pci_attach_args *pa; - if (bi_rdev == NULL) - return; /* no clue to determine */ - - if (dev->dv_class == DV_IFNET - && device_is_a(dev, bi_rdev->devname)) { - struct pci_attach_args *pa = aux; - - if (bi_rdev->cookie == pa->pa_tag) + if (dev->dv_class == DV_IFNET) { + pa = aux; + if (bi_rdev != NULL && device_is_a(dev, bi_rdev->devname) + && bi_rdev->cookie == pa->pa_tag) booted_device = dev; + if (bi_net != NULL && device_is_a(dev, bi_net->devname)) { + prop_data_t pd; + + pd = prop_data_create_data_nocopy(bi_net->mac_address, + ETHER_ADDR_LEN); + KASSERT(pd != NULL); + if (prop_dictionary_set(device_properties(dev), + "mac-address", pd) == false) + printf("WARNING: unable to set mac-addr " + "property for %s\n", dev->dv_xname); + prop_object_release(pd); + bi_net = NULL; /* do it just once */ + } } - if (dev->dv_class == DV_DISK + if (bi_rdev != NULL && dev->dv_class == DV_DISK && device_is_a(dev, bi_rdev->devname)) { booted_device = dev; booted_partition = 0; Index: src/sys/arch/sandpoint/stand/netboot/brdsetup.c diff -u src/sys/arch/sandpoint/stand/netboot/brdsetup.c:1.13 src/sys/arch/sandpoint/stand/netboot/brdsetup.c:1.14 --- src/sys/arch/sandpoint/stand/netboot/brdsetup.c:1.13 Thu May 13 10:40:02 2010 +++ src/sys/arch/sandpoint/stand/netboot/brdsetup.c Sun May 16 11:27:49 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: brdsetup.c,v 1.13 2010/05/13 10:40:02 phx Exp $ */ +/* $NetBSD: brdsetup.c,v 1.14 2010/05/16 11:27:49 phx Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. @@ -707,3 +707,77 @@ break; } } + +struct fis_dir_entry { + char name[16]; + uint32_t startaddr; + uint32_t loadaddr; + uint32_t flashsize; + uint32_t entryaddr; + uint32_t filesize; + char pad[256 - (16 + 5 * sizeof(uint32_t))]; +}; + +#define FIS_LOWER_LIMIT 0xfff00000 + +/* + * Look for a Redboot-style Flash Image System FIS-directory and + * return a pointer to the start address of the requested file. + */ +static void * +redboot_fis_lookup(const char *filename) +{ + static const char FISdirname[16] = { + 'F', 'I', 'S', ' ', + 'd', 'i', 'r', 'e', 'c', 't', 'o', 'r', 'y', 0, 0, 0 + }; + struct fis_dir_entry *dir; + + /* + * The FIS directory is usually in the last sector of the flash. + * But we do not know the sector size (erase size), so start + * at 0xffffff00 and scan backwards in steps of the FIS directory + * entry size (0x100). + */ + for (dir = (struct fis_dir_entry *)0xffffff00; + (uint32_t)dir >= FIS_LOWER_LIMIT; dir--) + if (memcmp(dir->name, FISdirname, sizeof(FISdirname)) == 0) + break; + if ((uint32_t)dir < FIS_LOWER_LIMIT) { + printf("No FIS directory found!\n"); + return NULL; + } + + /* Now find filename by scanning the directory from beginning. */ + dir = (struct fis_dir_entry *)dir->startaddr; + while (dir->name[0] != 0xff && (uint32_t)dir < 0xffffff00) { + if (strcmp(dir->name, filename) == 0) + return (void *)dir->startaddr; /* found */ + dir++; + } + printf("\"%s\" not found in FIS directory!\n", filename); + return NULL; +} + +/* + * For cost saving reasons some NAS boxes are missing the ROM for the + * NIC's ethernet address and keep it in their Flash memory. + */ +void +read_mac_from_flash(uint8_t *mac) +{ + uint8_t *p; + + if (brdtype == BRD_SYNOLOGY) { + p = redboot_fis_lookup("vendor"); + if (p != NULL) { + memcpy(mac, p, 6); + return; + } + } else + printf("Warning: This board has no known method defined " + "to determine its MAC address!\n"); + + /* set to 00:00:00:00:00:00 in case of error */ + memset(mac, 0, 6); +} Index: src/sys/arch/sandpoint/stand/netboot/globals.h diff -u src/sys/arch/sandpoint/stand/netboot/globals.h:1.14 src/sys/arch/sandpoint/stand/netboot/globals.h:1.15 --- src/sys/arch/sandpoint/stand/netboot/globals.h:1.14 Sat May 8 19:41:07 2010 +++ src/sys/arch/sandpoint/stand/netboot/globals.h Sun May 16 11:27:49 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: globals.h,v 1.14 2010/05/08 19:41:07 phx Exp $ */ +/* $NetBSD: globals.h,v 1.15 2010/05/16 11:27:49 phx Exp $ */ /* clock feed */ #ifndef EXT_CLK_FREQ @@ -23,6 +23,7 @@ extern uint32_t cpuclock, busclock; unsigned mpc107memsize(void); +void read_mac_from_flash(uint8_t *); /* PPC processor ctl */ void __syncicache(void *, size_t); Index: src/sys/arch/sandpoint/stand/netboot/main.c diff -u src/sys/arch/sandpoint/stand/netboot/main.c:1.28 src/sys/arch/sandpoint/stand/netboot/main.c:1.29 --- src/sys/arch/sandpoint/stand/netboot/main.c:1.28 Thu May 13 10:40:02 2010 +++ src/sys/arch/sandpoint/stand/netboot/main.c Sun May 16 11:27:49 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: main.c,v 1.28 2010/05/13 10:40:02 phx Exp $ */ +/* $NetBSD: main.c,v 1.29 2010/05/16 11:27:49 phx Exp $ */ /*- * Copyright (c) 2007 The NetBSD Foundation, Inc. @@ -69,6 +69,7 @@ struct btinfo_clock bi_clk; struct btinfo_bootpath bi_path; struct btinfo_rootdevice bi_rdev; + struct btinfo_net bi_net; unsigned long marks[MARK_MAX]; unsigned lata[1][2], lnif[1][2]; unsigned memsize, tag; @@ -158,12 +159,19 @@ snprintf(bi_path.bootpath, sizeof(bi_path.bootpath), bootfile); snprintf(bi_rdev.devname, sizeof(bi_rdev.devname), rootdev); bi_rdev.cookie = tag; /* PCI tag for fxp netboot case */ + if (brdtype == BRD_SYNOLOGY) { + /* need to set MAC address for Marvell-SKnet */ + strcpy(bi_net.devname, "sk"); + memcpy(bi_net.mac_address, en, sizeof(en)); + } bi_add(&bi_cons, BTINFO_CONSOLE, sizeof(bi_cons)); bi_add(&bi_mem, BTINFO_MEMORY, sizeof(bi_mem)); bi_add(&bi_clk, BTINFO_CLOCK, sizeof(bi_clk)); bi_add(&bi_path, BTINFO_BOOTPATH, sizeof(bi_path)); bi_add(&bi_rdev, BTINFO_ROOTDEVICE, sizeof(bi_rdev)); + if (brdtype == BRD_SYNOLOGY) + bi_add(&bi_net, BTINFO_NET, sizeof(bi_net)); printf("entry=%p, ssym=%p, esym=%p\n", (void *)marks[MARK_ENTRY], Index: src/sys/arch/sandpoint/stand/netboot/skg.c diff -u src/sys/arch/sandpoint/stand/netboot/skg.c:1.2 src/sys/arch/sandpoint/stand/netboot/skg.c:1.3 --- src/sys/arch/sandpoint/stand/netboot/skg.c:1.2 Mon May 3 18:55:09 2010 +++ src/sys/arch/sandpoint/stand/netboot/skg.c Sun May 16 11:27:49 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: skg.c,v 1.2 2010/05/03 18:55:09 phx Exp $ */ +/* $NetBSD: skg.c,v 1.3 2010/05/16 11:27:49 phx Exp $ */ /*- * Copyright (c) 2010 Frank Wille. @@ -227,25 +227,20 @@ /* read ethernet address */ en = data; - for (i = 0; i < 6; i++) - en[i] = CSR_READ_1(l, SK_MAC0 + i); + if (brdtype == BRD_SYNOLOGY) + read_mac_from_flash(en); + else + for (i = 0; i < 6; i++) + en[i] = CSR_READ_1(l, SK_MAC0 + i); printf("MAC address %02x:%02x:%02x:%02x:%02x:%02x\n", en[0], en[1], en[2], en[3], en[4], en[5]); printf("PHY %d (%04x.%04x)\n", l->phy, mii_read(l, l->phy, 2), mii_read(l, l->phy, 3)); /* set station address */ - for (i = 0; i < 3; i++) { -#if 0 - CSR_WRITE_2(l, YUKON_SA1 + i * 4, - CSR_READ_2(l, SK_MAC0 + i * 2)); - CSR_WRITE_2(l, YUKON_SA2 + i * 4, - CSR_READ_2(l, SK_MAC1 + i * 2)); -#else + for (i = 0; i < 3; i++) CSR_WRITE_2(l, YUKON_SA1 + i * 4, (en[i * 2] << 8) | en[i * 2 + 1]); -#endif - } /* configure RX and TX MAC FIFO */ CSR_WRITE_1(l, SK_RXMF1_CTRL_TEST, RFCTL_RESET_CLEAR); Index: src/sys/dev/pci/if_sk.c diff -u src/sys/dev/pci/if_sk.c:1.66 src/sys/dev/pci/if_sk.c:1.67 --- src/sys/dev/pci/if_sk.c:1.66 Mon Apr 5 07:20:27 2010 +++ src/sys/dev/pci/if_sk.c Sun May 16 11:27:49 2010 @@ -1,4 +1,4 @@ -/* $NetBSD: if_sk.c,v 1.66 2010/04/05 07:20:27 joerg Exp $ */ +/* $NetBSD: if_sk.c,v 1.67 2010/05/16 11:27:49 phx Exp $ */ /*- * Copyright (c) 2003 The NetBSD Foundation, Inc. @@ -115,7 +115,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: if_sk.c,v 1.66 2010/04/05 07:20:27 joerg Exp $"); +__KERNEL_RCSID(0, "$NetBSD: if_sk.c,v 1.67 2010/05/16 11:27:49 phx Exp $"); #include "rnd.h" @@ -1209,6 +1209,7 @@ struct ifnet *ifp; bus_dma_segment_t seg; bus_dmamap_t dmamap; + prop_data_t data; void *kva; int i, rseg; int mii_flags = 0; @@ -1236,10 +1237,20 @@ * are operating in failover mode. Currently we don't * use this extra address. */ - for (i = 0; i < ETHER_ADDR_LEN; i++) - sc_if->sk_enaddr[i] = - sk_win_read_1(sc, SK_MAC0_0 + (sa->skc_port * 8) + i); - + data = prop_dictionary_get(device_properties(self), "mac-address"); + if (data != NULL) { + /* + * Try to get the station address from device properties + * first, in case the ROM is missing. + */ + KASSERT(prop_object_type(data) == PROP_TYPE_DATA); + KASSERT(prop_data_size(data) == ETHER_ADDR_LEN); + memcpy(sc_if->sk_enaddr, prop_data_data_nocopy(data), + ETHER_ADDR_LEN); + } else + for (i = 0; i < ETHER_ADDR_LEN; i++) + sc_if->sk_enaddr[i] = sk_win_read_1(sc, + SK_MAC0_0 + (sa->skc_port * 8) + i); aprint_normal(": Ethernet address %s\n", ether_sprintf(sc_if->sk_enaddr));