Sophie

Sophie

distrib > Arklinux > devel > i586 > media > main-src > by-pkgid > 864eeed5503c67aceac42157c52bf744 > files > 1

neon-0.29.6-1ark.src.rpm

--- neon-0.24.7/src/ne_request.c.ark	2004-12-27 14:11:20.000000000 +0100
+++ neon-0.24.7/src/ne_request.c	2004-12-27 14:26:37.000000000 +0100
@@ -110,6 +110,8 @@
 	    
     size_t body_size, body_progress;
 
+    int chunked;		/* Send request incrementally chunked */
+
     /* temporary store for response lines. */
     char respbuf[BUFSIZ];
 
@@ -445,6 +447,29 @@
     return ret;
 }
 
+int ne_send_request_chunk(ne_request *req, const char *buffer, size_t size)
+{
+    char chunksize[20];
+    int ret;
+
+    ne_snprintf(chunksize, sizeof chunksize, "%x%s", size, EOL);
+    chunksize[sizeof(chunksize)-1] = '\0';
+
+    ret = ne_sock_fullwrite(req->session->socket, chunksize, strlen(chunksize));
+
+    if (!ret && size > 0)
+        ret = ne_sock_fullwrite(req->session->socket, buffer, size);
+
+    if (!ret)
+        ret = ne_sock_fullwrite(req->session->socket, EOL, sizeof(EOL)-1);
+
+    /* XXX Final EOL on last 0 byte chunk? perhaps call ne_finish_request? */
+    if (!ret && size == 0)
+        ret = ne_sock_fullwrite(req->session->socket, EOL, sizeof(EOL)-1);
+
+    return ret;
+}
+
 /* Lob the User-Agent, connection and host headers in to the request
  * headers */
 static void add_fixed_headers(ne_request *req) 
@@ -583,6 +608,11 @@
     set_body_size(req, bodysize);
 }
 
+void ne_set_request_chunked(ne_request *req, int chunked)
+{
+    req->chunked = chunked;
+}
+
 int ne_set_request_body_fd(ne_request *req, int fd)
 {
     struct stat bodyst;
@@ -978,6 +1008,9 @@
 	int aret = aborted(req, _("Could not send request"), ret);
 	return RETRY_RET(retry, ret, aret);
     }
+
+    /* Return with request in progress if sending incrementally chunked body. */
+    if (req->chunked) return ret;
     
     if (!req->use_expect100 && req->body_size > 0) {
 	/* Send request body, if not using 100-continue. */
@@ -1154,6 +1187,50 @@
     }
 }
 
+int ne_finish_request(ne_request *req)
+{
+    struct body_reader *rdr;
+    const ne_status *const st = &req->status;
+
+    /* Determine whether server claims HTTP/1.1 compliance. */
+    req->session->is_http11 = (st->major_version == 1 &&
+                              st->minor_version > 0) || st->major_version > 1;
+
+    /* Persistent connections supported implicitly in HTTP/1.1 */
+    if (req->session->is_http11) req->can_persist = 1;
+
+    ne_set_error(req->session, "%d %s", st->code, st->reason_phrase);
+
+    /* Read the headers */
+    HTTP_ERR(read_response_headers(req));
+
+#ifdef NEON_SSL
+    /* Special case for CONNECT handling: the response has no body,
+     * and the connection can persist. */
+    if (req->session->in_connect && st->klass == 2) {
+        req->resp.mode = R_NO_BODY;
+	req->can_persist = 1;
+    }
+#endif
+
+    /* HEAD requests and 201, 204, 205, 304 responses have no response body,
+     * regardless of what headers are present. */
+    if (req->method_is_head || st->code == 201 || st->code == 204 || st->code == 205 || st->code == 304)
+        req->resp.mode = R_NO_BODY;
+
+    /* Prepare for reading the response entity-body.  Call each of the
+     * body readers and ask them whether they want to accept this
+     * response or not. */
+    for (rdr = req->body_readers; rdr != NULL; rdr=rdr->next) {
+        rdr->use = rdr->accept_response(rdr->userdata, req, st);
+    }
+
+    req->resp.left = req->resp.length;
+    req->resp.chunk_left = 0;
+
+    return NE_OK;
+}
+
 int ne_begin_request(ne_request *req)
 {
     struct body_reader *rdr;
@@ -1185,43 +1262,13 @@
     ne_buffer_destroy(data);
     if (ret != NE_OK) return ret;
 
-    /* Determine whether server claims HTTP/1.1 compliance. */
-    req->session->is_http11 = (st->major_version == 1 && 
-                               st->minor_version > 0) || st->major_version > 1;
-
-    /* Persistent connections supported implicitly in HTTP/1.1 */
-    if (req->session->is_http11) req->can_persist = 1;
-
-    ne_set_error(req->session, "%d %s", st->code, st->reason_phrase);
+    /* Return with request in progress if sending incrementally chunked body. */
+    if (req->chunked)
+	    return ret;	/* XXX perhaps NE_INPROGRESS? */
 
-    /* Read the headers */
-    HTTP_ERR(read_response_headers(req));
+    ret = ne_finish_request(req);
 
-#ifdef NEON_SSL
-    /* Special case for CONNECT handling: the response has no body,
-     * and the connection can persist. */
-    if (req->session->in_connect && st->klass == 2) {
-	req->resp.mode = R_NO_BODY;
-	req->can_persist = 1;
-    }
-#endif
-
-    /* HEAD requests and 204, 205, 304 responses have no response body,
-     * regardless of what headers are present. */
-    if (req->method_is_head || st->code==204 || st->code==205 || st->code==304)
-    	req->resp.mode = R_NO_BODY;
-
-    /* Prepare for reading the response entity-body.  Call each of the
-     * body readers and ask them whether they want to accept this
-     * response or not. */
-    for (rdr = req->body_readers; rdr != NULL; rdr=rdr->next) {
-	rdr->use = rdr->accept_response(rdr->userdata, req, st);
-    }
-    
-    req->resp.left = req->resp.length;
-    req->resp.chunk_left = 0;
-
-    return NE_OK;
+    return ret;
 }
 
 int ne_end_request(ne_request *req)
--- neon-0.24.7/src/ne_request.h.ark	2004-12-27 14:26:39.000000000 +0100
+++ neon-0.24.7/src/ne_request.h	2004-12-27 14:28:44.000000000 +0100
@@ -57,6 +57,18 @@
 void ne_set_request_body_buffer(ne_request *req, const char *buffer,
 				size_t size);
 
+/* Mark the request body as incrementally chunked. */
+void ne_set_request_chunked(ne_request *req, int chunked) /*@modifies req @*/;
+
+/* Send request body chunk.
+ * Return 0 on success, else NE_* return. */
+int ne_send_request_chunk(ne_request *req, const char *buffer, size_t size) /*@modifies req @*/;
+
+/* Finish incrementally chunked request. */
+int ne_finish_request(ne_request *req)
+	/*@globals internalState @*/
+	/*@modifies req, internalState @*/;
+
 /* Send the contents of a file as the request body; 'fd' must be a
  * file descriptor of an open, seekable file.  Current file offset of
  * fd is not retained (and ignored: the file is read from the the