修改龙芯3B的itx主板的mac地址

龙芯3B-itx 小板, 使用了intel82574l的网卡, 所以改mac就很简单了。

 

debian下安装ethtool软件包。

aptitude install ethtool

然后直接改mac地址为 00:23:9e:00:00:01

ethtool --change-eeprom eth0 magic 0x10d38086 offset 0x00 value 0x00

ethtool --change-eeprom eth0 magic 0x10d38086 offset 0x01 value 0x23

ethtool --change-eeprom eth0 magic 0x10d38086 offset 0x02 value 0x9e

ethtool --change-eeprom eth0 magic 0x10d38086 offset 0x03 value 0x00

ethtool --change-eeprom eth0 magic 0x10d38086 offset 0x04 value 0x00

ethtool --change-eeprom eth0 magic 0x10d38086 offset 0x05 value 0x01

0x10d38086 是网卡的pid vid    ,lcpci -nn 可以看到

03:00.0 Ethernet controller [0200]: Intel Corporation 82574L Gigabit Network Connection [8086:10d3]

应该是新版本的内核的功能,现在修改e1000e网卡的eeprom,可以自动计算校验和了,以前需要自己算一下,eeprom的长度0x40个字, 高位在后,累加起来等于0xbaba.

可以用ethtool --eeprom-dump 来显示eeprom内容

root@henanzls:~# ethtool --eeprom-dump eth0
Offset        Values
------        ------

0x0000:        00 23 9e 00 00 01 20 0c 46 f7 13 20 ff ff ff ff

0x0010:        ff ff ff ff 6b 02 00 00 86 80 d3 10 ff ff 5a 80

0x0020:        00 00 01 20 74 7e ff ff 00 10 c8 00 00 00 04 27

0x0030:        c9 6c 50 31 3a 07 0b 46 84 2d 40 01 00 f0 01 0f

0x0040:        00 60 80 00 04 0f ff 7f 01 4d 00 c6 00 00 ff 20

0x0050:        28 00 03 00 00 00 00 00 00 00 03 00 00 00 ff ff

0x0060:        00 01 00 40 1c 12 07 40 ff ff ff ff ff ff ff ff

0x0070:        ff ff ff ff ff ff ff ff ff ff 00 01 ff ff 5e b7

 

校验算法在linux内核的 drivers/net/ethernet/intel/e1000e/nvm.c

提取出来如下:

<pre>

#include <stdio.h>
#include <stdint.h>
uint8_t nv[300]={
        0x00,0x23,0x9e,0x00,0x00,0x01,0x20,0x0c,0x46,0xf7,0x13,0x20,0xff,0xff,0xff,0xff,
        0xff,0xff,0xff,0xff,0x6b,0x02,0x00,0x00,0x86,0x80,0xd3,0x10,0xff,0xff,0x5a,0x80,
        0x00,0x00,0x01,0x20,0x74,0x7e,0xff,0xff,0x00,0x10,0xc8,0x00,0x00,0x00,0x04,0x27,
        0xc9,0x6c,0x50,0x31,0x3a,0x07,0x0b,0x46,0x84,0x2d,0x40,0x01,0x00,0xf0,0x01,0x0f,
        0x00,0x60,0x80,0x00,0x04,0x0f,0xff,0x7f,0x01,0x4d,0x00,0xc6,0x00,0x00,0xff,0x20,
        0x28,0x00,0x03,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x03,0x00,0x00,0x00,0xff,0xff,
        0x00,0x01,0x00,0x40,0x1c,0x12,0x07,0x40,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,
        0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x00,0x01,0xff,0xff,0x4c,0x0c
};

#define NVM_CHECKSUM_REG 0x3f
#define NVM_SUM 0xBABA

void main(void)
{
        uint16_t checksum = 0;
        uint16_t i, nvm_data;

        for (i = 0; i < (NVM_CHECKSUM_REG +1); i++) {

                nvm_data = nv[i*2] | (nv[i*2+1]<<8);
                if(i % 8==0) printf("\n0x%04x: ",i);
                printf("%02x %02x ",nv[i*2],nv[i*2+1]);
                checksum += nvm_data;
        }

        if (checksum != (uint16_t)NVM_SUM) {
                printf("\nNVM Checksum Invalid,%04x\n",checksum);
                checksum=checksum-nvm_data;
                printf("\nold=%02x %02x\n",nvm_data&0xff,(nvm_data&0xff00)>>8);
                nvm_data=NVM_SUM -checksum;
                printf("\nnew=%02x %02x\n",nvm_data&0xff,(nvm_data&0xff00)>>8);
        } else {
                printf("\nnew=%02x %02x\n",nvm_data&0xff,(nvm_data&0xff00)>>8);
        }

}
</pre>