diff --git a/include/debug.h b/include/debug.h index e3c16db05c..c0da67667a 100644 --- a/include/debug.h +++ b/include/debug.h @@ -51,6 +51,7 @@ #endif #include +#include /**************************************************************************** * Pre-processor Definitions @@ -1022,6 +1023,11 @@ extern "C" void lib_dumpbuffer(FAR const char *msg, FAR const uint8_t *buffer, unsigned int buflen); +/* Do a pretty buffer dump from multiple buffers. */ + +void lib_dumpvbuffer(FAR const char *msg, FAR const struct iovec *iov, + int iovcnt); + /* The system logging interfaces are normally accessed via the macros * provided above. If the cross-compiler's C pre-processor supports a * variable number of macro arguments, then those macros below will map all diff --git a/libs/libc/misc/Make.defs b/libs/libc/misc/Make.defs index 0f34be1b0f..8c5e931286 100644 --- a/libs/libc/misc/Make.defs +++ b/libs/libc/misc/Make.defs @@ -63,7 +63,7 @@ endif # Add the miscellaneous C files to the build CSRCS += lib_crc64.c lib_crc32.c lib_crc16.c lib_crc8.c lib_crc8ccitt.c -CSRCS += lib_dumpbuffer.c lib_match.c lib_debug.c +CSRCS += lib_dumpbuffer.c lib_dumpvbuffer.c lib_match.c lib_debug.c # Keyboard driver encoder/decoder diff --git a/libs/libc/misc/lib_dumpbuffer.c b/libs/libc/misc/lib_dumpbuffer.c index aa67aa0b14..db1705fbb0 100644 --- a/libs/libc/misc/lib_dumpbuffer.c +++ b/libs/libc/misc/lib_dumpbuffer.c @@ -1,35 +1,20 @@ /**************************************************************************** * libs/libc/misc/lib_dumpbuffer.c * - * Copyright (C) 2009, 2011, 2014, 2016 Gregory Nutt. All rights reserved. - * Author: Gregory Nutt + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. The + * ASF licenses this file to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance with the + * License. You may obtain a copy of the License at * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: + * http://www.apache.org/licenses/LICENSE-2.0 * - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in - * the documentation and/or other materials provided with the - * distribution. - * 3. Neither the name NuttX nor the names of its contributors may be - * used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS - * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE - * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, - * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, - * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS - * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED - * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN - * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. * ****************************************************************************/ @@ -43,43 +28,6 @@ #include #include -/**************************************************************************** - * Pre-processor definitions - ****************************************************************************/ - -/* 32 bytes displayed per line */ -#define _NITEMS (16) - -/* 16 * (2 hex chars + 1 blank) + 1 space */ -#define _ASCIICHAR_OFFSET (_NITEMS * 3 + 1) - -/* _ASCIICHAR_OFFSET + 16 ASCII char, 1 NULL */ -#define _LINESIZE (_ASCIICHAR_OFFSET + _NITEMS + 1) - -/**************************************************************************** - * Private Functions - ****************************************************************************/ - -/**************************************************************************** - * Name: lib_nibble - * - * Description: - * Convert a binary nibble to a hexadecimal character. - * - ****************************************************************************/ - -static char lib_nibble(unsigned char nibble) -{ - if (nibble < 10) - { - return '0' + nibble; - } - else - { - return 'a' + nibble - 10; - } -} - /**************************************************************************** * Public Functions ****************************************************************************/ @@ -98,54 +46,11 @@ static char lib_nibble(unsigned char nibble) void lib_dumpbuffer(FAR const char *msg, FAR const uint8_t *buffer, unsigned int buflen) { - char buf[_LINESIZE]; - unsigned int i; - unsigned int j; - unsigned int k; - - if (msg) + struct iovec buf = { - syslog(LOG_INFO, "%s (%p):\n", msg, buffer); - } + .iov_base = (FAR char *)buffer, + .iov_len = buflen, + }; - for (i = 0; i < buflen; i += _NITEMS) - { - FAR char *ptr = buf; - - /* Generate hex values: 2 * _NITEMS + 1 bytes */ - - for (j = 0; j < _NITEMS; j++) - { - k = i + j; - - if (k < buflen) - { - *ptr++ = lib_nibble((buffer[k] >> 4) & 0xf); - *ptr++ = lib_nibble(buffer[k] & 0xf); - - /* Generate printable characters */ - - if (buffer[k] >= 0x20 && buffer[k] < 0x7f) - { - buf[_ASCIICHAR_OFFSET + j] = buffer[k]; - } - else - { - buf[_ASCIICHAR_OFFSET + j] = '.'; - } - } - else - { - *ptr++ = ' '; - *ptr++ = ' '; - buf[_ASCIICHAR_OFFSET + j] = '\0'; - } - - *ptr++ = ' '; - } - - buf[_ASCIICHAR_OFFSET - 1] = ' '; /* Plus 1 byte */ - buf[_ASCIICHAR_OFFSET + _NITEMS] = '\0'; - syslog(LOG_INFO, "%04x %s\n", i, buf); - } + lib_dumpvbuffer(msg, &buf, 1); } diff --git a/libs/libc/misc/lib_dumpvbuffer.c b/libs/libc/misc/lib_dumpvbuffer.c new file mode 100644 index 0000000000..1a32ff7ab6 --- /dev/null +++ b/libs/libc/misc/lib_dumpvbuffer.c @@ -0,0 +1,142 @@ +/**************************************************************************** + * libs/libc/misc/lib_dumpvbuffer.c + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. The + * ASF licenses this file to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance with the + * License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + * + ****************************************************************************/ + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include +#include + +#include +#include +#include + +/**************************************************************************** + * Pre-processor definitions + ****************************************************************************/ + +/* 32 bytes displayed per line */ +#define _NITEMS (16) + +/* 16 * (2 hex chars + 1 blank) + 1 space */ +#define _ASCIICHAR_OFFSET (_NITEMS * 3 + 1) + +/* _ASCIICHAR_OFFSET + 16 ASCII char, 1 NULL */ +#define _LINESIZE (_ASCIICHAR_OFFSET + _NITEMS + 1) + +/**************************************************************************** + * Private Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: lib_nibble + * + * Description: + * Convert a binary nibble to a hexadecimal character. + * + ****************************************************************************/ + +static char lib_nibble(unsigned char nibble) +{ + if (nibble < 10) + { + return '0' + nibble; + } + else + { + return 'a' + nibble - 10; + } +} + +/**************************************************************************** + * Public Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: lib_dumpvbuffer + * + * Description: + * Do a pretty buffer dump from multiple buffers. + * + * A fairly large on-stack buffer is used for the case where timestamps are + * applied to each line. + * + ****************************************************************************/ + +void lib_dumpvbuffer(FAR const char *msg, FAR const struct iovec *iov, + int iovcnt) +{ + FAR const struct iovec *piov = iov; + FAR const uint8_t *iov_buf; + unsigned int len = 0; + char line[_LINESIZE]; + unsigned int nitems; + unsigned int i = 0; + FAR char *ptr; + + if (msg) + { + syslog(LOG_INFO, "%s (%p):\n", msg, iov->iov_base); + } + + /* Initialize the separator and terminator */ + + line[_ASCIICHAR_OFFSET - 1] = ' '; + line[_LINESIZE - 1] = '\0'; + + while (piov != &iov[iovcnt] && piov->iov_len) + { + iov_buf = piov->iov_base; + ptr = line; + + for (nitems = 0; nitems < _NITEMS; nitems++) + { + *ptr++ = lib_nibble((iov_buf[len] >> 4) & 0xf); + *ptr++ = lib_nibble(iov_buf[len] & 0xf); + *ptr++ = ' '; + + /* Generate printable characters */ + + if (iov_buf[len] >= 0x20 && iov_buf[len] < 0x7f) + { + line[_ASCIICHAR_OFFSET + nitems] = iov_buf[len]; + } + else + { + line[_ASCIICHAR_OFFSET + nitems] = '.'; + } + + if (++len == piov->iov_len) + { + len = 0; + if (++piov == &iov[iovcnt]) + { + memset(ptr, ' ', (_NITEMS - nitems) * 3); + memset(&line[_ASCIICHAR_OFFSET + nitems], ' ', + _NITEMS - nitems); + break; + } + } + } + + syslog(LOG_INFO, "%04x %s\n", i++ * _NITEMS, line); + } +}