qemu-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Qemu-devel] [PATCH 1/3] Add OACK support to slirp TFTP server


From: Anthony Liguori
Subject: [Qemu-devel] [PATCH 1/3] Add OACK support to slirp TFTP server
Date: Sat, 17 Feb 2007 19:01:36 -0600
User-agent: Thunderbird 1.5.0.9 (X11/20070103)

Specifically, this patch adds tsize handling which is needed for PXELinux.

Regards,

Anthony Liguori
diff -r 153828edbad3 slirp/tftp.c
--- a/slirp/tftp.c      Thu Feb 15 16:37:56 2007 -0600
+++ b/slirp/tftp.c      Thu Feb 15 21:37:26 2007 -0600
@@ -120,6 +120,45 @@ static int tftp_read_data(struct tftp_se
   return bytes_read;
 }
 
+static int tftp_send_oack(struct tftp_session *spt, 
+                          const char *key, uint32_t value,
+                          struct tftp_t *recv_tp)
+{
+    struct sockaddr_in saddr, daddr;
+    struct mbuf *m;
+    struct tftp_t *tp;
+    int n = 0;
+
+    m = m_get();
+
+    if (!m)
+       return -1;
+
+    memset(m->m_data, 0, m->m_size);
+
+    m->m_data += if_maxlinkhdr;
+    tp = (void *)m->m_data;
+    m->m_data += sizeof(struct udpiphdr);
+    
+    tp->tp_op = htons(TFTP_OACK);
+    n += sprintf(tp->x.tp_buf + n, "%s", key) + 1;
+    n += sprintf(tp->x.tp_buf + n, "%u", value) + 1;
+
+    saddr.sin_addr = recv_tp->ip.ip_dst;
+    saddr.sin_port = recv_tp->udp.uh_dport;
+    
+    daddr.sin_addr = spt->client_ip;
+    daddr.sin_port = spt->client_port;
+
+    m->m_len = sizeof(struct tftp_t) - 514 + n - 
+        sizeof(struct ip) - sizeof(struct udphdr);
+    udp_output2(NULL, m, &saddr, &daddr, IPTOS_LOWDELAY);
+
+    return 0;
+}
+
+
+
 static int tftp_send_error(struct tftp_session *spt, 
                           u_int16_t errorcode, const char *msg,
                           struct tftp_t *recv_tp)
@@ -273,6 +312,8 @@ static void tftp_handle_rrq(struct tftp_
       return;
   }
 
+  k += 6;/* skipping octet*/
+
   /* do sanity checks on the filename */
 
   if ((spt->filename[0] != '/')
@@ -297,6 +338,48 @@ static void tftp_handle_rrq(struct tftp_
       return;
   }
 
+  if (src[n - 1] != 0) {
+      tftp_send_error(spt, 2, "Access violation", tp);
+      return;
+  }
+
+  while (k < n) {
+      const char *key, *value;
+
+      key = src + k;
+      k += strlen(key) + 1;
+
+      if (k >= n) {
+         tftp_send_error(spt, 2, "Access violation", tp);
+         return;
+      }
+
+      value = src + k;
+      k += strlen(value) + 1;
+
+      if (strcmp(key, "tsize") == 0) {
+         int tsize = atoi(value);
+         struct stat stat_p;
+
+         if (tsize == 0 && tftp_prefix) {
+             char buffer[1024];
+             int len;
+
+             len = snprintf(buffer, sizeof(buffer), "%s/%s",
+                            tftp_prefix, spt->filename);
+
+             if (stat(buffer, &stat_p) == 0)
+                 tsize = stat_p.st_size;
+             else {
+                 tftp_send_error(spt, 1, "File not found", tp);
+                 return;
+             }
+         }
+
+         tftp_send_oack(spt, "tsize", tsize, tp);
+      }
+  }
+
   tftp_send_data(spt, 1, tp);
 }
 
diff -r 153828edbad3 slirp/tftp.h
--- a/slirp/tftp.h      Thu Feb 15 16:37:56 2007 -0600
+++ b/slirp/tftp.h      Thu Feb 15 16:37:57 2007 -0600
@@ -9,6 +9,7 @@
 #define TFTP_DATA   3
 #define TFTP_ACK    4
 #define TFTP_ERROR  5
+#define TFTP_OACK   6
 
 #define TFTP_FILENAME_MAX 512
 

reply via email to

[Prev in Thread] Current Thread [Next in Thread]