diff options
Diffstat (limited to 'src/net/tcp/httpcore.c')
| -rw-r--r-- | src/net/tcp/httpcore.c | 107 |
1 files changed, 60 insertions, 47 deletions
diff --git a/src/net/tcp/httpcore.c b/src/net/tcp/httpcore.c index fd94b5f08..9ad39656d 100644 --- a/src/net/tcp/httpcore.c +++ b/src/net/tcp/httpcore.c @@ -830,7 +830,9 @@ static int http_transfer_complete ( struct http_transaction *http ) { */ static int http_format_headers ( struct http_transaction *http, char *buf, size_t len ) { + struct parameters *params = http->uri->params; struct http_request_header *header; + struct parameter *param; size_t used; size_t remaining; char *line; @@ -844,7 +846,7 @@ static int http_format_headers ( struct http_transaction *http, char *buf, DBGC2 ( http, "HTTP %p TX %s\n", http, buf ); used += ssnprintf ( ( buf + used ), ( len - used ), "\r\n" ); - /* Construct all headers */ + /* Construct all fixed headers */ for_each_table_entry ( header, HTTP_REQUEST_HEADERS ) { /* Determine header value length */ @@ -869,6 +871,23 @@ static int http_format_headers ( struct http_transaction *http, char *buf, used += ssnprintf ( ( buf + used ), ( len - used ), "\r\n" ); } + /* Construct parameter headers, if any */ + if ( params ) { + + /* Construct all parameter headers */ + for_each_param ( param, params ) { + + /* Skip non-header parameters */ + if ( ! ( param->flags & PARAMETER_HEADER ) ) + continue; + + /* Add parameter */ + used += ssnprintf ( ( buf + used ), ( len - used ), + "%s: %s\r\n", param->key, + param->value ); + } + } + /* Construct terminating newline */ used += ssnprintf ( ( buf + used ), ( len - used ), "\r\n" ); @@ -1851,14 +1870,15 @@ static struct http_state http_trailers = { */ /** - * Construct HTTP parameter list + * Construct HTTP form parameter list * * @v params Parameter list * @v buf Buffer to contain HTTP POST parameters * @v len Length of buffer * @ret len Length of parameter list (excluding terminating NUL) */ -static size_t http_params ( struct parameters *params, char *buf, size_t len ) { +static size_t http_form_params ( struct parameters *params, char *buf, + size_t len ) { struct parameter *param; ssize_t remaining = len; size_t frag_len; @@ -1867,6 +1887,10 @@ static size_t http_params ( struct parameters *params, char *buf, size_t len ) { len = 0; for_each_param ( param, params ) { + /* Skip non-form parameters */ + if ( ! ( param->flags & PARAMETER_FORM ) ) + continue; + /* Add the "&", if applicable */ if ( len ) { if ( remaining > 0 ) @@ -1904,53 +1928,59 @@ static size_t http_params ( struct parameters *params, char *buf, size_t len ) { } /** - * Open HTTP transaction for simple GET URI - * - * @v xfer Data transfer interface - * @v uri Request URI - * @ret rc Return status code - */ -static int http_open_get_uri ( struct interface *xfer, struct uri *uri ) { - - return http_open ( xfer, &http_get, uri, NULL, NULL ); -} - -/** - * Open HTTP transaction for simple POST URI + * Open HTTP transaction for simple URI * * @v xfer Data transfer interface * @v uri Request URI * @ret rc Return status code */ -static int http_open_post_uri ( struct interface *xfer, struct uri *uri ) { +int http_open_uri ( struct interface *xfer, struct uri *uri ) { struct parameters *params = uri->params; struct http_request_content content; + struct http_method *method; + const char *type; void *data; size_t len; size_t check_len; int rc; - /* Calculate length of parameter list */ - len = http_params ( params, NULL, 0 ); + /* Calculate length of form parameter list, if any */ + len = ( params ? http_form_params ( params, NULL, 0 ) : 0 ); - /* Allocate temporary parameter list */ - data = zalloc ( len + 1 /* NUL */ ); - if ( ! data ) { - rc = -ENOMEM; - goto err_alloc; - } + /* Use POST if and only if there are form parameters */ + if ( len ) { - /* Construct temporary parameter list */ - check_len = http_params ( params, data, ( len + 1 /* NUL */ ) ); - assert ( check_len == len ); + /* Use POST */ + method = &http_post; + type = "application/x-www-form-urlencoded"; + + /* Allocate temporary form parameter list */ + data = zalloc ( len + 1 /* NUL */ ); + if ( ! data ) { + rc = -ENOMEM; + goto err_alloc; + } + + /* Construct temporary form parameter list */ + check_len = http_form_params ( params, data, + ( len + 1 /* NUL */ ) ); + assert ( check_len == len ); + + } else { + + /* Use GET */ + method = &http_get; + type = NULL; + data = NULL; + } /* Construct request content */ - content.type = "application/x-www-form-urlencoded"; + content.type = type; content.data = data; content.len = len; /* Open HTTP transaction */ - if ( ( rc = http_open ( xfer, &http_post, uri, NULL, &content ) ) != 0 ) + if ( ( rc = http_open ( xfer, method, uri, NULL, &content ) ) != 0 ) goto err_open; err_open: @@ -1959,23 +1989,6 @@ static int http_open_post_uri ( struct interface *xfer, struct uri *uri ) { return rc; } -/** - * Open HTTP transaction for simple URI - * - * @v xfer Data transfer interface - * @v uri Request URI - * @ret rc Return status code - */ -int http_open_uri ( struct interface *xfer, struct uri *uri ) { - - /* Open GET/POST URI as applicable */ - if ( uri->params ) { - return http_open_post_uri ( xfer, uri ); - } else { - return http_open_get_uri ( xfer, uri ); - } -} - /* Drag in HTTP extensions */ REQUIRING_SYMBOL ( http_open ); REQUIRE_OBJECT ( config_http ); |
