Index: xend_internal.c
===================================================================
RCS file: /data/cvs/libvirt/src/xend_internal.c,v
retrieving revision 1.39
diff -u -r1.39 xend_internal.c
--- xend_internal.c	29 Jun 2006 23:53:31 -0000	1.39
+++ xend_internal.c	30 Jun 2006 22:18:52 -0000
@@ -303,6 +303,42 @@
     return swrite(fd, string, strlen(string));
 }
 
+/**
+ * sreads:
+ * @fd:  the file descriptor
+ * @buffer: the I/O buffer
+ * @n_buffer: the size of the I/O buffer
+ *
+ * Internal routine to do a synchronous read of a line
+ *
+ * Returns the number of bytes read, or -1 in case of error
+ */
+static ssize_t
+sreads(int fd, char *buffer, size_t n_buffer)
+{
+    size_t offset;
+
+    if (n_buffer < 1)
+        return (-1);
+
+    for (offset = 0; offset < (n_buffer - 1); offset++) {
+        ssize_t ret;
+
+        ret = sread(fd, buffer + offset, 1);
+        if (ret == 0)
+            break;
+        else if (ret == -1)
+            return ret;
+
+        if (buffer[offset] == '\n') {
+            offset++;
+            break;
+        }
+    }
+    buffer[offset] = 0;
+
+    return offset;
+}
 
 static int
 istartswith(const char *haystack, const char *needle)
@@ -325,95 +361,31 @@
 xend_req(int fd, char *content, size_t n_content)
 {
     char buffer[4096];
-    int nbuf = -1;
     int content_length = -1;
     int retcode = 0;
 
-    /*
-     * Fill buffer with as much as possible to get 
-     * process going
-     */
-    nbuf = sread(fd, buffer, sizeof(buffer));
-
-    /*
-     * Extract lines from the buffer, until the 
-     * end of header is found
-     */
-    while (nbuf > -1) {
-        /* Seach for offset of first \r\n pair */
-        int i, offset = -1;
-
-        for (i = 0; i < (nbuf - 1); i++) {
-            if (buffer[i] == '\r' && buffer[i + 1] == '\n') {
-                offset = i;
-                break;
-            }
-        }
-
-        if (offset == -1) { /* No newline found, so try to fill more data */
-
-            if (nbuf == sizeof(buffer)) {
-                /* Already have 4096 bytes of data & no newline, 
-                 * get the hell out of this game */
-                break;
-            }
-
-            /* Fill remainder of buffer with more data */
-            int extra = sread(fd, buffer + nbuf, sizeof(buffer) - nbuf);
-
-            if (extra < 1) {
-                /* Couldn't get more, so quit trying */
-                break;
-            }
-            nbuf += extra;
-        } else if (!offset) { /* Immediate newline, indicates end of header */
-            /* Overwrite the \r\n pair */
-            offset += 2;
-            nbuf -= offset;
-            memmove(buffer, buffer + offset, nbuf);
+    while (sreads(fd, buffer, sizeof(buffer)) > 0) {
+        if (strcmp(buffer, "\r\n") == 0)
             break;
-        } else { /* We have a single line */
-            buffer[offset] = '\0';
 
-            if (istartswith(buffer, "Content-Length: "))
-                content_length = atoi(buffer + 16);
-            else if (istartswith(buffer, "HTTP/1.1 "))
-                retcode = atoi(buffer + 9);
-
-            /*
-	     * Now move buffer, overwriting first line, to make room for
-             * more data on next iteration of loop (if needed)
-	     */
-            offset += 2;
-            nbuf -= offset;
-            memmove(buffer, buffer + offset, nbuf);
-        }
+        if (istartswith(buffer, "Content-Length: "))
+            content_length = atoi(buffer + 16);
+        else if (istartswith(buffer, "HTTP/1.1 "))
+            retcode = atoi(buffer + 9);
     }
 
-    if (content_length > -1) {  /* Read the header, now get body */
+    if (content_length > -1) {
+        ssize_t ret;
+
         if ((unsigned int) content_length > (n_content + 1))
             content_length = n_content - 1;
 
-        /*
-	 * Copy across any data left in buffer after
-         * reading header
-	 */
-        if (nbuf > content_length) {
-            nbuf = content_length;
-        }
-        memmove(content, buffer, nbuf);
-
-        if (nbuf < content_length) { /* Still need more data for body */
-            size_t ret = sread(fd, content + nbuf, content_length - nbuf);
-
-            if (0 > (int) ret)
-                return -1;
+        ret = sread(fd, content, content_length);
+        if (ret < 0)
+            return -1;
 
-            content[nbuf + ret] = 0;
-        } else {
-            content[nbuf] = 0;
-        }
-    } else { /* Unable to complete reading header */
+        content[ret] = 0;
+    } else {
         content[0] = 0;
     }
 
