From 942b0218f49b8cfe7a26325e8729c2f8434f3f5a Mon Sep 17 00:00:00 2001 From: rswindell <> Date: Thu, 19 Mar 2020 05:33:27 +0000 Subject: [PATCH] New function: smb_msghdr_str_list() which returns a message header as a string list (str_list_t) where each string is a header field (variable or fixed) in "<name> <value>" format. This format more closely resembles the output of the sbbs_t::msghdr() function which is used to dump message headers (e.g. for sysops/sub-ops). I intend to replace the duplicate logic in sbbs_t::msghdr() with this new function. I would have liked to have used a list of named strings (named_string_t), but I don't yet have a library to alloc/add items to a named string list. --- src/smblib/smbdump.c | 151 +++++++++++++++++++++++-------------------- src/smblib/smblib.h | 4 +- 2 files changed, 85 insertions(+), 70 deletions(-) diff --git a/src/smblib/smbdump.c b/src/smblib/smbdump.c index a1b829a7e1..399e9a3e10 100644 --- a/src/smblib/smbdump.c +++ b/src/smblib/smbdump.c @@ -62,101 +62,114 @@ static char *binstr(uchar *buf, uint16_t length) return(str); } -void SMBCALL smb_dump_msghdr(FILE* fp, smbmsg_t* msg) +str_list_t SMBCALL smb_msghdr_str_list(smbmsg_t* msg) { int i; time_t tt; + str_list_t list = strListInit(); - fprintf(fp,"%-20.20s %"PRId32"\n" ,"number" ,msg->hdr.number); - - /* convenience strings */ - if(msg->subj) - fprintf(fp,"%-20.20s \"%s\"\n" ,"subject" ,msg->subj); - if(msg->to) { - fprintf(fp,"%-20.20s %s" ,"to" ,msg->to); - if(msg->to_net.type) - fprintf(fp," (%s: %s)",smb_nettype(msg->to_net.type), smb_netaddr(&msg->to_net)); - if(msg->to_ext) - fprintf(fp," #%s",msg->to_ext); - fprintf(fp,"\n"); - } - if(msg->from) { - fprintf(fp,"%-20.20s \"%s\"" ,"from" ,msg->from); - if(msg->from_net.type) - fprintf(fp," (%s: %s)",smb_nettype(msg->from_net.type), smb_netaddr(&msg->from_net)); - if(msg->from_ext) - fprintf(fp," #%s",msg->from_ext); - fprintf(fp,"\n"); - } - if(msg->replyto) { - fprintf(fp,"%-20.20s \"%s\"" ,"reply-to" ,msg->replyto); - if(msg->replyto_ext) - fprintf(fp," #%s",msg->replyto_ext); - if(msg->replyto_net.type) - fprintf(fp," (%s: %s)",smb_nettype(msg->replyto_net.type), smb_netaddr(&msg->replyto_net)); - fprintf(fp,"\n"); - } - if(msg->summary) - fprintf(fp,"%-20.20s \"%s\"\n" ,"summary" ,msg->summary); + if(list == NULL) + return NULL; - /* convenience integers */ - if(msg->expiration) { - tt=msg->expiration; - fprintf(fp,"%-20.20s %.24s\n","expiration" - ,ctime(&tt)); +#define HFIELD_NAME_FMT "%-16.16s " + + /* variable fields */ + for(i=0;i<msg->total_hfields;i++) { + switch(msg->hfield[i].type) { + case SMB_COLUMNS: + strListAppendFormat(&list, HFIELD_NAME_FMT "%u" + ,smb_hfieldtype(msg->hfield[i].type) + ,*(uint8_t*)msg->hfield_dat[i]); + break; + case SENDERNETTYPE: + case RECIPIENTNETTYPE: + case REPLYTONETTYPE: + strListAppendFormat(&list, HFIELD_NAME_FMT "%s" + ,smb_hfieldtype(msg->hfield[i].type) + ,smb_nettype((enum smb_net_type)*(uint16_t*)msg->hfield_dat[i])); + break; + default: + strListAppendFormat(&list, HFIELD_NAME_FMT "%s" + ,smb_hfieldtype(msg->hfield[i].type) + ,binstr((uchar *)msg->hfield_dat[i],msg->hfield[i].length)); + break; + } } /* fixed header fields */ tt=msg->hdr.when_written.time; - fprintf(fp,"%-20.20s %.24s UTC%+d:%02d\n" ,"when_written" + strListAppendFormat(&list, HFIELD_NAME_FMT "%08X %04hX %.24s %s" ,"when_written" + ,msg->hdr.when_written.time, msg->hdr.when_written.zone ,ctime(&tt) - ,smb_tzutc(msg->hdr.when_written.zone)/60 - ,abs(smb_tzutc(msg->hdr.when_written.zone)%60)); + ,smb_zonestr(msg->hdr.when_written.zone,NULL)); tt=msg->hdr.when_imported.time; - fprintf(fp,"%-20.20s %.24s UTC%+d:%02d\n" ,"when_imported" + strListAppendFormat(&list, HFIELD_NAME_FMT "%08X %04hX %.24s %s" ,"when_imported" + ,msg->hdr.when_imported.time, msg->hdr.when_imported.zone ,ctime(&tt) - ,smb_tzutc(msg->hdr.when_imported.zone)/60 - ,abs(smb_tzutc(msg->hdr.when_imported.zone)%60)); - fprintf(fp,"%-20.20s %04Xh\n" ,"type" ,msg->hdr.type); - fprintf(fp,"%-20.20s %04Xh\n" ,"version" ,msg->hdr.version); - fprintf(fp,"%-20.20s %04Xh\n" ,"attr" ,msg->hdr.attr); - fprintf(fp,"%-20.20s %08"PRIX32"h\n" ,"auxattr" ,msg->hdr.auxattr); - fprintf(fp,"%-20.20s %08"PRIX32"h\n" ,"netattr" ,msg->hdr.netattr); + ,smb_zonestr(msg->hdr.when_imported.zone,NULL)); + strListAppendFormat(&list, HFIELD_NAME_FMT "%04Xh" ,"type" ,msg->hdr.type); + strListAppendFormat(&list, HFIELD_NAME_FMT "%04Xh" ,"version" ,msg->hdr.version); + strListAppendFormat(&list, HFIELD_NAME_FMT "%04Xh" ,"attr" ,msg->hdr.attr); + strListAppendFormat(&list, HFIELD_NAME_FMT "%08"PRIX32"h" ,"auxattr" ,msg->hdr.auxattr); + strListAppendFormat(&list, HFIELD_NAME_FMT "%08"PRIX32"h" ,"netattr" ,msg->hdr.netattr); + strListAppendFormat(&list, HFIELD_NAME_FMT "%06"PRIX32"h" ,"header_offset" ,msg->idx.offset); + strListAppendFormat(&list, HFIELD_NAME_FMT "%u (calc: %lu)" ,"header_length" ,msg->hdr.length, smb_getmsghdrlen(msg)); + strListAppendFormat(&list, HFIELD_NAME_FMT "%"PRId32 ,"number" ,msg->hdr.number); /* optional fixed fields */ if(msg->hdr.thread_id) - fprintf(fp,"%-20.20s %"PRId32"\n" ,"thread_id" ,msg->hdr.thread_id); + strListAppendFormat(&list, HFIELD_NAME_FMT "%"PRId32 ,"thread_id" ,msg->hdr.thread_id); if(msg->hdr.thread_back) - fprintf(fp,"%-20.20s %"PRId32"\n" ,"thread_back" ,msg->hdr.thread_back); + strListAppendFormat(&list, HFIELD_NAME_FMT "%"PRId32 ,"thread_back" ,msg->hdr.thread_back); if(msg->hdr.thread_next) - fprintf(fp,"%-20.20s %"PRId32"\n" ,"thread_next" ,msg->hdr.thread_next); + strListAppendFormat(&list, HFIELD_NAME_FMT "%"PRId32 ,"thread_next" ,msg->hdr.thread_next); if(msg->hdr.thread_first) - fprintf(fp,"%-20.20s %"PRId32"\n" ,"thread_first" ,msg->hdr.thread_first); + strListAppendFormat(&list, HFIELD_NAME_FMT "%"PRId32 ,"thread_first" ,msg->hdr.thread_first); if(msg->hdr.delivery_attempts) - fprintf(fp,"%-20.20s %hu\n" ,"delivery_attempts",msg->hdr.delivery_attempts); - if(msg->hdr.times_downloaded) - fprintf(fp,"%-20.20s %"PRIu32"\n" ,"times_downloaded" ,msg->hdr.times_downloaded); - if(msg->hdr.last_downloaded) { - tt=msg->hdr.last_downloaded; - fprintf(fp,"%-20.20s %.24s\n" ,"last_downloaded" ,ctime(&tt)); + strListAppendFormat(&list, HFIELD_NAME_FMT "%hu" ,"delivery_attempts",msg->hdr.delivery_attempts); + if(msg->hdr.votes) + strListAppendFormat(&list, HFIELD_NAME_FMT "%hu" ,"votes" ,msg->hdr.votes); + if(msg->hdr.type == SMB_MSG_TYPE_NORMAL) { + if(msg->hdr.priority) + strListAppendFormat(&list, HFIELD_NAME_FMT "%u" ,"priority" ,msg->hdr.priority); + } else { // FILE + if(msg->hdr.times_downloaded) + strListAppendFormat(&list, HFIELD_NAME_FMT "%"PRIu32,"times_downloaded" ,msg->hdr.times_downloaded); + if(msg->hdr.last_downloaded) { + tt=msg->hdr.last_downloaded; + strListAppendFormat(&list, HFIELD_NAME_FMT "%.24s" ,"last_downloaded" ,ctime(&tt)); + } } - fprintf(fp,"%-20.20s %06"PRIX32"h\n" ,"header offset" ,msg->idx.offset); - fprintf(fp,"%-20.20s %u\n" ,"header length" ,msg->hdr.length); - fprintf(fp,"%-20.20s %lu\n" ,"calculated length",smb_getmsghdrlen(msg)); - - /* variable fields */ - for(i=0;i<msg->total_hfields;i++) - fprintf(fp,"%-20.20s \"%s\"\n" - ,smb_hfieldtype(msg->hfield[i].type) - ,binstr((uchar *)msg->hfield_dat[i],msg->hfield[i].length)); + /* convenience integers */ + if(msg->expiration) { + tt=msg->expiration; + strListAppendFormat(&list, HFIELD_NAME_FMT "%.24s", "expiration", ctime(&tt)); + } + if(msg->cost) + strListAppendFormat(&list, HFIELD_NAME_FMT "%u", "cost", msg->cost); /* data fields */ - fprintf(fp,"%-20.20s %06"PRIX32"h\n" ,"data offset" ,msg->hdr.offset); + strListAppendFormat(&list, HFIELD_NAME_FMT "%06"PRIX32"h" ,"data_offset" ,msg->hdr.offset); for(i=0;i<msg->hdr.total_dfields;i++) - fprintf(fp,"data field[%u] %s, offset %"PRIu32", length %"PRIu32"\n" + strListAppendFormat(&list, "data_field[%u] %s, offset %"PRIu32", length %"PRIu32 ,i ,smb_dfieldtype(msg->dfield[i].type) ,msg->dfield[i].offset ,msg->dfield[i].length); + + return list; +} + +void SMBCALL smb_dump_msghdr(FILE* fp, smbmsg_t* msg) +{ + int i; + + str_list_t list = smb_msghdr_str_list(msg); + if(list != NULL) { + for(i = 0; list[i] != NULL; i++) { + fprintf(fp, "%s\n", list[i]); + } + strListFree(&list); + } } diff --git a/src/smblib/smblib.h b/src/smblib/smblib.h index 42d96553c5..564fbe7cfa 100644 --- a/src/smblib/smblib.h +++ b/src/smblib/smblib.h @@ -65,6 +65,7 @@ #endif #include "smbdefs.h" +#include "str_list.h" #define SMB_SUCCESS 0 /* Successful result/return code */ #define SMB_FAILURE -1 /* Generic error (discouraged) */ @@ -265,7 +266,8 @@ SMBEXPORT fidoaddr_t SMBCALL smb_atofaddr(const fidoaddr_t* sys_addr, const char SMBEXPORT enum smb_net_type SMBCALL smb_netaddr_type(const char* addr); SMBEXPORT enum smb_net_type SMBCALL smb_get_net_type_by_addr(const char* addr); /* smbdump.c */ -SMBEXPORT void SMBCALL smb_dump_msghdr(FILE* fp, smbmsg_t* msg); +SMBEXPORT void SMBCALL smb_dump_msghdr(FILE*, smbmsg_t*); +SMBEXPORT str_list_t SMBCALL smb_msghdr_str_list(smbmsg_t*); /* smbtxt.c */ SMBEXPORT char* SMBCALL smb_getmsgtxt(smb_t*, smbmsg_t*, ulong mode); -- GitLab