TFTP Get integration

git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@885 42af7a65-404d-4744-a932-0658087f49c3
This commit is contained in:
patacongo
2008-09-06 15:44:41 +00:00
parent 72e20b303a
commit a9bc69b83e
10 changed files with 83 additions and 84 deletions
+24 -20
View File
@@ -95,7 +95,7 @@ static inline ssize_t tftp_write(int fd, const ubyte *buf, size_t len)
if (nbyteswritten < 0)
{
ndbg(g_tftpcallfailed, "write", errno);
ndbg("write failed: %d\n", errno);
return ERROR;
}
@@ -152,7 +152,6 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
struct sockaddr_in from; /* The address the last UDP message recv'd from */
ubyte *packet; /* Allocated memory to hold one packet */
uint16 blockno = 0; /* The current transfer block number */
uint16 port = 0; /* This is the port number for the transfer */
uint16 opcode; /* Received opcode */
uint16 rblockno; /* Received block number */
int len; /* Generic length */
@@ -174,7 +173,7 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
packet = (ubyte*)zalloc(TFTP_IOBUFSIZE);
if (!packet)
{
ndbg(g_tftpnomemory, "packet");
ndbg("packet memory allocation failure\n");
errno = ENOMEM;
goto errout;
}
@@ -184,7 +183,7 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
fd = open(local, O_WRONLY|O_CREAT|O_TRUNC, 0666);
if (fd < 0)
{
ndbg(g_tftpcallfailed, "open", errno);
ndbg("open failed: %d\n", errno);
goto errout_with_packet;
}
@@ -196,7 +195,7 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
goto errout_with_fd;
}
/* Send the read request */
/* Send the read request using the well-known port number */
len = tftp_mkreqpacket(packet, TFTP_RRQ, remote, binary);
ret = tftp_sendto(sd, packet, len, &server);
@@ -205,6 +204,12 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
goto errout_with_sd;
}
/* Subsequent recvfrom will use any port number until the correct
* port for the data transfer is established.
*/
server.sin_port = 0;
/* Then enter the transfer loop. Loop until the entire file has
* been received or until an error occurs.
*/
@@ -233,28 +238,20 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
if (nbytesrecvd >= 0)
{
/* Replace the server port to the one in the response */
if (!port)
{
port = from.sin_port;
server.sin_port = port;
}
/* Verify the sender address and port number */
if (server.sin_addr.s_addr != from.sin_addr.s_addr)
{
nvdbg(g_tftpaddress, "recvfrom");
nvdbg("Invalid address in DATA\n");
retry--;
continue;
}
if (port != from.sin_port)
if (server.sin_port && server.sin_port != from.sin_port)
{
nvdbg(g_tftpport, "recvfrom");
nvdbg("Invalid port in DATA\n");
len = tftp_mkerrpacket(packet, TFTP_ERR_UNKID, TFTP_ERRST_UNKID);
ret = tftp_sendto(sd, packet, len, &server);
ret = tftp_sendto(sd, packet, len, &from);
retry--;
continue;
}
@@ -269,12 +266,19 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
if (opcode > TFTP_MAXRFC1350)
{
len = tftp_mkerrpacket(packet, TFTP_ERR_ILLEGALOP, TFTP_ERRST_ILLEGALOP);
ret = tftp_sendto(sd, packet, len, &server);
ret = tftp_sendto(sd, packet, len, &from);
}
continue;
}
/* Break out of the loop when we receive a good data packet */
/* Replace the server port to the one in the good data response */
if (!server.sin_port)
{
server.sin_port = from.sin_port;
}
/* Then break out of the loop */
break;
}
@@ -284,7 +288,7 @@ int tftpget(const char *remote, const char *local, in_addr_t addr, boolean binar
if (retry == TFTP_RETRIES)
{
nvdbg(g_tftptoomanyretries);
nvdbg("Retry limit exceeded\n");
goto errout_with_sd;
}
-9
View File
@@ -142,15 +142,6 @@
* Public Data
****************************************************************************/
#if defined(CONFIG_DEBUG) && defined(CONFIG_DEBUG_NET)
extern const char g_tftpcallfailed[];
extern const char g_tftpcalltimedout[];
extern const char g_tftpnomemory[];
extern const char g_tftptoomanyretries[];
extern const char g_tftpaddress[];
extern const char g_tftpport[];
#endif
/****************************************************************************
* Public Function Prototypes
****************************************************************************/
+23 -33
View File
@@ -60,7 +60,7 @@
#include "tftpc_internal.h"
#if defined(CONFIG_NET) && defined(CONFIG_NET_UDP)
#if defined(CONFIG_NET) && defined(CONFIG_NET_UDP) && CONFIG_NFILE_DESCRIPTORS > 0
/****************************************************************************
* Definitions
@@ -70,15 +70,6 @@
* Public Data
****************************************************************************/
#if defined(CONFIG_DEBUG) && defined(CONFIG_DEBUG_NET)
const char g_tftpcallfailed[] = "%s failed: %d\n";
const char g_tftpcalltimedout[] = "%s timed out\n";
const char g_tftpnomemory[] = "%s memory allocation failure\n";
const char g_tftptoomanyretries[] = "Retry limit exceeded\n";
const char g_tftpaddress[] = "%s invalid address\n";
const char g_tftpport[] = "%s invalid port\n";
#endif
/****************************************************************************
* Private Functions
****************************************************************************/
@@ -114,29 +105,28 @@ int tftp_sockinit(struct sockaddr_in *server, in_addr_t addr)
/* Create the UDP socket */
sd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (sd >= 0)
if (sd < 0)
{
ndbg(g_tftpcallfailed, "socket", errno);
ndbg("socket failed: %d\n", errno);
return ERROR;
}
else
/* Set the recvfrom timeout */
timeo.tv_sec = CONFIG_NETUTILS_TFTP_TIMEOUT / 10;
timeo.tv_usec = (CONFIG_NETUTILS_TFTP_TIMEOUT % 10) * 100000;
ret = setsockopt(sd, SOL_SOCKET, SO_RCVTIMEO, &timeo, sizeof(struct timeval));
if (ret < 0)
{
/* Set the recvfrom timeout */
timeo.tv_sec = CONFIG_NETUTILS_TFTP_TIMEOUT / 10;
timeo.tv_usec = (CONFIG_NETUTILS_TFTP_TIMEOUT % 10) * 100000;
ret = setsockopt(sd, SOL_SOCKET, SO_RCVTIMEO, &timeo, sizeof(struct timeval));
if (ret < 0)
{
ndbg(g_tftpcallfailed, "setsockopt", errno);
}
/* Initialize the server address structure */
memset(server, 0, sizeof(struct sockaddr_in));
server->sin_family = AF_INET;
server->sin_addr.s_addr = addr;
server->sin_port = HTONS(CONFIG_NETUTILS_TFTP_PORT);
ndbg("setsockopt failed: %d\n", errno);
}
/* Initialize the server address structure */
memset(server, 0, sizeof(struct sockaddr_in));
server->sin_family = AF_INET;
server->sin_addr.s_addr = addr;
server->sin_port = HTONS(CONFIG_NETUTILS_TFTP_PORT);
return sd;
}
@@ -265,7 +255,7 @@ ssize_t tftp_recvfrom(int sd, void *buf, size_t len, struct sockaddr_in *from)
if (errno == EAGAIN)
{
ndbg(g_tftpcalltimedout, "recvfrom");
ndbg("recvfrom timed out\n");
return ERROR;
}
@@ -273,7 +263,7 @@ ssize_t tftp_recvfrom(int sd, void *buf, size_t len, struct sockaddr_in *from)
else if (errno != EINTR)
{
ndbg(g_tftpcallfailed, "recvfrom", errno);
ndbg("recvfrom failed: %d\n", errno);
return ERROR;
}
}
@@ -317,7 +307,7 @@ ssize_t tftp_sendto(int sd, const void *buf, size_t len, struct sockaddr_in *to)
if (errno != EINTR)
{
ndbg(g_tftpcallfailed, "sendto", errno);
ndbg("sendto failed: %d\n", errno);
return ERROR;
}
}
@@ -331,4 +321,4 @@ ssize_t tftp_sendto(int sd, const void *buf, size_t len, struct sockaddr_in *to)
}
}
#endif /* CONFIG_NET && CONFIG_NET_UDP */
#endif /* CONFIG_NET && CONFIG_NET_UDP && CONFIG_NFILE_DESCRIPTORS */
+7 -7
View File
@@ -114,7 +114,7 @@ static inline ssize_t tftp_read(int fd, ubyte *buf, size_t buflen)
if (nbytesread < 0)
{
ndbg(g_tftpcallfailed, "read", errno);
ndbg("read failed: %d\n", errno);
return ERROR;
}
@@ -175,7 +175,7 @@ int tftp_mkdatapacket(int fd, off_t offset, ubyte *packet, uint16 blockno)
tmp = lseek(fd, offset, SEEK_SET);
if (tmp == (off_t)-1)
{
ndbg(g_tftpcallfailed, "lseek", errno);
ndbg("lseek failed: %d\n", errno);
return ERROR;
}
@@ -245,13 +245,13 @@ static int tftp_rcvack(int sd, ubyte *packet, struct sockaddr_in *server,
if (server->sin_addr.s_addr != from.sin_addr.s_addr)
{
nvdbg(g_tftpaddress, "recvfrom");
nvdbg("Invalid address in DATA\n");
continue;
}
if (*port != server->sin_port)
{
nvdbg(g_tftpport, "recvfrom");
nvdbg("Invalid port in DATA\n");
packetlen = tftp_mkerrpacket(packet, TFTP_ERR_UNKID, TFTP_ERRST_UNKID);
(void)tftp_sendto(sd, packet, packetlen, server);
continue;
@@ -348,7 +348,7 @@ int tftpput(const char *local, const char *remote, in_addr_t addr, boolean binar
packet = (ubyte*)zalloc(TFTP_IOBUFSIZE);
if (!packet)
{
ndbg(g_tftpnomemory, "packet");
ndbg("packet memory allocation failure\n");
errno = ENOMEM;
goto errout;
}
@@ -358,7 +358,7 @@ int tftpput(const char *local, const char *remote, in_addr_t addr, boolean binar
fd = open(local, O_RDONLY);
if (fd < 0)
{
ndbg(g_tftpcallfailed, "open", errno);
ndbg("open failed: %d\n", errno);
goto errout_with_packet;
}
@@ -370,7 +370,7 @@ int tftpput(const char *local, const char *remote, in_addr_t addr, boolean binar
goto errout_with_fd;
}
/* Send the write request */
/* Send the write request using the well known port */
packetlen = tftp_mkreqpacket(packet, TFTP_WRQ, remote, binary);
ret = tftp_sendto(sd, packet, packetlen, &server);