diff --git a/ircd/send.c b/ircd/send.c index 888b8399..fe9aceec 100644 --- a/ircd/send.c +++ b/ircd/send.c @@ -209,36 +209,36 @@ send_queued_write(rb_fde_t *F, void *data) } /* - * linebuf_put_msgvbuf + * linebuf_put_tags_prefix * * inputs - msgbuf header, linebuf object, capability mask, pattern, arguments * outputs - none - * side effects - the linebuf object is cleared, then populated using rb_linebuf_putmsg(). + * side effects - the linebuf object is cleared, then populated using rb_linebuf_putprefix(). */ static void -linebuf_put_msgvbuf(struct MsgBuf *msgbuf, buf_head_t *linebuf, unsigned int capmask, const char *pattern, va_list *va) +linebuf_put_tags_vprefix(struct MsgBuf *msgbuf, buf_head_t *linebuf, unsigned int capmask, const char *pattern, va_list *va) { static char buf[EXT_BUFSIZE]; size_t buflen = sizeof(buf); rb_linebuf_newbuf(linebuf); msgbuf_unparse_prefix(buf, &buflen, msgbuf, capmask); - rb_linebuf_putprefix(linebuf, pattern, va, buf, buflen); + rb_linebuf_put_vtags_prefix(linebuf, pattern, va, buflen, buf); } -/* linebuf_put_msgbuf +/* linebuf_put_tags_prefixf * * inputs - msgbuf header, linebuf object, capability mask, pattern, arguments * outputs - none - * side effects - the linebuf object is cleared, then populated using rb_linebuf_putmsg(). + * side effects - the linebuf object is cleared, then populated using rb_linebuf_putprefix(). */ static void -linebuf_put_msgbuf(struct MsgBuf *msgbuf, buf_head_t *linebuf, unsigned int capmask, const char *pattern, ...) +linebuf_put_tags_prefixf(struct MsgBuf *msgbuf, buf_head_t *linebuf, unsigned int capmask, const char *pattern, ...) { va_list va; va_start(va, pattern); - linebuf_put_msgvbuf(msgbuf, linebuf, capmask, pattern, &va); + linebuf_put_tags_vprefix(msgbuf, linebuf, capmask, pattern, &va); va_end(va); } @@ -295,7 +295,7 @@ sendto_one(struct Client *target_p, const char *pattern, ...) rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, &args); va_end(args); _send_linebuf(target_p, &linebuf); @@ -328,7 +328,7 @@ sendto_one_prefix(struct Client *target_p, struct Client *source_p, rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s %s %s ", get_id(source_p, target_p), command, get_id(target_p, target_p)); @@ -363,7 +363,7 @@ sendto_one_notice(struct Client *target_p, const char *pattern, ...) rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s NOTICE %s ", get_id(&me, target_p), *(to = get_id(target_p, target_p)) != '\0' ? to : "*"); va_end(args); @@ -398,7 +398,7 @@ sendto_one_numeric(struct Client *target_p, int numeric, const char *pattern, .. rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s %03d %s ", get_id(&me, target_p), numeric, *(to = get_id(target_p, target_p)) != '\0' ? to : "*"); @@ -444,7 +444,7 @@ sendto_server(struct Client *one, struct Channel *chptr, unsigned long caps, rb_linebuf_newbuf(&linebuf); va_start(args, format); - rb_linebuf_putmsg(&linebuf, format, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, format, &args); va_end(args); RB_DLINK_FOREACH_SAFE(ptr, next_ptr, serv_list.head) @@ -482,16 +482,16 @@ sendto_channel_flags(struct Client *one, int type, struct Client *source_p, static char buf[BUFSIZE]; va_list args; buf_head_t rb_linebuf_local; - buf_head_t rb_linebuf_id; + buf_head_t rb_linebuf_remote; struct Client *target_p; struct membership *msptr; rb_dlink_node *ptr; rb_dlink_node *next_ptr; - int current_capmask = 0; + int current_capmask = NOCAPS; struct MsgBuf msgbuf; rb_linebuf_newbuf(&rb_linebuf_local); - rb_linebuf_newbuf(&rb_linebuf_id); + rb_linebuf_newbuf(&rb_linebuf_remote); current_serial++; @@ -501,8 +501,8 @@ sendto_channel_flags(struct Client *one, int type, struct Client *source_p, vsnprintf(buf, sizeof buf, pattern, args); va_end(args); - linebuf_put_msgbuf(&msgbuf, &rb_linebuf_local, NOCAPS, "%s", buf); - rb_linebuf_putmsg(&rb_linebuf_id, NULL, NULL, ":%s %s", use_id(source_p), buf); + linebuf_put_tags_prefixf(&msgbuf, &rb_linebuf_local, current_capmask, "%s", buf); + rb_linebuf_put_msgf(&rb_linebuf_remote, ":%s %s", use_id(source_p), buf); RB_DLINK_FOREACH_SAFE(ptr, next_ptr, chptr->members.head) { @@ -531,7 +531,7 @@ sendto_channel_flags(struct Client *one, int type, struct Client *source_p, if(target_p->from->serial != current_serial) { - send_linebuf_remote(target_p, source_p, &rb_linebuf_id); + send_linebuf_remote(target_p, source_p, &rb_linebuf_remote); target_p->from->serial = current_serial; } } @@ -545,7 +545,7 @@ sendto_channel_flags(struct Client *one, int type, struct Client *source_p, /* render the new linebuf and attach it */ current_capmask = target_p->localClient->caps; - linebuf_put_msgbuf(&msgbuf, &rb_linebuf_local, current_capmask, "%s", buf); + linebuf_put_tags_prefixf(&msgbuf, &rb_linebuf_local, current_capmask, "%s", buf); } _send_linebuf(target_p, &rb_linebuf_local); @@ -565,14 +565,14 @@ sendto_channel_flags(struct Client *one, int type, struct Client *source_p, /* render the new linebuf and attach it */ current_capmask = target_p->localClient->caps; - linebuf_put_msgbuf(&msgbuf, &rb_linebuf_local, current_capmask, "%s", buf); + linebuf_put_tags_prefixf(&msgbuf, &rb_linebuf_local, current_capmask, "%s", buf); } _send_linebuf(target_p, &rb_linebuf_local); } rb_linebuf_donebuf(&rb_linebuf_local); - rb_linebuf_donebuf(&rb_linebuf_id); + rb_linebuf_donebuf(&rb_linebuf_remote); } /* sendto_channel_flags() @@ -601,25 +601,25 @@ sendto_channel_opmod(struct Client *one, struct Client *source_p, current_serial++; if(IsServer(source_p)) - rb_linebuf_putmsg(&rb_linebuf_local, NULL, NULL, + rb_linebuf_put_msgf(&rb_linebuf_local, ":%s %s %s :%s", source_p->name, command, chptr->chname, text); else - rb_linebuf_putmsg(&rb_linebuf_local, NULL, NULL, + rb_linebuf_put_msgf(&rb_linebuf_local, ":%s!%s@%s %s %s :%s", source_p->name, source_p->username, source_p->host, command, chptr->chname, text); if (chptr->mode.mode & MODE_MODERATED) - rb_linebuf_putmsg(&rb_linebuf_old, NULL, NULL, + rb_linebuf_put_msgf(&rb_linebuf_old, ":%s %s %s :%s", use_id(source_p), command, chptr->chname, text); else - rb_linebuf_putmsg(&rb_linebuf_old, NULL, NULL, + rb_linebuf_put_msgf(&rb_linebuf_old, ":%s NOTICE @%s :<%s:%s> %s", use_id(source_p->servptr), chptr->chname, source_p->name, chptr->chname, text); - rb_linebuf_putmsg(&rb_linebuf_new, NULL, NULL, + rb_linebuf_put_msgf(&rb_linebuf_new, ":%s %s =%s :%s", use_id(source_p), command, chptr->chname, text); @@ -693,7 +693,7 @@ sendto_channel_local(int type, struct Channel *chptr, const char *pattern, ...) rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, &args); va_end(args); RB_DLINK_FOREACH_SAFE(ptr, next_ptr, chptr->locmembers.head) @@ -734,7 +734,7 @@ _sendto_channel_local_with_capability_butone(struct Client *one, int type, int c rb_dlink_node *next_ptr; rb_linebuf_newbuf(&linebuf); - rb_linebuf_putmsg(&linebuf, pattern, args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, args); RB_DLINK_FOREACH_SAFE(ptr, next_ptr, chptr->locmembers.head) { @@ -816,7 +816,7 @@ sendto_channel_local_butone(struct Client *one, int type, struct Channel *chptr, build_msgbuf_from(&msgbuf, one, NULL); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, &args); va_end(args); RB_DLINK_FOREACH_SAFE(ptr, next_ptr, chptr->locmembers.head) @@ -868,7 +868,7 @@ sendto_common_channels_local(struct Client *user, int cap, int negcap, const cha rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, &args); va_end(args); ++current_serial; @@ -931,7 +931,7 @@ sendto_common_channels_local_butone(struct Client *user, int cap, int negcap, co rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, &args); va_end(args); ++current_serial; @@ -978,25 +978,25 @@ sendto_match_butone(struct Client *one, struct Client *source_p, rb_dlink_node *ptr; rb_dlink_node *next_ptr; buf_head_t rb_linebuf_local; - buf_head_t rb_linebuf_id; + buf_head_t rb_linebuf_remote; rb_linebuf_newbuf(&rb_linebuf_local); - rb_linebuf_newbuf(&rb_linebuf_id); + rb_linebuf_newbuf(&rb_linebuf_remote); va_start(args, pattern); vsnprintf(buf, sizeof(buf), pattern, args); va_end(args); if(IsServer(source_p)) - rb_linebuf_putmsg(&rb_linebuf_local, NULL, NULL, + rb_linebuf_put_msgf(&rb_linebuf_local, ":%s %s", source_p->name, buf); else - rb_linebuf_putmsg(&rb_linebuf_local, NULL, NULL, + rb_linebuf_put_msgf(&rb_linebuf_local, ":%s!%s@%s %s", source_p->name, source_p->username, source_p->host, buf); - rb_linebuf_putmsg(&rb_linebuf_id, NULL, NULL, ":%s %s", use_id(source_p), buf); + rb_linebuf_put_msgf(&rb_linebuf_remote, ":%s %s", use_id(source_p), buf); if(what == MATCH_HOST) { @@ -1025,11 +1025,11 @@ sendto_match_butone(struct Client *one, struct Client *source_p, if(target_p == one) continue; - send_linebuf_remote(target_p, source_p, &rb_linebuf_id); + send_linebuf_remote(target_p, source_p, &rb_linebuf_remote); } rb_linebuf_donebuf(&rb_linebuf_local); - rb_linebuf_donebuf(&rb_linebuf_id); + rb_linebuf_donebuf(&rb_linebuf_remote); } /* sendto_match_servs() @@ -1057,8 +1057,7 @@ sendto_match_servs(struct Client *source_p, const char *mask, int cap, vsnprintf(buf, sizeof(buf), pattern, args); va_end(args); - rb_linebuf_putmsg(&rb_linebuf_id, NULL, NULL, - ":%s %s", use_id(source_p), buf); + rb_linebuf_put_msgf(&rb_linebuf_id, ":%s %s", use_id(source_p), buf); current_serial++; @@ -1110,7 +1109,7 @@ sendto_local_clients_with_capability(int cap, const char *pattern, ...) rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, &args); va_end(args); RB_DLINK_FOREACH(ptr, lclient_list.head) @@ -1144,7 +1143,7 @@ sendto_monitor(struct monitor *monptr, const char *pattern, ...) rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, NULL); + rb_linebuf_put_vmsg(&linebuf, pattern, &args); va_end(args); RB_DLINK_FOREACH_SAFE(ptr, next_ptr, monptr->users.head) @@ -1178,7 +1177,7 @@ _sendto_anywhere(struct Client *dest_p, struct Client *target_p, if(MyClient(dest_p)) { if(IsServer(source_p)) - rb_linebuf_putmsg(&linebuf, pattern, args, ":%s %s %s ", + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, args, ":%s %s %s ", source_p->name, command, target_p->name); else @@ -1188,11 +1187,11 @@ _sendto_anywhere(struct Client *dest_p, struct Client *target_p, build_msgbuf_from(&msgbuf, source_p, command); msgbuf.target = target_p->name; - linebuf_put_msgvbuf(&msgbuf, &linebuf, dest_p->localClient->caps, pattern, args); + linebuf_put_tags_vprefix(&msgbuf, &linebuf, dest_p->localClient->caps, pattern, args); } } else - rb_linebuf_putmsg(&linebuf, pattern, args, ":%s %s %s ", + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, args, ":%s %s %s ", get_id(source_p, target_p), command, get_id(target_p, target_p)); @@ -1268,7 +1267,8 @@ sendto_realops_snomask(int flags, int level, const char *pattern, ...) va_start(args, pattern); vsnprintf(buf, sizeof(buf), pattern, args); va_end(args); - rb_linebuf_putmsg(&linebuf, pattern, NULL, + + rb_linebuf_put_msgf(&linebuf, ":%s NOTICE * :*** Notice -- %s", me.name, buf); snobuf = construct_snobuf(flags); if (snobuf[1] != '\0') @@ -1282,14 +1282,15 @@ sendto_realops_snomask(int flags, int level, const char *pattern, ...) va_start(args, pattern); vsnprintf(buf, sizeof(buf), pattern, args); va_end(args); - rb_linebuf_putmsg(&linebuf, pattern, NULL, + + rb_linebuf_put_msgf(&linebuf, ":%s NOTICE * :*** Notice -- %s", me.name, buf); sendto_one_notice(remote_rehash_oper_p, ":*** Notice -- %s", buf); } else { va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s NOTICE * :*** Notice -- ", me.name); va_end(args); } @@ -1331,7 +1332,7 @@ sendto_realops_snomask_from(int flags, int level, struct Client *source_p, rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s NOTICE * :*** Notice -- ", source_p->name); va_end(args); @@ -1376,11 +1377,11 @@ sendto_wallops_flags(int flags, struct Client *source_p, const char *pattern, .. va_start(args, pattern); if(IsPerson(source_p)) - rb_linebuf_putmsg(&linebuf, pattern, &args, + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s!%s@%s WALLOPS :", source_p->name, source_p->username, source_p->host); else - rb_linebuf_putmsg(&linebuf, pattern, &args, ":%s WALLOPS :", source_p->name); + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s WALLOPS :", source_p->name); va_end(args); @@ -1410,7 +1411,7 @@ kill_client(struct Client *target_p, struct Client *diedie, const char *pattern, rb_linebuf_newbuf(&linebuf); va_start(args, pattern); - rb_linebuf_putmsg(&linebuf, pattern, &args, ":%s KILL %s :", + rb_linebuf_put_vmsg_prefixf(&linebuf, pattern, &args, ":%s KILL %s :", get_id(&me, target_p), get_id(diedie, target_p)); va_end(args); @@ -1446,7 +1447,7 @@ kill_client_serv_butone(struct Client *one, struct Client *target_p, const char vsnprintf(buf, sizeof(buf), pattern, args); va_end(args); - rb_linebuf_putmsg(&rb_linebuf_id, NULL, NULL, ":%s KILL %s :%s", + rb_linebuf_put_msgf(&rb_linebuf_id, ":%s KILL %s :%s", use_id(&me), use_id(target_p), buf); RB_DLINK_FOREACH_SAFE(ptr, next_ptr, serv_list.head) diff --git a/librb/include/rb_lib.h b/librb/include/rb_lib.h index e8440f54..d1ad39d3 100644 --- a/librb/include/rb_lib.h +++ b/librb/include/rb_lib.h @@ -127,6 +127,17 @@ char *rb_strerror(int error); #define HOSTIPLEN 53 #endif + +/* For those unfamiliar with GNU format attributes, a is the 1 based + * argument number of the format string, and b is the 1 based argument + * number of the variadic ... */ +#ifdef __GNUC__ +#define AFP(a,b) __attribute__((format (printf, a, b))) +#else +#define AFP(a,b) +#endif + + #ifdef __GNUC__ #define slrb_assert(expr) ( \ rb_likely((expr)) || ( \ diff --git a/librb/include/rb_linebuf.h b/librb/include/rb_linebuf.h index 2554025e..39e5bd84 100644 --- a/librb/include/rb_linebuf.h +++ b/librb/include/rb_linebuf.h @@ -39,12 +39,14 @@ struct _buf_line; struct _buf_head; /* IRCv3 tags (512 bytes) + RFC1459 message (510 bytes) */ -#define LINEBUF_DATA_SIZE (512 + 510) -#define CRLF_LEN 2 +#define LINEBUF_TAGSLEN 512 /* IRCv3 message tags */ +#define LINEBUF_DATALEN 510 /* RFC1459 message data */ +#define LINEBUF_SIZE (512 + 510) +#define CRLF_LEN 2 typedef struct _buf_line { - char buf[LINEBUF_DATA_SIZE + CRLF_LEN + 1]; + char buf[LINEBUF_SIZE + CRLF_LEN + 1]; uint8_t terminated; /* Whether we've terminated the buffer */ uint8_t raw; /* Whether this linebuf may hold 8-bit data */ int len; /* How much data we've got */ @@ -72,10 +74,15 @@ void rb_linebuf_newbuf(buf_head_t *); void rb_linebuf_donebuf(buf_head_t *); int rb_linebuf_parse(buf_head_t *, char *, int, int); int rb_linebuf_get(buf_head_t *, char *, int, int, int); -void rb_linebuf_putmsg(buf_head_t *, const char *, va_list *, const char *, ...); -void rb_linebuf_putprefix(buf_head_t *, const char *, va_list *, const char *, size_t); -void rb_linebuf_put(buf_head_t *, const char *, ...); -void rb_linebuf_putbuf(buf_head_t * bufhead, const char *buffer); +/* "msg" is limited to RFC1459 message size */ +void rb_linebuf_put_msgf(buf_head_t *, const char *, ...) AFP(2,3); +void rb_linebuf_put_vmsg(buf_head_t *, const char *, va_list *); +void rb_linebuf_put_vmsg_prefixf(buf_head_t *, const char *, va_list *, const char *, ...) AFP(4,5); +/* "tags" has a prefix that contains tags AND messages, it must + * specify the correct total buffer length to enforce the limit + * of the RFC1459 message size */ +void rb_linebuf_put_vtags_prefix(buf_head_t *, const char *, va_list *, size_t, const char *); +void rb_linebuf_put_vtags_prefixf(buf_head_t *, const char *, va_list *, size_t, const char *, ...) AFP(5,6); void rb_linebuf_attach(buf_head_t *, buf_head_t *); void rb_count_rb_linebuf_memory(size_t *, size_t *); int rb_linebuf_flush(rb_fde_t *F, buf_head_t *); diff --git a/librb/src/export-syms.txt b/librb/src/export-syms.txt index a7059d53..39256305 100644 --- a/librb/src/export-syms.txt +++ b/librb/src/export-syms.txt @@ -100,10 +100,11 @@ rb_linebuf_get rb_linebuf_init rb_linebuf_newbuf rb_linebuf_parse -rb_linebuf_put -rb_linebuf_putbuf -rb_linebuf_putmsg -rb_linebuf_putprefix +rb_linebuf_put_msgf +rb_linebuf_put_vmsg +rb_linebuf_put_vmsg_prefixf +rb_linebuf_put_vtags_prefix +rb_linebuf_put_vtags_prefixf rb_listen rb_make_rb_dlink_node rb_match_exact_string diff --git a/librb/src/helper.c b/librb/src/helper.c index a8dabf3d..0e2231dc 100644 --- a/librb/src/helper.c +++ b/librb/src/helper.c @@ -215,7 +215,7 @@ rb_helper_write_queue(rb_helper *helper, const char *format, ...) { va_list ap; va_start(ap, format); - rb_linebuf_putmsg(&helper->sendq, format, &ap, NULL); + rb_linebuf_put_vmsg(&helper->sendq, format, &ap); va_end(ap); } @@ -231,7 +231,7 @@ rb_helper_write(rb_helper *helper, const char *format, ...) { va_list ap; va_start(ap, format); - rb_linebuf_putmsg(&helper->sendq, format, &ap, NULL); + rb_linebuf_put_vmsg(&helper->sendq, format, &ap); va_end(ap); rb_helper_write_flush(helper); } diff --git a/librb/src/linebuf.c b/librb/src/linebuf.c index e4c92ee9..9d7e9bcf 100644 --- a/librb/src/linebuf.c +++ b/librb/src/linebuf.c @@ -204,7 +204,7 @@ rb_linebuf_copy_line(buf_head_t * bufhead, buf_line_t * bufline, char *data, int /* If its full or terminated, ignore it */ bufline->raw = 0; - lrb_assert(bufline->len <= LINEBUF_DATA_SIZE); + lrb_assert(bufline->len <= LINEBUF_SIZE); if(bufline->terminated == 1) return 0; @@ -213,12 +213,12 @@ rb_linebuf_copy_line(buf_head_t * bufhead, buf_line_t * bufline, char *data, int return -1; /* This is the ~overflow case..This doesn't happen often.. */ - if(cpylen > (LINEBUF_DATA_SIZE - bufline->len)) + if(cpylen > (LINEBUF_SIZE - bufline->len)) { - cpylen = LINEBUF_DATA_SIZE - bufline->len; + cpylen = LINEBUF_SIZE - bufline->len; memcpy(bufch, ch, cpylen); - bufline->buf[LINEBUF_DATA_SIZE] = '\0'; - bufch = bufline->buf + LINEBUF_DATA_SIZE - 1; + bufline->buf[LINEBUF_SIZE] = '\0'; + bufch = bufline->buf + LINEBUF_SIZE - 1; while(cpylen && (*bufch == '\r' || *bufch == '\n')) { *bufch = '\0'; @@ -226,8 +226,8 @@ rb_linebuf_copy_line(buf_head_t * bufhead, buf_line_t * bufline, char *data, int bufch--; } bufline->terminated = 1; - bufline->len = LINEBUF_DATA_SIZE; - bufhead->len += LINEBUF_DATA_SIZE; + bufline->len = LINEBUF_SIZE; + bufhead->len += LINEBUF_SIZE; return clen; } @@ -278,7 +278,7 @@ rb_linebuf_copy_raw(buf_head_t * bufhead, buf_line_t * bufline, char *data, int /* If its full or terminated, ignore it */ bufline->raw = 1; - lrb_assert(bufline->len <= LINEBUF_DATA_SIZE); + lrb_assert(bufline->len <= LINEBUF_SIZE); if(bufline->terminated == 1) return 0; @@ -287,14 +287,14 @@ rb_linebuf_copy_raw(buf_head_t * bufhead, buf_line_t * bufline, char *data, int return -1; /* This is the overflow case..This doesn't happen often.. */ - if(cpylen > (LINEBUF_DATA_SIZE - bufline->len)) + if(cpylen > (LINEBUF_SIZE - bufline->len)) { - clen = LINEBUF_DATA_SIZE - bufline->len; + clen = LINEBUF_SIZE - bufline->len; memcpy(bufch, ch, clen); - bufline->buf[LINEBUF_DATA_SIZE] = '\0'; + bufline->buf[LINEBUF_SIZE] = '\0'; bufline->terminated = 1; - bufline->len = LINEBUF_DATA_SIZE; - bufhead->len += LINEBUF_DATA_SIZE; + bufline->len = LINEBUF_SIZE; + bufhead->len += LINEBUF_SIZE; return clen; } @@ -485,253 +485,140 @@ rb_linebuf_attach(buf_head_t * bufhead, buf_head_t * new) } /* - * rb_linebuf_putmsg + * rb_linebuf_put_vstr_vprefix * - * Similar to rb_linebuf_put, but designed for use by send.c. + * prefix (with/without prefix_args) is inserted first, then format/va_args is + * appended to the buffer. * - * prefixfmt is used as a format for the varargs, and is inserted first. - * Then format/va_args is appended to the buffer. + * max_buflen is the maximum size of the buffer that can be used + * (including the NULL terminator) so that the RFC1459 message is not too long */ -void -rb_linebuf_putmsg(buf_head_t * bufhead, const char *format, va_list * va_args, - const char *prefixfmt, ...) +static void +rb_linebuf_put_vstr_vprefix(buf_head_t *bufhead, const char *format, va_list *format_args, + size_t max_buflen, const char *prefix, va_list *prefix_args) { buf_line_t *bufline; - int len = 0; - va_list prefix_args; + ssize_t len = 0; /* make sure the previous line is terminated */ - if(bufhead->list.tail) - { + if (bufhead->list.tail) { bufline = bufhead->list.tail->data; lrb_assert(bufline->terminated); } - /* Create a new line */ + /* create a new line */ bufline = rb_linebuf_new_line(bufhead); - if(prefixfmt != NULL) - { - va_start(prefix_args, prefixfmt); - len = vsnprintf(bufline->buf, LINEBUF_DATA_SIZE + 1, prefixfmt, prefix_args); - va_end(prefix_args); - } + if (max_buflen > LINEBUF_SIZE + 1) + max_buflen = LINEBUF_SIZE + 1; - if(va_args != NULL) - { - len += vsnprintf((bufline->buf + len), (LINEBUF_DATA_SIZE - len) + 1, format, *va_args); - } - - bufline->terminated = 1; - - /* Truncate the data if required */ - if(len > LINEBUF_DATA_SIZE) - { - len = LINEBUF_DATA_SIZE; - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - } - else if(len == 0) - { - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - bufline->buf[len] = '\0'; - } - else - { - /* Chop trailing CRLF's .. */ - while((bufline->buf[len] == '\r') || (bufline->buf[len] == '\n') - || (bufline->buf[len] == '\0')) - { - len--; + if (prefix != NULL) { + if (prefix_args != NULL) { + len = vsnprintf(bufline->buf, max_buflen, prefix, *prefix_args); + } else { + len = rb_strlcpy(bufline->buf, prefix, max_buflen); } - bufline->buf[++len] = '\r'; - bufline->buf[++len] = '\n'; - bufline->buf[++len] = '\0'; + if (len > max_buflen - 1) + len = max_buflen - 1; } + if (format != NULL) { + len += vsnprintf(bufline->buf + len, max_buflen - len, format, *format_args); + if (len > max_buflen - 1) + len = max_buflen - 1; + } + + /* add trailing CRLF */ + bufline->buf[len++] = '\r'; + bufline->buf[len++] = '\n'; + bufline->buf[len] = '\0'; + + bufline->terminated = 1; + bufline->len = len; bufhead->len += len; } /* - * rb_linebuf_putprefix + * rb_linebuf_put_vtags_prefix * - * Similar to rb_linebuf_put, but designed for use by send.c. + * prefix is inserted first, then format/va_args is + * appended to the buffer. * - * prefix is inserted first, then format/va_args is appended to the buffer. - * prefix_buflen is the maximum size of the buffer that can be used so that the RFC1459 message is not too long + * prefix_buflen is the maximum size of the buffer that can be used + * (including the NULL terminator) so that the RFC1459 message is not too long */ void -rb_linebuf_putprefix(buf_head_t * bufhead, const char *format, va_list * va_args, - const char *prefix, size_t prefix_buflen) +rb_linebuf_put_vtags_prefix(buf_head_t *bufhead, const char *format, va_list *va_args, + size_t prefix_buflen, const char *prefix) { - buf_line_t *bufline; - int len = 0; - - /* make sure the previous line is terminated */ - if(bufhead->list.tail) - { - bufline = bufhead->list.tail->data; - lrb_assert(bufline->terminated); - } - - /* Create a new line */ - bufline = rb_linebuf_new_line(bufhead); - - if(prefix != NULL) - len = rb_strlcpy(bufline->buf, prefix, LINEBUF_DATA_SIZE + 1); - - if(va_args != NULL) - { - if (prefix_buflen > LINEBUF_DATA_SIZE + 1) - prefix_buflen = LINEBUF_DATA_SIZE + 1; - len += vsnprintf((bufline->buf + len), prefix_buflen - len, format, *va_args); - } - - bufline->terminated = 1; - - /* Truncate the data if required */ - if(len > LINEBUF_DATA_SIZE) - { - len = LINEBUF_DATA_SIZE; - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - } - else if(len == 0) - { - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - bufline->buf[len] = '\0'; - } - else - { - /* Chop trailing CRLF's .. */ - while((bufline->buf[len] == '\r') || (bufline->buf[len] == '\n') - || (bufline->buf[len] == '\0')) - { - len--; - } - - bufline->buf[++len] = '\r'; - bufline->buf[++len] = '\n'; - bufline->buf[++len] = '\0'; - } - - bufline->len = len; - bufhead->len += len; + rb_linebuf_put_vstr_vprefix(bufhead, format, va_args, prefix_buflen, prefix, NULL); } +/* + * rb_linebuf_put_vtags_prefixf + * + * prefixfmt is inserted first, then format/va_args is + * appended to the buffer. + * + * prefix_buflen is the maximum size of the buffer that can be used + * (including the NULL terminator) so that the RFC1459 message is not too long + */ void -rb_linebuf_putbuf(buf_head_t * bufhead, const char *buffer) +rb_linebuf_put_vtags_prefixf(buf_head_t *bufhead, const char *format, va_list *va_args, + size_t prefix_buflen, const char *prefixfmt, ...) { - buf_line_t *bufline; - int len = 0; - - /* make sure the previous line is terminated */ - if(bufhead->list.tail) - { - bufline = bufhead->list.tail->data; - lrb_assert(bufline->terminated); - } - - /* Create a new line */ - bufline = rb_linebuf_new_line(bufhead); - - if(buffer != NULL) - len = rb_strlcpy(bufline->buf, buffer, LINEBUF_DATA_SIZE + 1); - - bufline->terminated = 1; - - /* Truncate the data if required */ - if(len > LINEBUF_DATA_SIZE) - { - len = LINEBUF_DATA_SIZE; - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - } - else if(len == 0) - { - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - bufline->buf[len] = '\0'; - } - else - { - /* Chop trailing CRLF's .. */ - while((bufline->buf[len] == '\r') || (bufline->buf[len] == '\n') - || (bufline->buf[len] == '\0')) - { - len--; - } - - bufline->buf[++len] = '\r'; - bufline->buf[++len] = '\n'; - bufline->buf[++len] = '\0'; - } - - bufline->len = len; - bufhead->len += len; - + va_list prefix_args; + va_start(prefix_args, prefixfmt); + rb_linebuf_put_vstr_vprefix(bufhead, format, va_args, prefix_buflen, prefixfmt, &prefix_args); + va_end(prefix_args); } +/* + * rb_linebuf_put_msgf + * + * format (with args) is appended to the buffer. + * Messages will be limited to the RFC1459 data length + */ void -rb_linebuf_put(buf_head_t * bufhead, const char *format, ...) +rb_linebuf_put_msgf(buf_head_t *bufhead, const char *format, ...) { - buf_line_t *bufline; - int len = 0; - va_list args; + va_list va_args; - /* make sure the previous line is terminated */ - if(bufhead->list.tail) - { - bufline = bufhead->list.tail->data; - lrb_assert(bufline->terminated); - } + va_start(va_args, format); + rb_linebuf_put_vstr_vprefix(bufhead, format, &va_args, LINEBUF_DATALEN + 1, NULL, NULL); + va_end(va_args); +} - /* Create a new line */ - bufline = rb_linebuf_new_line(bufhead); +/* + * rb_linebuf_put_vmsg + * + * format/va_args is appended to the buffer. + * Messages will be limited to the RFC1459 data length + */ +void +rb_linebuf_put_vmsg(buf_head_t *bufhead, const char *format, va_list *va_args) +{ + rb_linebuf_put_vstr_vprefix(bufhead, format, va_args, LINEBUF_DATALEN + 1, NULL, NULL); +} - if(format != NULL) - { - va_start(args, format); - len = vsnprintf(bufline->buf, LINEBUF_DATA_SIZE + 1, format, args); - va_end(args); - } +/* + * rb_linebuf_put_vmsg_prefixf + * + * prefix is inserted first, then format/va_args is appended to the buffer. + * Messages will be limited to the RFC1459 data length + */ +void +rb_linebuf_put_vmsg_prefixf(buf_head_t *bufhead, const char *format, va_list *va_args, + const char *prefixfmt, ...) +{ + va_list prefix_args; - bufline->terminated = 1; - - /* Truncate the data if required */ - if(len > LINEBUF_DATA_SIZE) - { - len = LINEBUF_DATA_SIZE; - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - } - else if(len == 0) - { - bufline->buf[len++] = '\r'; - bufline->buf[len++] = '\n'; - bufline->buf[len] = '\0'; - } - else - { - /* Chop trailing CRLF's .. */ - while((bufline->buf[len] == '\r') || (bufline->buf[len] == '\n') - || (bufline->buf[len] == '\0')) - { - len--; - } - - bufline->buf[++len] = '\r'; - bufline->buf[++len] = '\n'; - bufline->buf[++len] = '\0'; - } - - bufline->len = len; - bufhead->len += len; + va_start(prefix_args, prefixfmt); + rb_linebuf_put_vstr_vprefix(bufhead, format, va_args, LINEBUF_DATALEN + 1, prefixfmt, &prefix_args); + va_end(prefix_args); }