Add a common MAC address printing routine

* print_mac.c: New file.
* Makefile.am (strace_SOURCES): Add it.
* defs.h (sprint_mac_addr): New declaration.
(print_mac_addr): New function, a thin wrapper around sprint_mac_addr.
* print_fields.h (PRINT_FIELD_MAC, PRINT_FIELD_MAC_SZ): New macros.
* rtnl_link.c (decode_ifla_bridge_id): Use PRINT_FIELD_MAC for bridge
address printing.
* sock.c (print_ifreq) <case SIOCGIFHWADDR>: Use print_mac_addr for
ifr_hwaddr printing.
* sockaddr.c (print_sockaddr_data_bt): Use print_mac_addr for
{sco,rc,l2}_bdaddr field printing.

Co-Authored-by: Dmitry V. Levin <ldv@altlinux.org>
This commit is contained in:
Eugene Syromyatnikov 2018-05-07 00:04:18 +02:00 committed by Dmitry V. Levin
parent 2d82c2c50a
commit dc7901f5c3
7 changed files with 91 additions and 23 deletions

View File

@ -242,6 +242,7 @@ strace_SOURCES = \
print_group_req.c \
print_fields.h \
print_ifindex.c \
print_mac.c \
print_mq_attr.c \
print_msgbuf.c \
print_sg_req_info.c \

10
defs.h
View File

@ -687,6 +687,9 @@ extern const char *sprintflags_ex(const char *prefix, const struct xlat *xlat,
extern const char *sprinttime(long long sec);
extern const char *sprinttime_nsec(long long sec, unsigned long long nsec);
extern const char *sprinttime_usec(long long sec, unsigned long long usec);
extern const char *sprint_mac_addr(const uint8_t addr[], size_t size);
extern void print_symbolic_mode_t(unsigned int);
extern void print_numeric_umode_t(unsigned short);
extern void print_numeric_long_umask(unsigned long);
@ -969,6 +972,13 @@ extern void tprints(const char *str);
extern void tprintf_comment(const char *fmt, ...) ATTRIBUTE_FORMAT((printf, 1, 2));
extern void tprints_comment(const char *str);
static inline void
print_mac_addr(const char *prefix, const uint8_t addr[], size_t size)
{
tprints(prefix);
tprints(sprint_mac_addr(addr, size));
}
#if SUPPORTED_PERSONALITIES > 1
extern void set_personality(unsigned int personality);
extern unsigned current_personality;

View File

@ -220,4 +220,17 @@
printpath((tcp_), (where_).field_); \
} while (0)
#define PRINT_FIELD_MAC(prefix_, where_, field_) \
PRINT_FIELD_MAC_SZ((prefix_), (where_), field_, \
ARRAY_SIZE((where_).field_))
#define PRINT_FIELD_MAC_SZ(prefix_, where_, field_, size_) \
do { \
static_assert(sizeof(((where_).field_)[0]) == 1, \
"MAC address is not a byte array"); \
STRACE_PRINTF("%s%s=", (prefix_), #field_); \
print_mac_addr("", (const uint8_t *) ((where_).field_), \
(size_)); \
} while (0)
#endif /* !STRACE_PRINT_FIELDS_H */

55
print_mac.c Normal file
View File

@ -0,0 +1,55 @@
/*
* Copyright (c) 2018 The strace developers.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 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. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``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 AUTHOR 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.
*/
#include "defs.h"
#include "error_prints.h"
#include "xstring.h"
#ifndef MAX_ADDR_LEN
# define MAX_ADDR_LEN 32
#endif
const char *
sprint_mac_addr(const uint8_t addr[], size_t size)
{
static char res[MAX_ADDR_LEN * 3];
if (size > MAX_ADDR_LEN) {
error_func_msg("Address size (%zu) is more than maximum "
"supported (%u)", size, MAX_ADDR_LEN);
return NULL;
}
char *ptr = res;
for (size_t i = 0; i < size; i++)
ptr = xappendstr(res, ptr, "%s%02x", i ? ":" : "", addr[i]);
return res;
}

View File

@ -113,10 +113,9 @@ decode_ifla_bridge_id(struct tcb *const tcp,
if (len < sizeof(id))
return false;
else if (!umove_or_printaddr(tcp, addr, &id)) {
tprintf("{prio=[%u, %u], addr=%02x:%02x:%02x:%02x:%02x:%02x}",
id.prio[0], id.prio[1],
id.addr[0], id.addr[1], id.addr[2],
id.addr[3], id.addr[4], id.addr[5]);
tprintf("{prio=[%u, %u]", id.prio[0], id.prio[1]);
PRINT_FIELD_MAC(", ", id, addr);
tprints("}");
}
return true;

7
sock.c
View File

@ -78,11 +78,8 @@ print_ifreq(struct tcb *const tcp, const unsigned int code,
case SIOCGIFHWADDR: {
/* XXX Are there other hardware addresses
than 6-byte MACs? */
const unsigned char *bytes =
(unsigned char *) &ifr->ifr_hwaddr.sa_data;
tprintf("ifr_hwaddr=%02x:%02x:%02x:%02x:%02x:%02x",
bytes[0], bytes[1], bytes[2],
bytes[3], bytes[4], bytes[5]);
print_mac_addr("ifr_hwaddr=",
(const uint8_t *) &ifr->ifr_hwaddr.sa_data, 6);
break;
}
case SIOCSIFFLAGS:

View File

@ -384,29 +384,22 @@ print_sockaddr_data_bt(const void *const buf, const int addrlen)
}
case sizeof(struct sockaddr_sco): {
const struct sockaddr_sco *const sco = buf;
tprintf("sco_bdaddr=%02x:%02x:%02x:%02x:%02x:%02x",
sco->sco_bdaddr.b[0], sco->sco_bdaddr.b[1],
sco->sco_bdaddr.b[2], sco->sco_bdaddr.b[3],
sco->sco_bdaddr.b[4], sco->sco_bdaddr.b[5]);
print_mac_addr("sco_bdaddr=", sco->sco_bdaddr.b,
sizeof(sco->sco_bdaddr.b));
break;
}
case sizeof(struct sockaddr_rc): {
const struct sockaddr_rc *const rc = buf;
tprintf("rc_bdaddr=%02x:%02x:%02x:%02x:%02x:%02x"
", rc_channel=%u",
rc->rc_bdaddr.b[0], rc->rc_bdaddr.b[1],
rc->rc_bdaddr.b[2], rc->rc_bdaddr.b[3],
rc->rc_bdaddr.b[4], rc->rc_bdaddr.b[5],
rc->rc_channel);
print_mac_addr("rc_bdaddr=", rc->rc_bdaddr.b,
sizeof(rc->rc_bdaddr.b));
tprintf(", rc_channel=%u", rc->rc_channel);
break;
}
case sizeof(struct sockaddr_l2): {
const struct sockaddr_l2 *const l2 = buf;
print_bluetooth_l2_psm("l2_psm=", l2->l2_psm);
tprintf(", l2_bdaddr=%02x:%02x:%02x:%02x:%02x:%02x",
l2->l2_bdaddr.b[0], l2->l2_bdaddr.b[1],
l2->l2_bdaddr.b[2], l2->l2_bdaddr.b[3],
l2->l2_bdaddr.b[4], l2->l2_bdaddr.b[5]);
print_mac_addr(", l2_bdaddr=", l2->l2_bdaddr.b,
sizeof(l2->l2_bdaddr.b));
print_bluetooth_l2_cid(", l2_cid=", l2->l2_cid);
tprints(", l2_bdaddr_type=");
printxval_index(bdaddr_types, l2->l2_bdaddr_type,