Just noticed that there is a little bit of silliness (as usual) in the
original patch. Nothing serious, but this one should make a bit more
sense...

Bojan
--- mod_log_config.c.original   Tue Aug 20 12:51:20 2002
+++ mod_log_config.c    Tue Aug 20 13:33:50 2002
@@ -151,6 +151,8 @@
  * %...m:  the request method
  * %...H:  the request protocol
  * %...q:  the query string prepended by "?", or empty if no query string
+ * %...I:  bytes received, including request and headers, cannot be zero
+ * %...O:  bytes sent, including headers, cannot be zero
  *
  * The '...' can be nothing at all (e.g. "%h %u %r %s %b"), or it can
  * indicate conditions for inclusion of the item (which will cause it
@@ -489,6 +491,63 @@
     return "-";
 }
 
+/*
+ * Header length function to work with ap_table_do()
+ *
+ * This and log_bytes_recv_all() and log_bytes_sent_all() is reworked from
+ * Simone Tellini's mod_accounting: http://sourceforge.net/projects/mod-acct/
+ *
+ */
+static int get_header_len(void *count, const char *key, const char *val) {
+
+    /* Header name, colon, space, header value, CRLF */
+    *((long *)count) += strlen(key) + strlen(val) + 4;
+            
+    return 1;
+}
+
+static const char *log_bytes_recv_all(request_rec *r, char *a)
+{
+    /* Request length, CRLF and another CRLF after headers */
+    long recv = strlen(r->the_request) + 4; /* Never zero */
+    const char *clen = ap_table_get(r->headers_in, "Content-Length" );
+    
+    /* Add length of headers */
+    ap_table_do(get_header_len, &recv, r->headers_in, NULL);
+
+    if (clen) /* We checked the value makes sense in http_protocol.c */
+        recv += atol(clen);
+
+    return ap_psprintf(r->pool, "%ld", recv);
+}
+
+static const char *log_bytes_sent_all(request_rec *r, char *a)
+{
+    long sent;
+
+    /* Headers that don't make it into headers tables
+     * "HTTP/x.x " + CRLF = 11 bytes
+     * "Server: "  + CRLF = 10 bytes
+     * "Date: "    + CRLF =  8 bytes
+     * CRLF after headers =  2 bytes --> Total = 31 bytes */
+    sent = strlen(r->status_line) + strlen(ap_get_server_version()) +
+           strlen(ap_gm_timestr_822(r->pool, r->request_time)) + 31;
+
+    /* Add regular and error headers */
+    ap_table_do(get_header_len, &sent, r->headers_out, NULL);
+    ap_table_do(get_header_len, &sent, r->err_headers_out, NULL);
+
+    /* Is the browser bug being avoided?
+     * If so, header "X-Pad: avoid browser bug" will be added and a CRLF
+     * 26 bytes in total */
+    if (sent >= 255 && sent <= 257)
+        sent += 26;
+
+    sent += r->bytes_sent;
+
+    return ap_psprintf(r->pool, "%ld", sent);
+}
+
 /*****************************************************************
  *
  * Parsing the log format string
@@ -576,6 +635,12 @@
         'c', log_connection_status, 0
     },
     {
+        'I', log_bytes_recv_all, 0
+    },
+    {
+        'O', log_bytes_sent_all, 0
+    },
+    {
         '\0'
     }
 };

Reply via email to