【FAQ】全志R329如何在DragonSN烧写mac地址?
-
问题背景
硬件:R528+ Wi-Fi模组(XR829)
软件:Tina3.0及以上
说明:该FAQ旨在介绍DragonSN烧写mac地址的过程。问题简述
如何从私有分区获取mac地址?
问题分析
从私有分区获取mac地址,需要利用到DragonSN工具烧写mac地址到私有分区,然后借助uboot以comdline的形式传递到内核,内核addr_mgt驱动解析。
这里简要描述一下上述过程:
1.lichee/brandy-2.0/u-boot-2018/board/sunxi/sunxi_bootargs.c
+int update_user_data_ali(void) +{ + int data_len; + int ret; + char output[SST_WIFI_MAC_ADDR_LEN+1]; + char *sst_info = NULL; + int sec_inited = !sunxi_secure_storage_init(); //分区初始化 + memset(output, 0, SST_WIFI_MAC_ADDR_LEN+1); //获取存放mac地址的地址空间并初始化 + if (sec_inited) { + sst_info = (char *)malloc(SST_INFO_KEY_VALUE_ACTUAL_LEN); //分配存放mac地址的空间并赋值给sst_info结构体 + if (get_boot_work_mode() != WORK_MODE_BOOT) { + return 0; + } + + ret = sunxi_secure_object_read(SST_INFO_KEY_NAME, sst_info, SST_INFO_KEY_VALUE_ACTUAL_LEN, &data_len); //从flash secure storage读出 + if (ret) + pr_msg("=========%s->%d sunxi_secure_object_read failed==============\n", __func__, __LINE__); + memcpy(output, sst_info + SST_WIFI_MAC_ADDR_OFFSET, SST_WIFI_MAC_ADDR_LEN); + env_set("wifi_mac", output); + pr_msg("=========%s->%d fly test wifi_mac:%s==============\n", __func__, __LINE__, output); + }else{ + pr_msg("=========%s->%d sunxi_secure_storage_init failed==============\n", __func__, __LINE__); + } + + free(sst_info); + return 0; +}
通过sunxi_secure_object_read()接口根据偏移量读取分区中已经烧好的mac地址,赋值给wifi_mac。在通过env_set()接口将获取到的mac地址传递到env。
2.device/config/chips/r818/configs/ailabs_dictpen/linux/env.cfg
27 #set kernel cmdline if boot.img or recovery.img has no cmdline we will use this 28 setargs_nand=setenv bootargs console=${console}...mac_addr=${mac} wifi_mac=${wifi_mac} bt_mac=${bt_mac} 29 setargs_mmc=setenv bootargs console=${console}...mac_addr=${mac} wifi_mac=${wifi_mac} bt_mac=${bt_mac}
内核读取env.cfg时再把wifi_mac取出来,通过addr-mgt驱动获取。
3.lichee/linux-4.9/drivers/misc/sunxi-addr-mgt/sunxi-addr-mgt.c
83 int get_wifi_custom_mac_address(char *addr_str) 84 { 85 if (IS_TYPE_INVALID(info.type_cur_wifi) || 86 addr_parse(info.addr_wifi, 1)) 87 return -1; 88 89 strcpy(addr_str, info.addr_wifi); //直接拷贝info结构体的mac地址属性,最原始的就是uboot阶段的sst_info 90 return info.type_cur_wifi; 91 }
4.xr829驱动获取lichee/linux-4.9/drivers/net/wireless/xr829/wlan/main.c
478 extern int get_wifi_custom_mac_address(char *addr_str); 479 480 #define MAC_FROM_CHIPID 481 static void xradio_get_mac_addrs(u8 *macaddr) 482 { 483 int ret = 0; 484 char addr_str[20]; 485 SYS_BUG(!macaddr); 486 /* Check mac addrs param, if exsist, use it first.*/ 487 #ifdef XRADIO_MACPARAM_HEX 488 memcpy(macaddr, xradio_macaddr_param, ETH_ALEN); 489 #else 490 if (xradio_macaddr_param) { 491 ret = xradio_macaddr_char2val(macaddr, xradio_macaddr_param); 492 } 493 #endif 494 if (ret < 0 || !MACADDR_VAILID(macaddr)) { 495 ret = get_wifi_custom_mac_address(addr_str); //直接调用addr_mgt驱动的接口,即从分区读的方式获取mac地址。 496 if (ret != -1) { 497 sscanf(addr_str, "%02hhx:%02hhx:%02hhx:%02hhx:%02hhx:%02hhx", 498 &macaddr[0], &macaddr[1], &macaddr[2], 499 &macaddr[3], &macaddr[4], &macaddr[5]); 500 } 501 } 502 503 /* Use random value to set mac addr for the first time, 504 * and save it in wifi config file. TODO: read from product ID*/ 505 if (ret < 0 || !MACADDR_VAILID(macaddr)) { 506 #ifdef XRADIO_MACPARAM_HEX 507 ret = access_file(WIFI_CONF_PATH, macaddr, ETH_ALEN, 1); //自定义mac地址写入文件后,从文件获取mac地址 508 #else 509 char c_mac[XRADIO_MAC_CHARLEN+2] = {0}; 510 ret = access_file(WIFI_CONF_PATH, c_mac, XRADIO_MAC_CHARLEN, 1); 511 if (ret >= 0) { 512 ret = xradio_macaddr_char2val(macaddr, c_mac); 513 } 514 #endif 515 516 if (ret < 0 || !MACADDR_VAILID(macaddr)) { 517 #if defined(MAC_FROM_CHIPID) 518 u32 databuf[4] = {0}; 519 520 sunxi_get_soc_chipid((u8 *)databuf); //获取chipid后定制mac地址的方式 521 macaddr[0] = (((databuf[1] >> 28) & 0x0f) | ((databuf[2] & 0x0f) << 4)) & 0xff; 522 macaddr[1] = (databuf[2] >> 4) & 0xff; 523 macaddr[2] = (databuf[2] >> 12) & 0xff; 524 macaddr[3] = (databuf[3] >> 6) & 0xff; 525 macaddr[4] = (databuf[3] >> 16) & 0xff; 526 macaddr[5] = (databuf[3] >> 26) & 0xff; 527 #else 528 get_random_bytes(macaddr, 6); //随机生成mac地址的方式 529 #endif 530 macaddr[0] &= 0xFC; 531 #ifdef XRADIO_MACPARAM_HEX 532 ret = access_file(WIFI_CONF_PATH, macaddr, ETH_ALEN, 0); 533 #else 534 ret = xradio_macaddr_val2char(c_mac, macaddr); 535 ret = access_file(WIFI_CONF_PATH, c_mac, ret, 0); 536 #endif 537 if (ret < 0) 538 xradio_dbg(XRADIO_DBG_ERROR, "Access_file failed, path:%s!\n", 539 WIFI_CONF_PATH); 540 if (!MACADDR_VAILID(macaddr)) { 541 xradio_dbg(XRADIO_DBG_WARN, "Use default Mac addr!\n"); //驱动默认可以写死一个mac地址。 542 macaddr[0] = 0xDC; 543 macaddr[1] = 0x44; 544 macaddr[2] = 0x6D; 545 } else { 546 xradio_dbg(XRADIO_DBG_NIY, "Use random Mac addr!\n"); 547 } 548 } else { 549 xradio_dbg(XRADIO_DBG_NIY, "Use Mac addr in file!\n"); 550 } 551 } 552 xradio_dbg(XRADIO_DBG_NIY, "MACADDR=%02x:%02x:%02x:%02x:%02x:%02x\n", 553 macaddr[0], macaddr[1], macaddr[2], 554 macaddr[3], macaddr[4], macaddr[5]); 555 }
解决方法
1.工作获取
从全志一号通入口获取
https://one.allwinnertech.com/#/devtool?menuID=37
2.烧写流程
前提条件:软件支持从private分区获取mac地址。
2.1配置添加类型
2.2设置key类型
2.3开始烧写
2.4烧写成功
3.确认操作
可以直接通过系统起来后ifconfig命令查看mac地址是否与烧写的一致 -
-
-
-
-
-
Copyright © 2024 深圳全志在线有限公司 粤ICP备2021084185号 粤公网安备44030502007680号