diff --git a/include/client.h b/include/client.h index 52c53519..b81a9c6a 100644 --- a/include/client.h +++ b/include/client.h @@ -406,6 +406,7 @@ struct ListClient #define FLAGS_TGCHANGE 0x400000 /* we're allowed to clear something */ #define FLAGS_DYNSPOOF 0x800000 /* dynamic spoof, only opers see ip */ #define FLAGS_TGEXCESSIVE 0x1000000 /* whether the client has attemped to change targets excessively fast */ +#define FLAGS_CLICAP_DATA 0x2000000 /* requested CAP LS 302 */ /* flags for local clients, this needs stuff moved from above to here at some point */ #define LFLAGS_SSL 0x00000001 diff --git a/modules/m_cap.c b/modules/m_cap.c index 2619c27c..9f05f3de 100644 --- a/modules/m_cap.c +++ b/modules/m_cap.c @@ -171,6 +171,10 @@ clicap_generate(struct Client *source_p, const char *subcmd, int flags, int clea DICTIONARY_FOREACH(entry, &iter, cli_capindex->cap_dict) { + size_t caplen = 0; + struct ClientCapability *clicap = entry->ownerdata; + const char *data = NULL; + if(flags) { if(!IsCapableEntry(source_p, entry)) @@ -183,8 +187,15 @@ clicap_generate(struct Client *source_p, const char *subcmd, int flags, int clea if (!clicap_visible(entry)) continue; + caplen = strlen(entry->cap); + if (!flags && (source_p->flags & FLAGS_CLICAP_DATA) && clicap != NULL && clicap->data != NULL) + data = clicap->data(); + + if (data != NULL) + caplen += strlen(data) + 1; + /* \r\n\0, possible "-~=", space, " *" */ - if(buflen + strlen(entry->cap) >= BUFSIZE - 10) + if(buflen + caplen >= BUFSIZE - 10) { /* remove our trailing space -- if buflen == mlen * here, we didnt even succeed in adding one. @@ -205,7 +216,11 @@ clicap_generate(struct Client *source_p, const char *subcmd, int flags, int clea buflen++; } - curlen = sprintf(p, "%s ", entry->cap); + if (data == NULL) + curlen = sprintf(p, "%s ", entry->cap); + else + curlen = sprintf(p, "%s=%s ", entry->cap, data); + p += curlen; buflen += curlen; } @@ -289,6 +304,9 @@ cap_ls(struct Client *source_p, const char *arg) if(!IsRegistered(source_p)) source_p->flags |= FLAGS_CLICAP; + if (arg != NULL && !strcmp(arg, "302")) + source_p->flags |= FLAGS_CLICAP_DATA; + /* list of what we support */ clicap_generate(source_p, "LS", 0, 0); }