annotate toys/pending/tftpd.c @ 1126:2131db66a732 draft

tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
author Rob Landley <rob@landley.net>
date Wed, 20 Nov 2013 23:01:49 -0600
parents f7bec236efd3
children 6df194c6de88
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
1 /* tftpd.c - TFTP server.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
2 *
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
3 * Copyright 2013 Ranjan Kumar <ranjankumar.bth@gmail.com>
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
4 * Copyright 2013 Kyungwan Han <asura321@gmail.com>
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
5 *
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
6 * No Standard.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
7
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
8 USE_TFTPD(NEWTOY(tftpd, "rcu:l", TOYFLAG_BIN))
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
9
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
10 config TFTPD
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
11 bool "tftpd"
1112
f7bec236efd3 Stuff in pending should default n until cleaned up.
Rob Landley <rob@landley.net>
parents: 1111
diff changeset
12 default n
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
13 help
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
14 usage: tftpd [-cr] [-u USER] [DIR]
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
15
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
16 Transfer file from/to tftp server.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
17
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
18 -r Prohibit upload
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
19 -c Allow file creation via upload
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
20 -u Access files as USER
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
21 -l Log to syslog (inetd mode requires this)
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
22 */
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
23 #define FOR_tftpd
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
24 #include "toys.h"
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
25
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
26 GLOBALS(
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
27 char *user;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
28 long sfd;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
29 struct passwd *pw;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
30 )
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
31
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
32 #define TFTPD_BLKSIZE 512 // as per RFC 1350.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
33
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
34 // opcodes
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
35 #define TFTPD_OP_RRQ 1 // Read Request RFC 1350, RFC 2090
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
36 #define TFTPD_OP_WRQ 2 // Write Request RFC 1350
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
37 #define TFTPD_OP_DATA 3 // Data chunk RFC 1350
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
38 #define TFTPD_OP_ACK 4 // Acknowledgement RFC 1350
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
39 #define TFTPD_OP_ERR 5 // Error Message RFC 1350
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
40 #define TFTPD_OP_OACK 6 // Option acknowledgment RFC 2347
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
41
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
42 // Error Codes:
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
43 #define TFTPD_ER_NOSUCHFILE 1 // File not found
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
44 #define TFTPD_ER_ACCESS 2 // Access violation
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
45 #define TFTPD_ER_FULL 3 // Disk full or allocation exceeded
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
46 #define TFTPD_ER_ILLEGALOP 4 // Illegal TFTP operation
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
47 #define TFTPD_ER_UNKID 5 // Unknown transfer ID
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
48 #define TFTPD_ER_EXISTS 6 // File already exists
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
49 #define TFTPD_ER_UNKUSER 7 // No such user
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
50 #define TFTPD_ER_NEGOTIATE 8 // Terminate transfer due to option negotiation
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
51
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
52 /* TFTP Packet Formats
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
53 * Type Op # Format without header
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
54 * 2 bytes string 1 byte string 1 byte
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
55 * -----------------------------------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
56 * RRQ/ | 01/02 | Filename | 0 | Mode | 0 |
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
57 * WRQ -----------------------------------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
58 * 2 bytes 2 bytes n bytes
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
59 * ---------------------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
60 * DATA | 03 | Block # | Data |
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
61 * ---------------------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
62 * 2 bytes 2 bytes
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
63 * -------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
64 * ACK | 04 | Block # |
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
65 * --------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
66 * 2 bytes 2 bytes string 1 byte
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
67 * ----------------------------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
68 * ERROR | 05 | ErrorCode | ErrMsg | 0 |
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
69 * ----------------------------------------
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
70 */
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
71
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
72 static char *g_errpkt = toybuf + TFTPD_BLKSIZE;
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
73
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
74 // Create and send error packet.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
75 static void send_errpkt(struct sockaddr *dstaddr,
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
76 socklen_t socklen, char *errmsg)
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
77 {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
78 error_msg(errmsg);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
79 g_errpkt[1] = TFTPD_OP_ERR;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
80 strcpy(g_errpkt + 4, errmsg);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
81 if (sendto(TT.sfd, g_errpkt, strlen(errmsg)+5, 0, dstaddr, socklen) < 0)
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
82 perror_exit("sendto failed");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
83 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
84
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
85 // Used to send / receive packets.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
86 static void do_action(struct sockaddr *srcaddr, struct sockaddr *dstaddr,
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
87 socklen_t socklen, char *file, int opcode, int tsize, int blksize)
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
88 {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
89 int fd, done = 0, retry_count = 12, timeout = 100, len;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
90 uint16_t blockno = 1, pktopcode, rblockno;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
91 char *ptr, *spkt, *rpkt;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
92 struct pollfd pollfds[1];
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
93
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
94 spkt = xzalloc(blksize + 4);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
95 rpkt = xzalloc(blksize + 4);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
96 ptr = spkt+2; //point after opcode.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
97
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
98 pollfds[0].fd = TT.sfd;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
99 // initialize groups, setgid and setuid
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
100 if (TT.pw) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
101 if (change_identity(TT.pw)) perror_exit("Failed to change identity");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
102 endgrent();
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
103 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
104
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
105 if (opcode == TFTPD_OP_RRQ) fd = open(file, O_RDONLY, 0666);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
106 else fd = open(file, ((toys.optflags & FLAG_c) ?
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
107 (O_WRONLY|O_TRUNC|O_CREAT) : (O_WRONLY|O_TRUNC)) , 0666);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
108 if (fd < 0) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
109 g_errpkt[3] = TFTPD_ER_NOSUCHFILE;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
110 send_errpkt(dstaddr, socklen, "can't open file");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
111 goto CLEAN_APP;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
112 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
113 // For download -> blockno will be 1.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
114 // 1st ACK will be from dst,which will have blockno-=1
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
115 // Create and send ACK packet.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
116 if (blksize != TFTPD_BLKSIZE || tsize) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
117 pktopcode = TFTPD_OP_OACK;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
118 // add "blksize\000blksize_val\000" in send buffer.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
119 if (blksize != TFTPD_BLKSIZE) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
120 strcpy(ptr, "blksize");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
121 ptr += strlen("blksize") + 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
122 ptr += snprintf(ptr, 6, "%d", blksize) + 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
123 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
124 if (tsize) {// add "tsize\000tsize_val\000" in send buffer.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
125 struct stat sb;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
126
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
127 sb.st_size = 0;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
128 fstat(fd, &sb);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
129 strcpy(ptr, "tsize");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
130 ptr += strlen("tsize") + 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
131 ptr += sprintf(ptr, "%lu", (unsigned long)sb.st_size)+1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
132 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
133 goto SEND_PKT;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
134 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
135 // upload -> ACK 1st packet with filename, as it has blockno 0.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
136 if (opcode == TFTPD_OP_WRQ) blockno = 0;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
137
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
138 // Prepare DATA and/or ACK pkt and send it.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
139 for (;;) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
140 int poll_ret;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
141
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
142 retry_count = 12, timeout = 100, pktopcode = TFTPD_OP_ACK;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
143 ptr = spkt+2;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
144 *((uint16_t*)ptr) = htons(blockno);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
145 blockno++;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
146 ptr += 2;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
147 if (opcode == TFTPD_OP_RRQ) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
148 pktopcode = TFTPD_OP_DATA;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
149 len = readall(fd, ptr, blksize);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
150 if (len < 0) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
151 send_errpkt(dstaddr, socklen, "read-error");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
152 break;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
153 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
154 if (len != blksize) done = 1; //last pkt.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
155 ptr += len;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
156 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
157 SEND_PKT:
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
158 // 1st ACK will be from dst, which will have blockno-=1
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
159 *((uint16_t*)spkt) = htons(pktopcode); //append send pkt's opcode.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
160 RETRY_SEND:
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
161 if (sendto(TT.sfd, spkt, (ptr - spkt), 0, dstaddr, socklen) <0)
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
162 perror_exit("sendto failed");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
163 // if "block size < 512", send ACK and exit.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
164 if ((pktopcode == TFTPD_OP_ACK) && done) break;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
165
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
166 POLL_IN:
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
167 pollfds[0].events = POLLIN;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
168 pollfds[0].fd = TT.sfd;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
169 poll_ret = poll(pollfds, 1, timeout);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
170 if (poll_ret < 0 && (errno == EINTR || errno == ENOMEM)) goto POLL_IN;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
171 if (!poll_ret) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
172 if (!--retry_count) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
173 error_msg("timeout");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
174 break;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
175 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
176 timeout += 150;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
177 goto RETRY_SEND;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
178 } else if (poll_ret == 1) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
179 len = read(pollfds[0].fd, rpkt, blksize + 4);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
180 if (len < 0) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
181 send_errpkt(dstaddr, socklen, "read-error");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
182 break;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
183 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
184 if (len < 4) goto POLL_IN;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
185 } else {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
186 perror_msg("poll");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
187 break;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
188 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
189 // Validate receive packet.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
190 pktopcode = ntohs(((uint16_t*)rpkt)[0]);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
191 rblockno = ntohs(((uint16_t*)rpkt)[1]);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
192 if (pktopcode == TFTPD_OP_ERR) {
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
193 char *message = "DATA Check failure.";
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
194 char *arr[] = {"File not found", "Access violation",
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
195 "Disk full or allocation exceeded", "Illegal TFTP operation",
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
196 "Unknown transfer ID", "File already exists",
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
197 "No such user", "Terminate transfer due to option negotiation"};
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
198
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
199 if (rblockno && (rblockno < 9)) message = arr[rblockno - 1];
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
200 error_msg(message);
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
201 break; // Break the for loop.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
202 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
203
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
204 // if download requested by client,
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
205 // server will send data pkt and will receive ACK pkt from client.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
206 if ((opcode == TFTPD_OP_RRQ) && (pktopcode == TFTPD_OP_ACK)) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
207 if (rblockno == (uint16_t) (blockno - 1)) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
208 if (!done) continue; // Send next chunk of data.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
209 break;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
210 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
211 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
212
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
213 // server will receive DATA pkt and write the data.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
214 if ((opcode == TFTPD_OP_WRQ) && (pktopcode == TFTPD_OP_DATA)) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
215 if (rblockno == blockno) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
216 int nw = writeall(fd, &rpkt[4], len-4);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
217 if (nw != len-4) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
218 g_errpkt[3] = TFTPD_ER_FULL;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
219 send_errpkt(dstaddr, socklen, "write error");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
220 break;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
221 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
222
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
223 if (nw != blksize) done = 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
224 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
225 continue;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
226 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
227 goto POLL_IN;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
228 } // end of loop
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
229
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
230 CLEAN_APP:
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
231 if (CFG_TOYBOX_FREE) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
232 free(spkt);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
233 free(rpkt);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
234 close(fd);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
235 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
236 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
237
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
238 void tftpd_main(void)
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
239 {
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
240 int recvmsg_len, rbuflen, opcode, blksize = TFTPD_BLKSIZE, tsize = 0, set =1;
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
241 struct sockaddr_storage srcaddr, dstaddr;
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
242 socklen_t socklen = sizeof(struct sockaddr_storage);
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
243 char *buf = toybuf;
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
244
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
245 TT.pw = NULL;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
246 memset(&srcaddr, 0, sizeof(srcaddr));
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
247 if (getsockname(STDIN_FILENO, (struct sockaddr*)&srcaddr, &socklen)) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
248 toys.exithelp = 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
249 error_exit(NULL);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
250 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
251
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
252 if (toys.optflags & FLAG_u) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
253 struct passwd *pw = getpwnam(TT.user);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
254 if (!pw) error_exit("unknown user %s", TT.user);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
255 TT.pw = pw;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
256 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
257 if (*toys.optargs) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
258 if (chroot(*toys.optargs))
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
259 perror_exit("can't change root directory to '%s'", *toys.optargs);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
260 if (chdir("/")) perror_exit("can't change directory to '/'");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
261 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
262
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
263 recvmsg_len = recvfrom(STDIN_FILENO, toybuf, TFTPD_BLKSIZE, 0,
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
264 (struct sockaddr*)&dstaddr, &socklen);
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
265
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
266 TT.sfd = xsocket(((struct sockaddr*)&dstaddr)->sa_family, SOCK_DGRAM, 0);
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
267 if (setsockopt(TT.sfd, SOL_SOCKET, SO_REUSEADDR, (const void *)&set,
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
268 sizeof(set)) < 0) perror_exit("setsockopt failed");
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
269 if (bind(TT.sfd, (struct sockaddr*)&srcaddr, socklen)) perror_exit("bind");
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
270 if (connect(TT.sfd, (struct sockaddr*)&dstaddr, socklen) < 0)
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
271 perror_exit("can't connect to remote host");
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
272 // Error condition.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
273 if (recvmsg_len < 4 || recvmsg_len > TFTPD_BLKSIZE
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
274 || toybuf[recvmsg_len-1] != '\0') {
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
275 send_errpkt((struct sockaddr*)&dstaddr, socklen, "packet format error");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
276 return;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
277 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
278
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
279 // request is either upload or Download.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
280 opcode = ntohs(*(uint16_t*)buf);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
281 if (((opcode != TFTPD_OP_RRQ) && (opcode != TFTPD_OP_WRQ))
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
282 || ((opcode == TFTPD_OP_WRQ) && (toys.optflags & FLAG_r))) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
283 send_errpkt((struct sockaddr*)&dstaddr, socklen,
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
284 ((opcode == TFTPD_OP_WRQ) ? "write error" : "packet format error"));
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
285 return;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
286 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
287
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
288 buf += 2;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
289 if (*buf == '.' || strstr(buf, "/.")) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
290 send_errpkt((struct sockaddr*)&dstaddr, socklen, "dot in filename");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
291 return;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
292 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
293
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
294 buf += strlen(buf) + 1; //1 '\0'.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
295 // As per RFC 1350, mode is case in-sensitive.
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
296 if ((buf >= (toybuf + recvmsg_len)) || (strcasecmp(buf, "octet"))) {
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
297 send_errpkt((struct sockaddr*)&dstaddr, socklen, "packet format error");
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
298 return;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
299 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
300
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
301 //RFC2348. e.g. of size type: "ttype1\0ttype1_val\0...ttypeN\0ttypeN_val\0"
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
302 buf += strlen(buf) + 1;
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
303 rbuflen = toybuf + recvmsg_len - buf;
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
304 if (rbuflen) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
305 int jump = 0, bflag = 0;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
306
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
307 for (; rbuflen; rbuflen -= jump, buf += jump) {
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
308 if (!bflag && !strcasecmp(buf, "blksize")) { //get blksize
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
309 errno = 0;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
310 blksize = strtoul(buf, NULL, 10);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
311 if (errno || blksize > 65564 || blksize < 8) blksize = TFTPD_BLKSIZE;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
312 bflag ^= 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
313 } else if (!tsize && !strcasecmp(buf, "tsize")) tsize ^= 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
314
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
315 jump += strlen(buf) + 1;
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
316 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
317 tsize &= (opcode == TFTPD_OP_RRQ);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
318 }
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
319
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
320 //do send / receive file.
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
321 do_action((struct sockaddr*)&srcaddr, (struct sockaddr*)&dstaddr,
1126
2131db66a732 tftpd upgrade from Ashwini Sharma based on comments from Felix Janda.
Rob Landley <rob@landley.net>
parents: 1112
diff changeset
322 socklen, toybuf + 2, opcode, tsize, blksize);
1111
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
323 if (CFG_TOYBOX_FREE) close(STDIN_FILENO);
f665f065fe87 Add tftpd
Ashwini Sharma <ak.ashwini@gmail.com>
parents:
diff changeset
324 }