changeset 7736:a46fcf101cfc

Core: added format specifiers to output binary data as hex. Now "s", "V", and "v" format specifiers may be prefixed with "x" (lowercase) or "X" (uppercase) to output corresponding data in hexadecimal format. In collaboration with Maxim Dounin.
author Vladimir Homutov <vl@nginx.com>
date Wed, 28 Oct 2020 10:56:11 +0300
parents 908f48bd3c2f
children ed17a2a95c8d
files src/core/ngx_string.c src/event/ngx_event_openssl.c src/event/ngx_event_openssl_stapling.c src/http/modules/ngx_http_grpc_module.c
diffstat 4 files changed, 86 insertions(+), 67 deletions(-) [+]
line wrap: on
line diff
--- a/src/core/ngx_string.c
+++ b/src/core/ngx_string.c
@@ -11,6 +11,8 @@
 
 static u_char *ngx_sprintf_num(u_char *buf, u_char *last, uint64_t ui64,
     u_char zero, ngx_uint_t hexadecimal, ngx_uint_t width);
+static u_char *ngx_sprintf_str(u_char *buf, u_char *last, u_char *src,
+    size_t len, ngx_uint_t hexadecimal);
 static void ngx_encode_base64_internal(ngx_str_t *dst, ngx_str_t *src,
     const u_char *basis, ngx_uint_t padding);
 static ngx_int_t ngx_decode_base64_internal(ngx_str_t *dst, ngx_str_t *src,
@@ -101,10 +103,10 @@ ngx_pstrdup(ngx_pool_t *pool, ngx_str_t 
  *    %M                        ngx_msec_t
  *    %r                        rlim_t
  *    %p                        void *
- *    %V                        ngx_str_t *
- *    %v                        ngx_variable_value_t *
- *    %s                        null-terminated string
- *    %*s                       length and string
+ *    %[x|X]V                   ngx_str_t *
+ *    %[x|X]v                   ngx_variable_value_t *
+ *    %[x|X]s                   null-terminated string
+ *    %*[x|X]s                  length and string
  *    %Z                        '\0'
  *    %N                        '\n'
  *    %c                        char
@@ -165,7 +167,7 @@ ngx_vslprintf(u_char *buf, u_char *last,
     u_char                *p, zero;
     int                    d;
     double                 f;
-    size_t                 len, slen;
+    size_t                 slen;
     int64_t                i64;
     uint64_t               ui64, frac;
     ngx_msec_t             ms;
@@ -250,8 +252,7 @@ ngx_vslprintf(u_char *buf, u_char *last,
             case 'V':
                 v = va_arg(args, ngx_str_t *);
 
-                len = ngx_min(((size_t) (last - buf)), v->len);
-                buf = ngx_cpymem(buf, v->data, len);
+                buf = ngx_sprintf_str(buf, last, v->data, v->len, hex);
                 fmt++;
 
                 continue;
@@ -259,8 +260,7 @@ ngx_vslprintf(u_char *buf, u_char *last,
             case 'v':
                 vv = va_arg(args, ngx_variable_value_t *);
 
-                len = ngx_min(((size_t) (last - buf)), vv->len);
-                buf = ngx_cpymem(buf, vv->data, len);
+                buf = ngx_sprintf_str(buf, last, vv->data, vv->len, hex);
                 fmt++;
 
                 continue;
@@ -268,16 +268,7 @@ ngx_vslprintf(u_char *buf, u_char *last,
             case 's':
                 p = va_arg(args, u_char *);
 
-                if (slen == (size_t) -1) {
-                    while (*p && buf < last) {
-                        *buf++ = *p++;
-                    }
-
-                } else {
-                    len = ngx_min(((size_t) (last - buf)), slen);
-                    buf = ngx_cpymem(buf, p, len);
-                }
-
+                buf = ngx_sprintf_str(buf, last, p, slen, hex);
                 fmt++;
 
                 continue;
@@ -576,6 +567,64 @@ ngx_sprintf_num(u_char *buf, u_char *las
 }
 
 
+static u_char *
+ngx_sprintf_str(u_char *buf, u_char *last, u_char *src, size_t len,
+    ngx_uint_t hexadecimal)
+{
+    static u_char   hex[] = "0123456789abcdef";
+    static u_char   HEX[] = "0123456789ABCDEF";
+
+    if (hexadecimal == 0) {
+
+        if (len == (size_t) -1) {
+            while (*src && buf < last) {
+                *buf++ = *src++;
+            }
+
+        } else {
+            len = ngx_min((size_t) (last - buf), len);
+            buf = ngx_cpymem(buf, src, len);
+        }
+
+    } else if (hexadecimal == 1) {
+
+        if (len == (size_t) -1) {
+
+            while (*src && buf < last - 1) {
+                *buf++ = hex[*src >> 4];
+                *buf++ = hex[*src++ & 0xf];
+            }
+
+        } else {
+
+            while (len-- && buf < last - 1) {
+                *buf++ = hex[*src >> 4];
+                *buf++ = hex[*src++ & 0xf];
+            }
+        }
+
+    } else { /* hexadecimal == 2 */
+
+        if (len == (size_t) -1) {
+
+            while (*src && buf < last - 1) {
+                *buf++ = HEX[*src >> 4];
+                *buf++ = HEX[*src++ & 0xf];
+            }
+
+        } else {
+
+            while (len-- && buf < last - 1) {
+                *buf++ = HEX[*src >> 4];
+                *buf++ = HEX[*src++ & 0xf];
+            }
+        }
+    }
+
+    return buf;
+}
+
+
 /*
  * We use ngx_strcasecmp()/ngx_strncasecmp() for 7-bit ASCII strings only,
  * and implement our own ngx_strcasecmp()/ngx_strncasecmp()
--- a/src/event/ngx_event_openssl.c
+++ b/src/event/ngx_event_openssl.c
@@ -4057,9 +4057,6 @@ ngx_ssl_session_ticket_key_callback(ngx_
     ngx_ssl_session_ticket_key_t  *key;
     const EVP_MD                  *digest;
     const EVP_CIPHER              *cipher;
-#if (NGX_DEBUG)
-    u_char                         buf[32];
-#endif
 
     c = ngx_ssl_get_connection(ssl_conn);
     ssl_ctx = c->ssl->session_ctx;
@@ -4081,8 +4078,8 @@ ngx_ssl_session_ticket_key_callback(ngx_
         /* encrypt session ticket */
 
         ngx_log_debug3(NGX_LOG_DEBUG_EVENT, c->log, 0,
-                       "ssl session ticket encrypt, key: \"%*s\" (%s session)",
-                       ngx_hex_dump(buf, key[0].name, 16) - buf, buf,
+                       "ssl session ticket encrypt, key: \"%*xs\" (%s session)",
+                       (size_t) 16, key[0].name,
                        SSL_session_reused(ssl_conn) ? "reused" : "new");
 
         if (key[0].size == 48) {
@@ -4128,17 +4125,16 @@ ngx_ssl_session_ticket_key_callback(ngx_
         }
 
         ngx_log_debug2(NGX_LOG_DEBUG_EVENT, c->log, 0,
-                       "ssl session ticket decrypt, key: \"%*s\" not found",
-                       ngx_hex_dump(buf, name, 16) - buf, buf);
+                       "ssl session ticket decrypt, key: \"%*xs\" not found",
+                       (size_t) 16, name);
 
         return 0;
 
     found:
 
         ngx_log_debug3(NGX_LOG_DEBUG_EVENT, c->log, 0,
-                       "ssl session ticket decrypt, key: \"%*s\"%s",
-                       ngx_hex_dump(buf, key[i].name, 16) - buf, buf,
-                       (i == 0) ? " (default)" : "");
+                       "ssl session ticket decrypt, key: \"%*xs\"%s",
+                       (size_t) 16, key[i].name, (i == 0) ? " (default)" : "");
 
         if (key[i].size == 48) {
             cipher = EVP_aes_128_cbc();
--- a/src/event/ngx_event_openssl_stapling.c
+++ b/src/event/ngx_event_openssl_stapling.c
@@ -2662,16 +2662,8 @@ ngx_ssl_ocsp_create_key(ngx_ssl_ocsp_ctx
     p = ngx_cpymem(p, serial->data, serial->length);
     ngx_memzero(p, 20 - serial->length);
 
-#if (NGX_DEBUG)
-    {
-        u_char  buf[120];
-
-        ngx_hex_dump(buf, ctx->key.data, ctx->key.len);
-
-        ngx_log_debug2(NGX_LOG_DEBUG_EVENT, ctx->log, 0,
-                       "ssl ocsp key %*s", sizeof(buf), buf);
-    }
-#endif
+    ngx_log_debug1(NGX_LOG_DEBUG_EVENT, ctx->log, 0,
+                   "ssl ocsp key %xV", &ctx->key);
 
     return NGX_OK;
 }
--- a/src/http/modules/ngx_http_grpc_module.c
+++ b/src/http/modules/ngx_http_grpc_module.c
@@ -1141,20 +1141,11 @@ ngx_http_grpc_create_request(ngx_http_re
 
     f->flags |= NGX_HTTP_V2_END_HEADERS_FLAG;
 
-#if (NGX_DEBUG)
-    if (r->connection->log->log_level & NGX_LOG_DEBUG_HTTP) {
-        u_char  buf[512];
-        size_t  n, m;
-
-        n = ngx_min(b->last - b->pos, 256);
-        m = ngx_hex_dump(buf, b->pos, n) - buf;
-
-        ngx_log_debug4(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
-                       "grpc header: %*s%s, len: %uz",
-                       m, buf, b->last - b->pos > 256 ? "..." : "",
-                       b->last - b->pos);
-    }
-#endif
+    ngx_log_debug4(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
+                   "grpc header: %*xs%s, len: %uz",
+                   (size_t) ngx_min(b->last - b->pos, 256), b->pos,
+                   b->last - b->pos > 256 ? "..." : "",
+                   b->last - b->pos);
 
     if (r->request_body_no_buffering) {
 
@@ -1604,20 +1595,11 @@ ngx_http_grpc_process_header(ngx_http_re
     u = r->upstream;
     b = &u->buffer;
 
-#if (NGX_DEBUG)
-    if (r->connection->log->log_level & NGX_LOG_DEBUG_HTTP) {
-        u_char  buf[512];
-        size_t  n, m;
-
-        n = ngx_min(b->last - b->pos, 256);
-        m = ngx_hex_dump(buf, b->pos, n) - buf;
-
-        ngx_log_debug4(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
-                       "grpc response: %*s%s, len: %uz",
-                       m, buf, b->last - b->pos > 256 ? "..." : "",
-                       b->last - b->pos);
-    }
-#endif
+    ngx_log_debug4(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
+                   "grpc response: %*xs%s, len: %uz",
+                   (size_t) ngx_min(b->last - b->pos, 256),
+                   b->pos, b->last - b->pos > 256 ? "..." : "",
+                   b->last - b->pos);
 
     ctx = ngx_http_grpc_get_ctx(r);