Use linear channel list comparisons
This commit is contained in:
parent
25365ce716
commit
5e413b1372
4 changed files with 86 additions and 27 deletions
|
@ -14,7 +14,7 @@
|
||||||
|
|
||||||
static const char hide_desc[] = "Hides channel memberships not shared";
|
static const char hide_desc[] = "Hides channel memberships not shared";
|
||||||
|
|
||||||
static void h_huc_doing_whois_channel_visibility(hook_data_client *);
|
static void h_huc_doing_whois_channel_visibility(void *);
|
||||||
|
|
||||||
mapi_hfn_list_av1 huc_hfnlist[] = {
|
mapi_hfn_list_av1 huc_hfnlist[] = {
|
||||||
{ "doing_whois_channel_visibility", (hookfn) h_huc_doing_whois_channel_visibility },
|
{ "doing_whois_channel_visibility", (hookfn) h_huc_doing_whois_channel_visibility },
|
||||||
|
@ -24,7 +24,8 @@ mapi_hfn_list_av1 huc_hfnlist[] = {
|
||||||
DECLARE_MODULE_AV2(hide_uncommon_channels, NULL, NULL, NULL, NULL, huc_hfnlist, NULL, NULL, hide_desc);
|
DECLARE_MODULE_AV2(hide_uncommon_channels, NULL, NULL, NULL, NULL, huc_hfnlist, NULL, NULL, hide_desc);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
h_huc_doing_whois_channel_visibility(hook_data_client *hdata)
|
h_huc_doing_whois_channel_visibility(void *data_)
|
||||||
{
|
{
|
||||||
hdata->approved = ((PubChannel(hdata->chptr) && !IsInvisible(hdata->target)) || IsMember((hdata->client), (hdata->chptr)));
|
hook_data_channel_visibility *data = data_;
|
||||||
|
data->approved = data->approved && (!IsInvisible(data->targms->client_p) || data->clientms != NULL);
|
||||||
}
|
}
|
||||||
|
|
|
@ -79,8 +79,6 @@ typedef struct
|
||||||
{
|
{
|
||||||
struct Client *client;
|
struct Client *client;
|
||||||
struct Client *target;
|
struct Client *target;
|
||||||
struct Channel *chptr;
|
|
||||||
int approved;
|
|
||||||
} hook_data_client;
|
} hook_data_client;
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
|
@ -109,6 +107,15 @@ typedef struct
|
||||||
const char *error;
|
const char *error;
|
||||||
} hook_data_channel_approval;
|
} hook_data_channel_approval;
|
||||||
|
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
struct Client *client;
|
||||||
|
struct Channel *chptr;
|
||||||
|
struct membership *clientms;
|
||||||
|
struct membership *targms;
|
||||||
|
int approved;
|
||||||
|
} hook_data_channel_visibility;
|
||||||
|
|
||||||
typedef struct
|
typedef struct
|
||||||
{
|
{
|
||||||
struct Client *client;
|
struct Client *client;
|
||||||
|
|
|
@ -38,14 +38,29 @@ static int add_hashed_target(struct Client *source_p, uint32_t hashv);
|
||||||
struct Channel *
|
struct Channel *
|
||||||
find_allowing_channel(struct Client *source_p, struct Client *target_p)
|
find_allowing_channel(struct Client *source_p, struct Client *target_p)
|
||||||
{
|
{
|
||||||
rb_dlink_node *ptr;
|
rb_dlink_node *ps = source_p->user->channel.head;
|
||||||
struct membership *msptr;
|
rb_dlink_node *pt = target_p->user->channel.head;
|
||||||
|
|
||||||
RB_DLINK_FOREACH(ptr, source_p->user->channel.head)
|
while (ps && pt)
|
||||||
{
|
{
|
||||||
msptr = ptr->data;
|
struct membership *ms = ps->data;
|
||||||
if (is_chanop_voiced(msptr) && IsMember(target_p, msptr->chptr))
|
struct membership *mt = pt->data;
|
||||||
return msptr->chptr;
|
int d;
|
||||||
|
if (ms->chptr == mt->chptr)
|
||||||
|
{
|
||||||
|
if (is_chanop_voiced(ms))
|
||||||
|
return ms->chptr;
|
||||||
|
ps = ps->next;
|
||||||
|
pt = pt->next;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
d = irccmp(ms->chptr->chname, mt->chptr->chname);
|
||||||
|
if (d < 0)
|
||||||
|
ps = ps->next;
|
||||||
|
else if (d > 0)
|
||||||
|
pt = pt->next;
|
||||||
|
else
|
||||||
|
assert("different channels can't have equal names" && false);
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
|
@ -225,8 +225,6 @@ single_whois(struct Client *source_p, struct Client *target_p, int operspy)
|
||||||
{
|
{
|
||||||
char buf[BUFSIZE];
|
char buf[BUFSIZE];
|
||||||
rb_dlink_node *ptr;
|
rb_dlink_node *ptr;
|
||||||
struct membership *msptr;
|
|
||||||
struct Channel *chptr;
|
|
||||||
int cur_len = 0;
|
int cur_len = 0;
|
||||||
int mlen;
|
int mlen;
|
||||||
char *t;
|
char *t;
|
||||||
|
@ -269,19 +267,57 @@ single_whois(struct Client *source_p, struct Client *target_p, int operspy)
|
||||||
|
|
||||||
if (!IsService(target_p))
|
if (!IsService(target_p))
|
||||||
{
|
{
|
||||||
RB_DLINK_FOREACH(ptr, target_p->user->channel.head)
|
hook_data_channel_visibility hdata_vis;
|
||||||
|
rb_dlink_node *ps = source_p->user->channel.head;
|
||||||
|
rb_dlink_node *pt = target_p->user->channel.head;
|
||||||
|
|
||||||
|
hdata_vis.client = source_p;
|
||||||
|
|
||||||
|
while (pt)
|
||||||
{
|
{
|
||||||
msptr = ptr->data;
|
struct membership *mt = pt->data;
|
||||||
chptr = msptr->chptr;
|
int dir = 0;
|
||||||
|
if (ps != NULL)
|
||||||
hdata.chptr = chptr;
|
|
||||||
|
|
||||||
hdata.approved = ShowChannel(source_p, chptr);
|
|
||||||
call_hook(doing_whois_channel_visibility_hook, &hdata);
|
|
||||||
|
|
||||||
if(hdata.approved || operspy)
|
|
||||||
{
|
{
|
||||||
if((cur_len + strlen(chptr->chname) + 3) > (BUFSIZE - 5))
|
struct membership *ms = ps->data;
|
||||||
|
if (ms->chptr == mt->chptr)
|
||||||
|
{
|
||||||
|
ps = ps->next;
|
||||||
|
pt = pt->next;
|
||||||
|
hdata_vis.chptr = mt->chptr;
|
||||||
|
hdata_vis.clientms = ms;
|
||||||
|
hdata_vis.targms = mt;
|
||||||
|
hdata_vis.approved = 1;
|
||||||
|
dir = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dir = irccmp(ms->chptr->chname, mt->chptr->chname);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dir = 1;
|
||||||
|
}
|
||||||
|
if (dir < 0)
|
||||||
|
{
|
||||||
|
ps = ps->next;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
else if (dir > 0)
|
||||||
|
{
|
||||||
|
pt = pt->next;
|
||||||
|
hdata_vis.chptr = mt->chptr;
|
||||||
|
hdata_vis.clientms = NULL;
|
||||||
|
hdata_vis.targms = mt;
|
||||||
|
hdata_vis.approved = PubChannel(mt->chptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
call_hook(doing_whois_channel_visibility_hook, &hdata_vis);
|
||||||
|
|
||||||
|
if(hdata_vis.approved || operspy)
|
||||||
|
{
|
||||||
|
if((cur_len + strlen(mt->chptr->chname) + 3) > (BUFSIZE - 5))
|
||||||
{
|
{
|
||||||
sendto_one(source_p, "%s", buf);
|
sendto_one(source_p, "%s", buf);
|
||||||
cur_len = mlen + extra_space;
|
cur_len = mlen + extra_space;
|
||||||
|
@ -289,9 +325,9 @@ single_whois(struct Client *source_p, struct Client *target_p, int operspy)
|
||||||
}
|
}
|
||||||
|
|
||||||
tlen = sprintf(t, "%s%s%s ",
|
tlen = sprintf(t, "%s%s%s ",
|
||||||
hdata.approved ? "" : "!",
|
hdata_vis.approved ? "" : "!",
|
||||||
find_channel_status(msptr, 1),
|
find_channel_status(mt, 1),
|
||||||
chptr->chname);
|
mt->chptr->chname);
|
||||||
t += tlen;
|
t += tlen;
|
||||||
cur_len += tlen;
|
cur_len += tlen;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue