On 25.11.2016 16:30, Olliver Schinagl wrote: > This patch allows Kconfig to enable and set parameters to make it > possible to read the MAC address from an EEPROM. The net core layer then > uses this information to read MAC addresses from this EEPROM. > > Besides the various tuneables as to how to access the eeprom (bus, > address, addressing mode/length, 2 configurable that are EEPROM generic > (e.g. SPI or some other form of access) which are: > > NET_ETHADDR_EEPROM_OFFSET, indicating where in the EEPROM the start of > the MAC address is. The default is 8 allowing for 8 bytes before the MAC > for other purposes (header MAGIC for example). > > NET_ETHADDR_EEPROM_CRC8, indicating the MAC is appended with a CRC8-CCIT > checksum that should be verified. > > Currently only I2C eeproms have been tested and thus only those options > are available, but shouldn't be a limit. NET_ETHADDR_EEPROM_SPI can be > just as created and added. > > The code currently first checks if there is a non-zero MAC address in > the eeprom. If that fails to be the case, the read_rom_hwaddr can be > used by a board to supply the MAC in other ways. > > If both these fails, the other code is still in place to query the > environent, which then can be used to override the hardware supplied > data. > > Signed-off-by: Olliver Schinagl <oli...@schinagl.nl> > --- > doc/README.enetaddr | 99 > +++++++++++++++++++++++++++++++++++++++++++++++++++++ > include/net.h | 14 ++++++++ > net/Kconfig | 59 +++++++++++++++++++++++++++++++ > net/eth-uclass.c | 9 +++-- > net/eth_common.c | 34 ++++++++++++++++++ > net/eth_legacy.c | 2 ++ > 6 files changed, 214 insertions(+), 3 deletions(-) > > diff --git a/doc/README.enetaddr b/doc/README.enetaddr > index 50e4899..89c1f7d 100644 > --- a/doc/README.enetaddr > +++ b/doc/README.enetaddr > @@ -47,6 +47,105 @@ Correct flow of setting up the MAC address (summarized): > Previous behavior had the MAC address always being programmed into hardware > in the device's init() function. > > +-------- > + EEPROM > +-------- > + > +Boards may come with an EEPROM specifically to store configuration bits, such > +as a MAC address. Using CONFIG_NET_ETHADDR_EEPROM enables this feature. > +Depending on the board, the EEPROM may be connected on various methods, but > +currently, only the I2C bus can be used via CONFIG_NET_ETHADDR_EEPROM_I2C. > + > +The following config options are available, > +CONFIG_NET_ETHADDR_EEPROM_I2C_BUS is the I2C bus on which the eeprom is > present. > +CONFIG_NET_ETHADDR_EEPROM_I2C_ADDR sets the address of the EEPROM, which > +defaults to the very common 0x50. Small size EEPROM's generally use single > byte > +addressing but larger EEPROM's may use double byte addressing, which can be > +configured using CONFIG_NET_ETHADDR_EEPROM_ADDRLEN. > + > +Within the EEPROM, the MAC address can be stored on any arbitrary offset, > +CONFIG_NET_ETHADDR_EEPROM_OFFSET sets this to 8 as a default however, > allowing > +the first 8 bytes to be used for an optional data, for example a > configuration > +struct where the mac address is part of. > + > +Appending the 6 (ARP_HLEN) bytes is a CRC8 byte over the previous ARP_HLEN > +bytes. Whether to check this CRC8 or not is dependent on > +CONFIG_NET_ETHADDR_EEPROM_CRC8. > + > +To keep things nicely aligned, a final 'reserved' byte is added to the mac > +address + crc8 combo. > + > +A board may want to store more information in its eeprom, using the following > +example layout, this can be achieved. > + > +struct mac_addr { > + uint8_t mac[ARP_HLEN]; > + uint8_t crc8; > + uint8_t reserved; > +}; > + > +struct config_eeprom { > + uint32_t magic; > + uint8_t version; > + uint8_t reserved[2]; > + uint8_t mac_cnt; > + struct mac_addr[mac_cnt]; > +}; > + > +Filling this in: > +struct config_eeprom eeprom = { > + .magic = { 'M', 'g', 'i', 'c' }, > + .reserved = { 0x00, 0x00 }, > + .mac_cnt = 2, > + .mac_addr = { > + { > + .mac = { > + 0x01, 0x23, 0x45, > + 0x67, 0x89, 0xab, > + }, > + .crc8 = 0xbe, > + .reserved = 0x00, > + }, { > + .mac = { > + 0xba, 0x98, 0x76, > + 0x54, 0x32, 0x10, > + }, > + .crc8 = 0x82, > + .reserved = 0x00, > + }, > + }, > +}; > + > +The eeprom content would look like this. > + > +00000000 4d 67 69 63 01 00 00 02 01 23 45 67 89 ab be 00 |Mgic.....#Eg....| > +00000010 ba 98 76 54 32 10 82 00 |..vT2...| > + > +This can be done from linux using the i2c-tools: > + > +i2cset I2CBUS 0x50 0x08 0x01 > +i2cset I2CBUS 0x50 0x09 0x23 > +i2cset I2CBUS 0x50 0x0a 0x45 > +i2cset I2CBUS 0x50 0x0b 0x67 > +i2cset I2CBUS 0x50 0x0c 0x89 > +i2cset I2CBUS 0x50 0x0d 0xab > +i2cset I2CBUS 0x50 0x0e 0xbe > + > +Alternativly this can be done from the u-boot console as: > + > +u-boot> mm.b 0 > +00000000: 00 ? 01 > +00000001: 23 ? 23 > +00000002: 45 ? 45 > +00000003: 67 ? 67 > +00000004: 89 ? 89 > +00000005: ab ? ab > +00000006: be ? be > +00000007: 00 ? q > +i2c dev I2CBUS > +i2c write 0 50 8 7 > +i2c md 50 8 > + > ------- > Usage > ------- > diff --git a/include/net.h b/include/net.h > index 08f8af8..e50ab5d 100644 > --- a/include/net.h > +++ b/include/net.h > @@ -248,6 +248,20 @@ int eth_getenv_enetaddr(const char *name, uchar > *enetaddr); > int eth_setenv_enetaddr(const char *name, const uchar *enetaddr); > > /** > + * eeprom_read_enetaddr() - Read the hardware address from an eeprom > + * > + * This function tries to read the MAC address from an eeprom as can be read > + * in docs/README.enetaddr. > + * > + * @index: index of the interface to get the hwaddr for > + * @enetaddr: pointer for the found hwaddr. Needs to be atleast > ARP_HLEN > + * @return: 0 on success, non-zero is error status. Additionally hwaddr > + * is set to 00:00:00:00:00. This is also the case if > + * CONFIG_NET_ETHADDR_EEPROM is not set. > + */ > +int eeprom_read_enetaddr(const int index, unsigned char *enetaddr); > + > +/** > * eth_setenv_enetaddr_by_index() - set the MAC address environment variable > * > * This sets up an environment variable with the given MAC address > (@enetaddr). > diff --git a/net/Kconfig b/net/Kconfig > index 414c549..f699e1c 100644 > --- a/net/Kconfig > +++ b/net/Kconfig > @@ -7,6 +7,65 @@ menuconfig NET > > if NET > > +config NET_ETHADDR_EEPROM > + bool "Get ethaddr from eeprom" > + help > + Selecting this will try to get the Ethernet address from an onboard > + EEPROM and set into the environment if and only if the environment > + does currently not already hold a MAC address. For more information > + see doc/README.enetaddr. > + > +config NET_ETHADDR_EEPROM_I2C > + depends on NET_ETHADDR_EEPROM > + bool "EEPROM on I2C bus" > + help > + This switch enables checks for an EEPROM on the I2C bus. Naturally > + this will only work if there is an actual EEPROM connected on the > + I2C bus and the bus and device are properly configured via the > + options below. > + > +config NET_ETHADDR_EEPROM_I2C_BUS > + depends on NET_ETHADDR_EEPROM_I2C > + int "I2C bus" > + default 0 > + help > + Select the bus on which the EEPROM is present, defaults to bus 0. > + Remember to also make the selected bus available via I2Cn_ENABLE. > + > +config NET_ETHADDR_EEPROM_I2C_ADDR > + depends on NET_ETHADDR_EEPROM_I2C > + hex "EEPROM address" > + default 0x50 > + help > + Select the address of the EEPROM, defaults to address 0x50. > + > +config NET_ETHADDR_EEPROM_I2C_ADDRLEN > + depends on NET_ETHADDR_EEPROM_I2C > + int "EEPROM address length" > + default 1 > + help > + Number of bytes to be used for the I2C address length. Typically 1, > + 2 for large memories, 0 for register type devices with only one > + register. > + > +config NET_ETHADDR_EEPROM_OFFSET > + depends on NET_ETHADDR_EEPROM > + int "EEPROM offset" > + default 8 > + help > + Select the byte offset of the MAC address within the page, > + defaults to byte 8.
I would prefer to all these values to be in hex because i2c commands are also taking values in hex. > + > +config NET_ETHADDR_EEPROM_CRC8 > + depends on NET_ETHADDR_EEPROM > + bool "Check CRC8 of MAC" > + default y > + help > + Optionally, it is possible to run a CRC-8-CCITT check on the MAC > + address. To do so, the MAC address is stored with a CRC8 byte append. > + This option enables the CRC check of the MAC address against the CRC > + byte. > + Would it be possible to have default n here? I would guess that more boards don't have this CRC8 sums. Thanks, Michal _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de http://lists.denx.de/mailman/listinfo/u-boot