在U-boot上搭建TFTP服务器
来源:互联网 发布:电子产品目录软件 编辑:程序博客网 时间:2024/05/17 23:43
实现这个的整体目的是为了以后实现远程更新u-boot kernel rootfs而设计的。目前已经完全在u-boot实现的TFTP服务器了。先把它贴出来。
说明:
Uboot3是没有改动的。
9UbootTftpServemini是移植好的。
u-boot版本为2009.11.
交叉工具链版本为:4.4.3
测试开发板:mini2440(这些修改都是板级无关的,其它板子应该也是可以的)
参考文档《BootLoader TFTP服务器功能的追加》
一.添加命令tftpserver
模仿tftpboot来添加,主要修改common/cmd_net.c和include/net.h。具体的改动如下:
--- Uboot3/common/cmd_net.c 2013-03-09 17:35:54.186849800 +0800
+++ 9UbootTftpServemini/common/cmd_net.c 2013-03-16 16:38:52.017695933 +0800
@@ -54,6 +54,17 @@
"[loadAddress] [[hostIPaddr:]bootfilename]"
);
+int do_tftpserver (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ return netboot_common (TFTPSERVER , cmdtp, argc, argv);
+}
+
+U_BOOT_CMD(
+ tftpserver, 1, 1, do_tftpserver,
+ "tftpserver-set TFTP server, wait client data.\n",
+ "[] []"
+);
+
int do_rarpb (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
{
return netboot_common (RARP, cmdtp, argc, argv);--- Uboot3/include/net.h 2013-03-09 17:35:55.110849761 +0800
+++ 9UbootTftpServemini/include/net.h 2013-03-16 17:02:29.281754689 +0800
@@ -356,7 +357,7 @@
extern int NetRestartWrap; /* Tried all network devices */
#endif
-typedef enum { BOOTP, RARP, ARP, TFTP, DHCP, PING, DNS, NFS, CDP, NETCONS, SNTP } proto_t;
+typedef enum { BOOTP, RARP, ARP, TFTP, TFTPSERVER, DHCP, PING, DNS, NFS, CDP, NETCONS, SNTP } proto_t;
/* from net/net.c */
extern char BootFile[128]; /* Boot File name */
+++ 9UbootTftpServemini/common/cmd_net.c 2013-03-16 16:38:52.017695933 +0800
@@ -54,6 +54,17 @@
"[loadAddress] [[hostIPaddr:]bootfilename]"
);
+int do_tftpserver (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ return netboot_common (TFTPSERVER , cmdtp, argc, argv);
+}
+
+U_BOOT_CMD(
+ tftpserver, 1, 1, do_tftpserver,
+ "tftpserver-set TFTP server, wait client data.\n",
+ "[] []"
+);
+
int do_rarpb (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
{
return netboot_common (RARP, cmdtp, argc, argv);--- Uboot3/include/net.h 2013-03-09 17:35:55.110849761 +0800
+++ 9UbootTftpServemini/include/net.h 2013-03-16 17:02:29.281754689 +0800
@@ -356,7 +357,7 @@
extern int NetRestartWrap; /* Tried all network devices */
#endif
-typedef enum { BOOTP, RARP, ARP, TFTP, DHCP, PING, DNS, NFS, CDP, NETCONS, SNTP } proto_t;
+typedef enum { BOOTP, RARP, ARP, TFTP, TFTPSERVER, DHCP, PING, DNS, NFS, CDP, NETCONS, SNTP } proto_t;
/* from net/net.c */
extern char BootFile[128]; /* Boot File name */
这样就可以用这个命令了如下图所示:
二.网络层移植
--- Uboot3/include/net.h 2013-03-09 17:35:55.110849761 +0800
+++ 9UbootTftpServemini/include/net.h 2013-03-16 17:02:29.281754689 +0800
@@ -329,6 +329,7 @@
extern uchar NetServerEther[6]; /* Boot server enet address */
extern IPaddr_t NetOurIP; /* Our IP addr (0 = unknown) */
extern IPaddr_t NetServerIP; /* Server IP addr (0 = unknown) */
+extern IPaddr_t NetClientIP; /* Server IP addr (0 = unknown) */
extern volatile uchar * NetTxPacket; /* THE transmit packet */
extern volatile uchar * NetRxPackets[PKTBUFSRX];/* Receive packets */
extern volatile uchar * NetRxPacket; /* Current receive packet */--- Uboot3/net/net.c 2013-03-09 17:35:54.282849796 +0800
+++ 9UbootTftpServemini/net/net.c 2013-03-17 12:26:15.460618862 +0800
@@ -80,6 +80,7 @@
#include <net.h>
#include "bootp.h"
#include "tftp.h"
+#include "tftpserver.h"
#include "rarp.h"
#include "nfs.h"
#ifdef CONFIG_STATUS_LED
@@ -138,6 +139,7 @@
{ 0, 0, 0, 0, 0, 0 };
IPaddr_t NetOurIP; /* Our IP addr (0 = unknown) */
IPaddr_t NetServerIP; /* Server IP addr (0 = unknown) */
+IPaddr_t NetClientIP; /* Server IP addr (0 = unknown) */
volatile uchar *NetRxPacket; /* Current receive packet */
int NetRxPacketLen; /* Current rx packet length */
unsigned NetIPID; /* IP packet ID */
@@ -279,6 +281,7 @@
static void
NetInitLoop(proto_t protocol)
{
+ debug("NetInitLoop ... \n");
static int env_changed_id = 0;
bd_t *bd = gd->bd;
int env_id = get_env_id ();
@@ -389,6 +392,12 @@
TftpStart();
break;
+ case TFTPSERVER:
+ puts("net.c/TFTPSERVER...\n");
+ /* always use ARP to get server ethernet address */
+ TftpServerStart();
+ break;
+
#if defined(CONFIG_CMD_DHCP)
case DHCP:
BootpTry = 0;
@@ -1672,6 +1681,7 @@
/*
* IP header OK. Pass the packet to the current handler.
*/
+ NetClientIP = NetReadIP(&ip->ip_src);
(*packetHandler)((uchar *)ip +IP_HDR_SIZE,
ntohs(ip->udp_dst),
ntohs(ip->udp_src),
@@ -1715,6 +1725,11 @@
case NFS:
#endif
case NETCONS:
+ case TFTPSERVER:
+ if (NetOurIP == 0) {
+ puts ("*** ERROR: `ipaddr' not set\n");
+ return (1);
+ }
case TFTP:
if (NetServerIP == 0) {
puts ("*** ERROR: `serverip' not set\n");
+++ 9UbootTftpServemini/include/net.h 2013-03-16 17:02:29.281754689 +0800
@@ -329,6 +329,7 @@
extern uchar NetServerEther[6]; /* Boot server enet address */
extern IPaddr_t NetOurIP; /* Our IP addr (0 = unknown) */
extern IPaddr_t NetServerIP; /* Server IP addr (0 = unknown) */
+extern IPaddr_t NetClientIP; /* Server IP addr (0 = unknown) */
extern volatile uchar * NetTxPacket; /* THE transmit packet */
extern volatile uchar * NetRxPackets[PKTBUFSRX];/* Receive packets */
extern volatile uchar * NetRxPacket; /* Current receive packet */--- Uboot3/net/net.c 2013-03-09 17:35:54.282849796 +0800
+++ 9UbootTftpServemini/net/net.c 2013-03-17 12:26:15.460618862 +0800
@@ -80,6 +80,7 @@
#include <net.h>
#include "bootp.h"
#include "tftp.h"
+#include "tftpserver.h"
#include "rarp.h"
#include "nfs.h"
#ifdef CONFIG_STATUS_LED
@@ -138,6 +139,7 @@
{ 0, 0, 0, 0, 0, 0 };
IPaddr_t NetOurIP; /* Our IP addr (0 = unknown) */
IPaddr_t NetServerIP; /* Server IP addr (0 = unknown) */
+IPaddr_t NetClientIP; /* Server IP addr (0 = unknown) */
volatile uchar *NetRxPacket; /* Current receive packet */
int NetRxPacketLen; /* Current rx packet length */
unsigned NetIPID; /* IP packet ID */
@@ -279,6 +281,7 @@
static void
NetInitLoop(proto_t protocol)
{
+ debug("NetInitLoop ... \n");
static int env_changed_id = 0;
bd_t *bd = gd->bd;
int env_id = get_env_id ();
@@ -389,6 +392,12 @@
TftpStart();
break;
+ case TFTPSERVER:
+ puts("net.c/TFTPSERVER...\n");
+ /* always use ARP to get server ethernet address */
+ TftpServerStart();
+ break;
+
#if defined(CONFIG_CMD_DHCP)
case DHCP:
BootpTry = 0;
@@ -1672,6 +1681,7 @@
/*
* IP header OK. Pass the packet to the current handler.
*/
+ NetClientIP = NetReadIP(&ip->ip_src);
(*packetHandler)((uchar *)ip +IP_HDR_SIZE,
ntohs(ip->udp_dst),
ntohs(ip->udp_src),
@@ -1715,6 +1725,11 @@
case NFS:
#endif
case NETCONS:
+ case TFTPSERVER:
+ if (NetOurIP == 0) {
+ puts ("*** ERROR: `ipaddr' not set\n");
+ return (1);
+ }
case TFTP:
if (NetServerIP == 0) {
puts ("*** ERROR: `serverip' not set\n");
三.实现tftpserver处理函数
--- 9UbootTftpServemini/net/tftp.c 2013-03-17 14:59:43.660439608 +0800
+++ 9UbootTftpServemini/net/tftpserver.c 2013-03-17 15:36:20.575274671 +0800
@@ -7,7 +7,7 @@
#include <common.h>
#include <command.h>
#include <net.h>
-#include "tftp.h"
+#include "tftpserver.h"
#include "bootp.h"
#if defined(CONFIG_CMD_NET)
@@ -44,8 +44,8 @@
* positive. The globals are meant to be set (and restored) by code needing
* non-standard timeout behavior when initiating a TFTP transfer.
*/
-ulong TftpRRQTimeoutMSecs = TIMEOUT;
-int TftpRRQTimeoutCountMax = TIMEOUT_COUNT;
+static ulong TftpRRQTimeoutMSecs = TIMEOUT;
+static TftpRRQTimeoutCountMax = TIMEOUT_COUNT;
static IPaddr_t TftpServerIP;
static int TftpServerPort; /* The UDP port at their end */
@@ -66,6 +66,8 @@
#define STATE_TOO_LARGE 3
#define STATE_BAD_MAGIC 4
#define STATE_OACK 5
+#define STATE_WAIT 6
+#define STATE_WRQ 7
#define TFTP_BLOCK_SIZE 512 /* default TFTP block size */
#define TFTP_SEQUENCE_SIZE ((ulong)(1<<16)) /* sequence number is 16 bit */
@@ -192,6 +194,15 @@
switch (TftpState) {
+ case STATE_WRQ:
+ xp = pkt;
+ s = (ushort *)pkt;
+ *s++ = htons(TFTP_ACK);
+ *s++ = htons(TftpBlock);
+ pkt = (uchar *)s;
+ len = pkt - xp;
+ break;
+
case STATE_RRQ:
xp = pkt;
s = (ushort *)pkt;
@@ -283,7 +294,7 @@
#endif
return;
}
- if (TftpState != STATE_RRQ && src != TftpServerPort) {
+ if (TftpState != STATE_WAIT && src != TftpServerPort) {
return;
}
@@ -299,6 +310,12 @@
case TFTP_RRQ:
case TFTP_WRQ:
+ NetServerIP = NetClientIP;
+ TftpBlock = 0;
+ TftpState = STATE_WRQ;
+ TftpServerPort = src;
+ TftpSend ();
+ break;
case TFTP_ACK:
break;
default:
@@ -492,15 +509,13 @@
#endif
NetStartAgain ();
} else {
- puts ("T ");
NetSetTimeout (TftpTimeoutMSecs, TftpTimeout);
- TftpSend ();
}
}
void
-TftpStart (void)
+TftpServerStart (void)
{
char *ep; /* Environment pointer */
@@ -572,9 +587,9 @@
TftpServerPort = WELL_KNOWN_PORT;
TftpTimeoutCount = 0;
- TftpState = STATE_RRQ;
+ TftpState = STATE_WAIT;
/* Use a pseudo-random port unless a specific port is set */
- TftpOurPort = 1024 + (get_timer(0) % 3072);
+ TftpOurPort = WELL_KNOWN_PORT;
#ifdef CONFIG_TFTP_PORT
if ((ep = getenv("tftpdstp")) != NULL) {
@@ -598,7 +613,6 @@
TftpNumchars = 0;
#endif
- TftpSend ();
}
#ifdef CONFIG_MCAST_TFTP
--- Uboot3/net/tftp.h 2013-03-09 17:35:54.282849796 +0800
+++ 9UbootTftpServemini/net/tftpserver.h 2013-03-16 16:53:09.109731467 +0800
@@ -1,12 +1,14 @@
/*
- * LiMon - BOOTP/TFTP.
+ * LiMon - BOOTP/TFTPSERVER.
+ *
+ * 2013 BY kangear
*
* Copyright 1994, 1995, 2000 Neil Russell.
* (See License)
*/
-#ifndef __TFTP_H__
-#define __TFTP_H__
+#ifndef __TFTPSERVER_H__
+#define __TFTPSERVER_H__
/**********************************************************************/
/*
@@ -14,8 +16,8 @@
*/
/* tftp.c */
-extern void TftpStart (void); /* Begin TFTP get */
+extern void TftpServerStart (void); /* Begin TFTPSERVER get */
/**********************************************************************/
-#endif /* __TFTP_H__ */
+#endif /* __TFTPSERVER_H__ */
--- Uboot3/net/Makefile2013-03-09 17:35:54.282849796 +0800
+++ 9UbootTftpServemini/net/Makefile 2013-03-16 17:11:20.817776725 +0800
@@ -35,6 +35,7 @@
COBJS-y += rarp.o
COBJS-$(CONFIG_CMD_SNTP) += sntp.o
COBJS-y += tftp.o
+COBJS-y += tftpserver.o
COBJS := $(COBJS-y)
SRCS := $(COBJS:.o=.c)
+++ 9UbootTftpServemini/net/tftpserver.c 2013-03-17 15:36:20.575274671 +0800
@@ -7,7 +7,7 @@
#include <common.h>
#include <command.h>
#include <net.h>
-#include "tftp.h"
+#include "tftpserver.h"
#include "bootp.h"
#if defined(CONFIG_CMD_NET)
@@ -44,8 +44,8 @@
* positive. The globals are meant to be set (and restored) by code needing
* non-standard timeout behavior when initiating a TFTP transfer.
*/
-ulong TftpRRQTimeoutMSecs = TIMEOUT;
-int TftpRRQTimeoutCountMax = TIMEOUT_COUNT;
+static ulong TftpRRQTimeoutMSecs = TIMEOUT;
+static TftpRRQTimeoutCountMax = TIMEOUT_COUNT;
static IPaddr_t TftpServerIP;
static int TftpServerPort; /* The UDP port at their end */
@@ -66,6 +66,8 @@
#define STATE_TOO_LARGE 3
#define STATE_BAD_MAGIC 4
#define STATE_OACK 5
+#define STATE_WAIT 6
+#define STATE_WRQ 7
#define TFTP_BLOCK_SIZE 512 /* default TFTP block size */
#define TFTP_SEQUENCE_SIZE ((ulong)(1<<16)) /* sequence number is 16 bit */
@@ -192,6 +194,15 @@
switch (TftpState) {
+ case STATE_WRQ:
+ xp = pkt;
+ s = (ushort *)pkt;
+ *s++ = htons(TFTP_ACK);
+ *s++ = htons(TftpBlock);
+ pkt = (uchar *)s;
+ len = pkt - xp;
+ break;
+
case STATE_RRQ:
xp = pkt;
s = (ushort *)pkt;
@@ -283,7 +294,7 @@
#endif
return;
}
- if (TftpState != STATE_RRQ && src != TftpServerPort) {
+ if (TftpState != STATE_WAIT && src != TftpServerPort) {
return;
}
@@ -299,6 +310,12 @@
case TFTP_RRQ:
case TFTP_WRQ:
+ NetServerIP = NetClientIP;
+ TftpBlock = 0;
+ TftpState = STATE_WRQ;
+ TftpServerPort = src;
+ TftpSend ();
+ break;
case TFTP_ACK:
break;
default:
@@ -492,15 +509,13 @@
#endif
NetStartAgain ();
} else {
- puts ("T ");
NetSetTimeout (TftpTimeoutMSecs, TftpTimeout);
- TftpSend ();
}
}
void
-TftpStart (void)
+TftpServerStart (void)
{
char *ep; /* Environment pointer */
@@ -572,9 +587,9 @@
TftpServerPort = WELL_KNOWN_PORT;
TftpTimeoutCount = 0;
- TftpState = STATE_RRQ;
+ TftpState = STATE_WAIT;
/* Use a pseudo-random port unless a specific port is set */
- TftpOurPort = 1024 + (get_timer(0) % 3072);
+ TftpOurPort = WELL_KNOWN_PORT;
#ifdef CONFIG_TFTP_PORT
if ((ep = getenv("tftpdstp")) != NULL) {
@@ -598,7 +613,6 @@
TftpNumchars = 0;
#endif
- TftpSend ();
}
#ifdef CONFIG_MCAST_TFTP
--- Uboot3/net/tftp.h 2013-03-09 17:35:54.282849796 +0800
+++ 9UbootTftpServemini/net/tftpserver.h 2013-03-16 16:53:09.109731467 +0800
@@ -1,12 +1,14 @@
/*
- * LiMon - BOOTP/TFTP.
+ * LiMon - BOOTP/TFTPSERVER.
+ *
+ * 2013 BY kangear
*
* Copyright 1994, 1995, 2000 Neil Russell.
* (See License)
*/
-#ifndef __TFTP_H__
-#define __TFTP_H__
+#ifndef __TFTPSERVER_H__
+#define __TFTPSERVER_H__
/**********************************************************************/
/*
@@ -14,8 +16,8 @@
*/
/* tftp.c */
-extern void TftpStart (void); /* Begin TFTP get */
+extern void TftpServerStart (void); /* Begin TFTPSERVER get */
/**********************************************************************/
-#endif /* __TFTP_H__ */
+#endif /* __TFTPSERVER_H__ */
--- Uboot3/net/Makefile2013-03-09 17:35:54.282849796 +0800
+++ 9UbootTftpServemini/net/Makefile 2013-03-16 17:11:20.817776725 +0800
@@ -35,6 +35,7 @@
COBJS-y += rarp.o
COBJS-$(CONFIG_CMD_SNTP) += sntp.o
COBJS-y += tftp.o
+COBJS-y += tftpserver.o
COBJS := $(COBJS-y)
SRCS := $(COBJS:.o=.c)
测试一下:
关于上图的打印信息仍然是tftpboot时候的打印信息。可以根据实际情况更改。启动一下看看:可以看到是可以启动的。至此tftp服务器就算是移植成功了。
- 在U-boot上搭建TFTP服务器
- Fedora14平台上U-boot 之TFTP服务器配置
- 基于U-boot上TFTP服务器更新系统
- 在ubuntuserver上搭建tftp服务器
- U-boot 之TFTP服务器配置
- U-boot 之TFTP服务器配置
- U-boot 之TFTP服务器配置
- 在Ubunut12.04上搭建TFTP和NFS服务器
- u-boot-2011.03在TQ2440上的移植(9)--TFTP下载菜单制作
- U-boot-200908在FL2440上的移植(四)--用nfs和tftp下载
- ubuntu11.10搭建tftp服务器以及在开发板上使用tftp
- ubuntu11.10搭建tftp服务器以及在开发板上使用tftp
- U-boot从tftp服务器启动,挂载到NFS根文件系统
- CentOS7上TFTP服务器简单搭建
- 在Ubuntu下tftp服务器搭建
- 在Ubuntu12.0.4下搭建TFTP服务器
- U-boot中TFTP 解释
- U-boot中TFTP 解释
- get_template_directory_uri() 模板目录
- Slave服务器中datanode启动后又自动关闭
- NYOJ - 士兵杀敌(一)
- STK AzEI蒙版工具的使用方法
- Imps --此题主要是体会下效率
- 在U-boot上搭建TFTP服务器
- Syscall系统调用Linux内核跟踪
- 字节序/CPU大小端
- contiki2.6之Makefile详细解读二
- Java笔记2
- 修改使用XCODE来管理项目的用户名和密码
- Data Guard RMAN-04006 和 ORA-01017 错误诊断
- 十进制转化为2进制
- 第二次程序报告(课堂作业)