歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
Linux教程網 >> Linux編程 >> Linux編程 >> u-boot2010.03 移植篇(四)-----支持DM9000,實現tftp下載

u-boot2010.03 移植篇(四)-----支持DM9000,實現tftp下載

日期:2017/3/1 10:07:28   编辑:Linux編程

相關系列閱讀:

u-boot2010.03 移植篇(一)-----建立編譯目標 http://www.linuxidc.com/Linux/2012-11/73814.htm
u-boot2010.03 移植篇(二)-----修改start.S,支持nand啟動 http://www.linuxidc.com/Linux/2012-11/73815.htm
u-boot2010.03 移植篇(三)-----修正配置文件.解決內存大小顯示問題 http://www.linuxidc.com/Linux/2012-11/73816.htm
u-boot2010.03 移植篇(四)-----支持DM9000,實現tftp下載 http://www.linuxidc.com/Linux/2012-11/73817.htm

----------------------------------------------------------
使用環境
PC: Ubuntu 11.04
kernel: 2.6.32-28-generic
corss: arm-linux-gcc 4.3.2
arm: s3c6410
uboot: uboot-2010-03
----------------------------------------------------------
作者: LvApp
聯系方式: [email protected]

一切版權均有作者所有,歡迎轉載,請指明出處,如何修改請與本人聯系,謝謝

哇塞..tftp下載,很多6410買的開發板夢寐以求需要的功能,為嘛?當然為了方便實現系統更新.一鍵下載之類的..想想都覺得興奮..那就開始吧

首先.前陣子本人比較忙..所以一直沒有更新.再加上.最近在看別的資料.所以在寫這些內容的時候,我還得自己實戰下.保證寫出來沒有錯誤吧..

這篇內容不多.因為uboot已經做的很好了..幾乎不需要修改太多的東西,就能支持dm9000這款用的比較多的網卡了..

這篇文章其實有稍許超前了.因為對應的分析貼還沒寫好.所以這裡我會適當加上一些理論補充,比如:我為什麼要加這句代碼到這個地方?類似於這樣的問題

根據smdk6400 copy 過來的那麼默認用的就是cs8900這塊網卡,可以從configs/smdk6410.h這個文件中看到....這裡當然不需要了..所以,果斷先把關於8900的宏

全都去掉..如下:

像這樣.去掉先...接著就是添加DM9000相關的宏了...這裡我也貼出來..

  1. #define CONFIG_DM9000_NO_SROM //此處說明,該網卡沒有eeprom存儲..其實dm9000是有的,只是沒用,所以只好說沒有了
  2. #define CONFIG_DM9000 //定義DM9000 回頭初始化驅動,就判斷這個宏了
  3. #define CONFIG_DRIVER_DM9000 //開啟DM9000驅動的代碼
  4. #define CONFIG_DM9000_BASE 0x18800300 //這個宏是定義網卡連接到你的arm上面的地址.屬於sram1地址區域
  5. #define DM9000_IO CONFIG_DM9000_BASE //根據網卡手冊,指定I/O DATA操作地址
  6. #define DM9000_DATA (CONFIG_DM9000_BASE + 0x04)
  7. #define CONFIG_DM9000_USE_16BIT //指明使用16位數據模式,該宏其實是為了方便知道網卡信息而已,在代碼中沒有半毛錢關系...網卡的16位選擇,
  8. //是在內存設置的時候設置的...也就是說設定sram1內存寄存器
  9. #define CONFIG_ETHADDR 00:40:5C:26:0A:5B //這裡定義一些網絡相關參數,這些以後也可以直接手動設定環境變量.
  10. #define CONFIG_NETMASK 255.255.255.0 //放在這裡也是比較方面而已
  11. #define CONFIG_IPADDR 192.168.1.123
  12. #define CONFIG_SERVERIP 192.168.1.100
  13. #define CONFIG_GATEWAYIP 192.168.1.1
  14. #define CONFIG_DM9000_DEBUG //開啟調試

ok 網卡的配置就好了...非常簡單..就是開啟一些宏和設定一些相關的參數而已...

下面去添加dm9000的初始化,不然不能用,那麼初始化放哪呢?網卡初始化的地方究竟是吧....在第一部分的時候分析.沒有發現關於網卡初始化的地方...那麼也就是說.網卡

的初始化其實是在第二部分裡面完成的?沒錯....直接定位到start_armboot第二部分代碼入口...

  1. #if defined(CONFIG_CMD_NET)
  2. #if defined(CONFIG_NET_MULTI)
  3. puts ("Net: ");
  4. #endif
  5. eth_initialize(gd->bd); /* 這裡就是網卡的初始化函數了 */
  6. #if defined(CONFIG_RESET_PHY_R)
  7. debug ("Reset Ethernet PHY\n");
  8. reset_phy();
  9. #endif

直接定位到 eth_initialize函數中...這個函數蠻長的.....

  1. int eth_initialize(bd_t *bis)
  2. {
  3. unsigned char env_enetaddr[6];
  4. int eth_number = 0;
  5. eth_devices = NULL;
  6. eth_current = NULL;
  7. show_boot_progress (64);
  8. #if defined(CONFIG_MII) || defined(CONFIG_CMD_MII)
  9. miiphy_init();
  10. #endif
  11. /* Try board-specific initialization first. If it fails or isn't
  12. * present, try the cpu-specific initialization */
  13. if (board_eth_init(bis) < 0) /* 注意這裡有個板級初始化調用...board_eth_init(bis) */
  14. cpu_eth_init(bis);
  15. #if defined(CONFIG_DB64360) || defined(CONFIG_CPCI750)
  16. mv6436x_eth_initialize(bis);
  17. #endif
  18. #if defined(CONFIG_DB64460) || defined(CONFIG_P3Mx)
  19. mv6446x_eth_initialize(bis);
  20. #endif
  21. if (!eth_devices) {
  22. puts ("No ethernet found.\n");
  23. show_boot_progress (-64);
  24. } else {
  25. struct eth_device *dev = eth_devices;
  26. char *ethprime = getenv ("ethprime");
  27. show_boot_progress (65);
  28. do {
  29. if (eth_number)
  30. puts (", ");
  31. printf("%s", dev->name);
  32. if (ethprime && strcmp (dev->name, ethprime) == 0) {
  33. eth_current = dev;
  34. puts (" [PRIME]");
  35. }
  36. eth_getenv_enetaddr_by_index(eth_number, env_enetaddr);/* 獲取網卡ethaddr的MAC地址 */
  37. if (memcmp(env_enetaddr, "\0\0\0\0\0\0", 6)) {
  38. if (memcmp(dev->enetaddr, "\0\0\0\0\0\0", 6) &&
  39. memcmp(dev->enetaddr, env_enetaddr, 6))
  40. {
  41. printf ("\nWarning: %s MAC addresses don't match:\n",
  42. dev->name);
  43. printf ("Address in SROM is %pM\n",
  44. dev->enetaddr);
  45. printf ("Address in environment is %pM\n",
  46. env_enetaddr);
  47. }
  48. memcpy(dev->enetaddr, env_enetaddr, 6);
  49. }
  50. eth_number++;
  51. dev = dev->next;
  52. } while(dev != eth_devices);
  53. #ifdef CONFIG_NET_MULTI
  54. /* update current ethernet name */
  55. if (eth_current) {
  56. char *act = getenv("ethact");
  57. if (act == NULL || strcmp(act, eth_current->name) != 0)
  58. setenv("ethact", eth_current->name);
  59. } else
  60. setenv("ethact", NULL);
  61. #endif
  62. putc ('\n');
  63. }
  64. return eth_number;
  65. }
Copyright © Linux教程網 All Rights Reserved