From 324470205860303edb6ea213fc8670b2b69a7f11 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Nils=20O=2E=20Sel=C3=A5sdal?= Date: Thu, 2 Jan 2014 14:04:43 +0100 Subject: utils: Greatly improve performance of osmo_hexdump routines In the osmo-bts and libosmo-abis code the hexdump routine is used for every incoming/outgoing packet (including voice frames) and the usage of snprintf showed up inside profiles. There is a semantic change when more than 4096 characters are used. The code will now truncate at byte boundaries (and not nibbles). Code: static const int lengths[] = { 23, 1000, 52 }; char buf[4096]; int i; for (i = 0; i < 30000; ++i) char *res = osmo_hexdump(buf, lengths[i & 3]); Results: before: after: real 0m3.233s real 0m0.085s user 0m3.212s user 0m0.084s sys 0m0.000s sys 0m0.000s --- src/utils.c | 18 +++++++++++++----- 1 file changed, 13 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/utils.c b/src/utils.c index 5874077c..cc339941 100644 --- a/src/utils.c +++ b/src/utils.c @@ -107,6 +107,7 @@ int osmo_hexparse(const char *str, uint8_t *b, int max_len) } static char hexd_buff[4096]; +static const char hex_chars[] = "0123456789abcdef"; static char *_osmo_hexdump(const unsigned char *buf, int len, char *delim) { @@ -115,13 +116,20 @@ static char *_osmo_hexdump(const unsigned char *buf, int len, char *delim) hexd_buff[0] = 0; for (i = 0; i < len; i++) { + const char *delimp = delim; int len_remain = sizeof(hexd_buff) - (cur - hexd_buff); - if (len_remain <= 0) + if (len_remain < 3) break; - int rc = snprintf(cur, len_remain, "%02x%s", buf[i], delim); - if (rc <= 0) - break; - cur += rc; + + *cur++ = hex_chars[buf[i] >> 4]; + *cur++ = hex_chars[buf[i] & 0xf]; + + while (len_remain > 1 && *delimp) { + *cur++ = *delimp++; + len_remain--; + } + + *cur = 0; } hexd_buff[sizeof(hexd_buff)-1] = 0; return hexd_buff; -- cgit v1.2.3