3535#include <sys/socket.h>
3636#include <sys/time.h>
3737#include <sys/types.h>
38+ #include <sys/uio.h>
3839#include <unistd.h>
3940
4041#include "lwan.h"
@@ -596,10 +597,11 @@ lwan_request_set_response(lwan_request_t *request, lwan_response_t *response)
596597#define APPEND_CONSTANT (const_str_ ) \
597598 APPEND_STRING_LEN((const_str_), sizeof(const_str_) - 1)
598599
599- bool
600- lwan_response_header (lwan_t * l __attribute__((unused )), lwan_request_t * request , lwan_http_status_t status )
600+ ALWAYS_INLINE size_t
601+ lwan_prepare_response_header (lwan_t * l __attribute__((unused )), lwan_request_t * request , lwan_http_status_t status ,
602+ char headers [])
601603{
602- char headers [ 512 ], * p_headers ;
604+ char * p_headers ;
603605 char buffer [32 ];
604606 int32_t len ;
605607
@@ -620,12 +622,7 @@ lwan_response_header(lwan_t *l __attribute__((unused)), lwan_request_t *request,
620622 (request -> flags .is_keep_alive ? sizeof ("Keep-Alive" ) : sizeof ("Close" )) - 1 );
621623 APPEND_CONSTANT ("\r\n\r\n\0" );
622624
623- if (UNLIKELY (write (request -> fd , headers , strlen (headers )) < 0 )) {
624- perror ("write header" );
625- return false;
626- }
627-
628- return true;
625+ return p_headers - headers - 1 ;
629626}
630627
631628#undef APPEND_STRING_LEN
@@ -637,6 +634,8 @@ lwan_response_header(lwan_t *l __attribute__((unused)), lwan_request_t *request,
637634bool
638635lwan_response (lwan_t * l , lwan_request_t * request , lwan_http_status_t status )
639636{
637+ char headers [512 ];
638+
640639 if (UNLIKELY (!request -> response )) {
641640 lwan_default_response (l , request , status );
642641 return false;
@@ -654,16 +653,25 @@ lwan_response(lwan_t *l, lwan_request_t *request, lwan_http_status_t status)
654653 return false;
655654 }
656655
657- if (UNLIKELY (!lwan_response_header (l , request , status )))
658- return false;
656+ size_t header_len = lwan_prepare_response_header (l , request , status , headers );
657+ if (!header_len )
658+ return lwan_default_response (l , request , HTTP_INTERNAL_ERROR );
659659
660- if (request -> method == HTTP_HEAD )
660+ if (request -> method == HTTP_HEAD ) {
661+ if (write (request -> fd , headers , header_len ) < 0 ) {
662+ perror ("write" );
663+ return false;
664+ }
661665 return true;
666+ }
667+
668+ struct iovec response_vec [] = {
669+ { .iov_base = headers , .iov_len = header_len },
670+ { .iov_base = request -> response -> content , .iov_len = request -> response -> content_length }
671+ };
662672
663- if (UNLIKELY (write (request -> fd ,
664- request -> response -> content ,
665- request -> response -> content_length ) < 0 )) {
666- perror ("write response" );
673+ if (UNLIKELY (writev (request -> fd , response_vec , N_ELEMENTS (response_vec )) < 0 )) {
674+ perror ("writev" );
667675 return false;
668676 }
669677
0 commit comments