diff --git a/Changes b/Changes index 6675a07fa..452ab7830 100644 --- a/Changes +++ b/Changes @@ -472,5 +472,5 @@ - Removed SVSMODE +l support, and fixed servicestamp and +d support - Changed to ircu/hybrid6/unreal mix of numeric 005 - Fixed a SJ3 Fake Direction loopbug (kills on nick collisions) -- NS part 1 -- SJ3 fixes +- SJ3 fixes, loop fix +- Added NS, new generation ALN. diff --git a/src/aln.c b/src/aln.c index 61cdb692e..3a17a8fe2 100644 --- a/src/aln.c +++ b/src/aln.c @@ -135,6 +135,34 @@ char *find_server_id(aClient *which) return (base64enc(which->serv->numeric)); } +aClient *find_server_quick(char *name) +{ + Link *lp; + + for (lp = servers; lp; lp = lp->next) + if (!strcmp(lp->value.cptr->name, name)) + return (lp->value.cptr); + return NULL; +} + +aClient *find_server_b64_or_real(char *name) +{ + Link *lp; + + if (strlen(name) < 4) + { + for (lp = servers; lp; lp = lp->next) + if (!strcmp(base64enc(lp->value.cptr->serv->numeric), name)) + return (lp->value.cptr); + } + else + { + return find_server_quick(name); + } + return NULL; + +} + /* ':' and '#' and '&' and '+' and '@' must never be in this table. */ /* these tables must NEVER CHANGE! >) */ char int6_to_base64_map[] = { @@ -213,3 +241,4 @@ void ns_stats(aClient *cptr) find_server_id(sptr)); } } + diff --git a/src/channel.c b/src/channel.c index 60e9ad6f6..319a0ceee 100644 --- a/src/channel.c +++ b/src/channel.c @@ -4763,9 +4763,9 @@ int m_sjoin(cptr, sptr, parc, parv) nick[i++] = *(tp++); /* get nick */ nick[i] = '\0'; if (nick[0] == ' ') - continue; + goto nextnick; if (nick[0] == '\0') - continue; + goto nextnick; if (!(modeflags & CHFL_BAN) && !(modeflags & CHFL_EXCEPT)) { @@ -4775,9 +4775,9 @@ int m_sjoin(cptr, sptr, parc, parv) ("Missing user %s in SJOIN for %s from %s (%s)", nick, chptr->chname, sptr->name, backupbuf); - continue; + goto nextnick; } -/* if (acptr->from != sptr->from) + if (acptr->from != sptr->from) { sendto_one(sptr, ":%s KICK %s %s :Fake direction", @@ -4787,9 +4787,8 @@ int m_sjoin(cptr, sptr, parc, parv) nick, acptr->from->name, sptr->name, chptr->chname); - continue; + goto nextnick; } -*/ if (removetheirs) { modeflags = 0; @@ -4811,7 +4810,7 @@ int m_sjoin(cptr, sptr, parc, parv) else { if (removetheirs) - continue; + goto nextnick; if (modeflags & CHFL_BAN) { add_banid(sptr, chptr, nick); @@ -4835,6 +4834,7 @@ int m_sjoin(cptr, sptr, parc, parv) } } +nextnick: t++; c++; } diff --git a/src/list.c b/src/list.c index 833cd22dd..685a93906 100644 --- a/src/list.c +++ b/src/list.c @@ -196,6 +196,7 @@ anUser *make_user(cptr) aServer *make_server(cptr) aClient *cptr; { + aServer *serv = cptr->serv; if (!serv) diff --git a/src/parse.c b/src/parse.c index eb203db92..3b3e06981 100644 --- a/src/parse.c +++ b/src/parse.c @@ -54,6 +54,7 @@ static char sender[HOSTLEN + 1]; static int cancel_clients PROTO((aClient *, aClient *, char *)); static void remove_unknown PROTO((aClient *, char *)); static char unknownserver[] = "Unknown.Server"; +static char nsprefix = 0; /* ** Find a client (server or user) by name. ** @@ -70,13 +71,6 @@ aClient *find_client(name, cptr) if (name) { -/* if (*name == '@') - { - newname = name; - if (!name) - name = newname; - } -*/ cptr = hash_find_client(name, cptr); } return cptr; @@ -113,14 +107,6 @@ aClient *find_server(name, cptr) char *newname; if (name) { -/* if (*name == '@') - { - newname = name; - name = find_by_aln(name + 1); - if (!name) - name = newname; - } -*/ cptr = hash_find_server(name, cptr); } return cptr; @@ -249,6 +235,8 @@ int parse(cptr, buffer, bufend, mptr) para[0] = from->name; if (*ch == ':' || *ch == '@') { + if (*ch == '@') + nsprefix = 1; /* ** Copy the prefix to 'sender' assuming it terminates ** with SPACE (or NULL, which is an error, though). @@ -270,13 +258,21 @@ int parse(cptr, buffer, bufend, mptr) */ if (*sender && IsServer(cptr)) { - from = find_client(sender, (aClient *)NULL); - if (!from || match(from->name, sender)) - from = find_server(sender, (aClient *)NULL); - else if (!from && index(sender, '@')) - from = find_nickserv(sender, (aClient *)NULL); - - para[0] = sender; + if (nsprefix) + { + from = (aClient *) find_server_by_base64(sender); + if (from) + para[0] = from->name; + } + else + { + from = find_client(sender, (aClient *)NULL); + if (!from || match(from->name, sender)) + from = find_server(sender, (aClient *)NULL); + else if (!from && index(sender, '@')) + from = find_nickserv(sender, (aClient *)NULL); + para[0] = sender; + } /* Hmm! If the client corresponding to the * prefix is not found--what is the correct @@ -694,7 +690,7 @@ static void remove_unknown(cptr, sender) * Do kill if it came from a server because it means there is a ghost * user on the other server which needs to be removed. -avalon */ - if (!index(sender, '.')) + if (!index(sender, '.') && !nsprefix) sendto_one(cptr, ":%s KILL %s :%s (%s(?) <- %s)", me.name, sender, me.name, sender, get_client_name(cptr, FALSE)); diff --git a/src/s_bsd.c b/src/s_bsd.c index d2760552f..144e71a4e 100644 --- a/src/s_bsd.c +++ b/src/s_bsd.c @@ -964,8 +964,9 @@ static int completed_connection(cptr) return -1; } sendto_one(cptr, "PROTOCTL %s", PROTOCTL_SERVER); - sendto_one(cptr, "SERVER %s 1 :U%d-%s %s", - my_name_for_link(me.name, aconf), UnrealProtocol, serveropts,me.info); + sendto_one(cptr, "SERVER %s 1 :U%d-%s-%i %s", + my_name_for_link(me.name, aconf), UnrealProtocol, serveropts, me.serv->numeric, + me.info); if (!IsDead(cptr)) start_auth(cptr); diff --git a/src/s_serv.c b/src/s_serv.c index c2ffae93e..305152f33 100644 --- a/src/s_serv.c +++ b/src/s_serv.c @@ -201,33 +201,47 @@ int m_squit(cptr, sptr, parc, parv) if (parc > 1) { - server = parv[1]; - /* - ** To accomodate host masking, a squit for a masked server - ** name is expanded if the incoming mask is the same as - ** the server name for that link to the name of link. - */ - while ((*server == '*') && IsServer(cptr)) + if (!(*parv[1] == '@')) { - aconf = cptr->serv->nline; - if (!aconf) - break; - if (!mycmp(server, my_name_for_link(me.name, aconf))) - server = cptr->name; - break; /* WARNING is normal here */ + server = parv[1]; + /* + ** To accomodate host masking, a squit for a masked server + ** name is expanded if the incoming mask is the same as + ** the server name for that link to the name of link. + */ + while ((*server == '*') && IsServer(cptr)) + { + aconf = cptr->serv->nline; + if (!aconf) + break; + if (!mycmp(server, my_name_for_link(me.name, aconf))) + server = cptr->name; + break; /* WARNING is normal here */ + } + + /* + ** The following allows wild cards in SQUIT. Only usefull + ** when the command is issued by an oper. + */ + for (acptr = client; (acptr = next_client(acptr, server)); + acptr = acptr->next) + if (IsServer(acptr) || IsMe(acptr)) + break; + if (acptr && IsMe(acptr)) + { + acptr = cptr; + server = cptr->sockhost; + } } - /* - ** The following allows wild cards in SQUIT. Only usefull - ** when the command is issued by an oper. - */ - for (acptr = client; (acptr = next_client(acptr, server)); - acptr = acptr->next) - if (IsServer(acptr) || IsMe(acptr)) - break; - if (acptr && IsMe(acptr)) + else { - acptr = cptr; - server = cptr->sockhost; + server = parv[1]; + acptr = (aClient *) find_server_by_base64(server + 1); + if (acptr && IsMe(acptr)) + { + acptr = cptr; + server = cptr->sockhost; + } } } else @@ -546,6 +560,7 @@ int m_protoctl(cptr, sptr, parc, parv) return 0; } +char *num = NULL; /* ** m_server @@ -567,7 +582,7 @@ int m_server(cptr, sptr, parc, parv) aConfItem *aconf, *cconf; int hop, numeric = 0; int ts = 0; - char *flags, *protocol, *inf; + char *flags = NULL, *protocol = NULL, *inf = NULL; info[0] = '\0'; inpath = get_client_name(cptr, FALSE); @@ -843,16 +858,23 @@ int m_server(cptr, sptr, parc, parv) if (match(my_name_for_link(me.name, aconf), acptr->name) == 0) continue; - if (numeric && SupportNS(bcptr)) - sendto_one(bcptr, ":%s %s %s %d %d :%s", - parv[0], - IsToken(bcptr) ? TOK_SERVER : MSG_SERVER, - acptr->name, hop + 1, numeric, acptr->info); - else + + if (SupportNS(bcptr)) + { + sendto_one(bcptr, + "%c%s %s %s %d %i :%s", + (sptr->serv->numeric ? '@' : ':'), + (sptr->serv->numeric ? base64enc(sptr->serv->numeric) : sptr->name), + IsToken(bcptr) ? TOK_SERVER : MSG_SERVER, + acptr->name, hop + 1, numeric, acptr->info); + } + else + { sendto_one(bcptr, ":%s %s %s %d :%s", parv[0], IsToken(bcptr) ? TOK_SERVER : MSG_SERVER, acptr->name, hop + 1, acptr->info); + } } return 0; } @@ -875,11 +897,13 @@ int m_server(cptr, sptr, parc, parv) inf = NULL; protocol = NULL; flags = NULL; - + num = NULL; protocol = (char *)strtok((char *)info, "-"); if (protocol) - flags = (char *)strtok((char *)NULL, " "); + flags = (char *)strtok((char *)NULL, "-"); if (flags) + num = (char *)strtok((char *)NULL, " "); + if (num) inf = (char *)strtok((char *)NULL, ""); if (inf) { @@ -1030,6 +1054,7 @@ int m_server_estab(cptr) char *inpath, *host, *s, *encr; int split, i; extern char serveropts[]; + unsigned long numeric; inpath = get_client_name(cptr, TRUE); /* "refresh" inpath with host */ split = mycmp(cptr->name, cptr->sockhost); @@ -1101,9 +1126,9 @@ int m_server_estab(cptr) ** Pass my info to the new server */ /* modified so we send out the Uproto and flags */ - sendto_one(cptr, "SERVER %s 1 :U%d-%s %s", + sendto_one(cptr, "SERVER %s 1 :U%d-%s-%i %s", my_name_for_link(me.name, aconf), UnrealProtocol, - serveropts, (me.info[0]) ? (me.info) : "IRCers United"); + serveropts, me.serv->numeric, (me.info[0]) ? (me.info) : "IRCers United"); } else { @@ -1162,8 +1187,12 @@ int m_server_estab(cptr) cptr->serv->up = me.name; cptr->srvptr = &me; cptr->serv->nline = aconf; + if (num) + { + cptr->serv->numeric = atoi(num); + num = NULL; + } add_server_to_table(cptr); - /* ** Old sendto_serv_but_one() call removed because we now ** need to send different names to different servers @@ -1177,16 +1206,23 @@ int m_server_estab(cptr) if ((aconf = acptr->serv->nline) && !match(my_name_for_link(me.name, aconf), cptr->name)) continue; - if (cptr->serv->numeric && SupportNS(acptr)) - sendto_one(acptr, ":%s %s %s 2 %i :%s", - me.name, - (IsToken(acptr) ? TOK_SERVER : MSG_SERVER), - cptr->name, cptr->serv->numeric, cptr->info); - else + + if (SupportNS(acptr)) + { + sendto_one(acptr, "%c%s %s %s 2 %i :%s", + (me.serv->numeric ? '@' : ':'), + (me.serv->numeric ? base64enc(me.serv->numeric) : me.name), + (IsToken(acptr) ? TOK_SERVER : MSG_SERVER), + cptr->name, cptr->serv->numeric, + cptr->info); + } + else + { sendto_one(acptr, ":%s %s %s 2 :%s", - me.name, - (IsToken(cptr) ? TOK_SERVER : MSG_SERVER), - cptr->name, cptr->info); + me.name, + (IsToken(acptr) ? TOK_SERVER : MSG_SERVER), + cptr->name, cptr->info); + } } /* @@ -1221,12 +1257,19 @@ int m_server_estab(cptr) continue; split = (MyConnect(acptr) && mycmp(acptr->name, acptr->sockhost)); - if (acptr->serv->numeric && SupportNS(cptr)) - sendto_one(cptr, ":%s %s %s %d %i :%s", - acptr->serv->up, - (IsToken(cptr) ? TOK_SERVER : MSG_SERVER), - acptr->name, acptr->hopcount + 1, - acptr->serv->numeric, acptr->info); + + if (SupportNS(cptr)) + { + /* this has to work. */ + numeric = ((aClient *) find_server_quick(acptr->serv->up))->serv->numeric; + + sendto_one(cptr, "%c%s %s %s %d %i :%s", + (numeric ? '@' : ':'), + (numeric ? base64enc(numeric) : acptr->serv->up), + IsToken(cptr) ? TOK_SERVER : MSG_SERVER, + acptr->name, acptr->hopcount + 1, + acptr->serv->numeric, acptr->name); + } else sendto_one(cptr, ":%s %s %s %d :%s", acptr->serv->up, diff --git a/src/s_user.c b/src/s_user.c index 59b515848..bc29da791 100644 --- a/src/s_user.c +++ b/src/s_user.c @@ -1,4 +1,3 @@ -/* /* * Unreal Internet Relay Chat Daemon, src/s_user.c * Copyright (C) 1990 Jarkko Oikarinen and @@ -67,7 +66,7 @@ int sendanyways = 0; int dontspread = 0; extern char *me_hash; extern ircstats IRCstats; - +extern char backupbuf[]; static char buf[BUFSIZE], buf2[BUFSIZE]; static int user_modes[] = { UMODE_OPER, 'o', UMODE_LOCOP, 'O', @@ -893,7 +892,7 @@ static int register_user(cptr, sptr, nick, username, umode, virthost) { aClient *acptr; - if (!(acptr = find_server(user->server, NULL))) + if (!(acptr = (aClient *) find_server_quick(user->server, NULL))) { sendto_ops ("Bad USER [%s] :%s USER %s %s : No such server", @@ -1131,10 +1130,12 @@ int m_nick(cptr, sptr, parc, parv) ** -- Aeto */ if (IsServer(cptr) && - (parc > 7 && (!(serv = (aClient *)find_server(parv[6], NULL)) || + (parc > 7 && (!(serv = (aClient *)find_server_b64_or_real(parv[6], NULL)) || serv->from != cptr->from))) + { + sendto_ops("Cannot find server (%s)", backupbuf); return 0; - + } /* ** Check against nick name collisions. ** @@ -2796,6 +2797,7 @@ int m_user(cptr, sptr, parc, parv) NULL; u_int32_t sstamp = 0; anUser *user; + aClient *acptr; char *mparv[] = { sptr->name, sptr->name, NULL }; if (IsServer(cptr) && !IsUnknown(sptr)) @@ -2849,7 +2851,16 @@ int m_user(cptr, sptr, parc, parv) if (sptr->srvptr == NULL) sendto_ops("WARNING, User %s introduced as being " "on non-existant server %s.", sptr->name, server); - user->server = find_or_add(server); + if (SupportNS(cptr)) + { + acptr = (aClient *) find_server_b64_or_real(server); + if (acptr) + user->server = find_or_add(acptr->name); + else + user->server = find_or_add(server); + } + else + user->server = find_or_add(server); strncpyzt(user->realhost, host, sizeof(user->realhost)); goto user_finish; } diff --git a/src/send.c b/src/send.c index cdaa8030b..05c88c6d3 100644 --- a/src/send.c +++ b/src/send.c @@ -1611,7 +1611,8 @@ void sendto_serv_butone_nickcmd(aClient *one, aClient *sptr, "%s %s %d %d %s %s %s %lu %s %s :%s", (IsToken(cptr) ? TOK_NICK : MSG_NICK), nick, hopcount, lastnick, username, realhost, - server, servicestamp, umodes, + SupportNS(cptr) && sptr->srvptr->serv->numeric ? base64enc(sptr->srvptr->serv->numeric) : server, + servicestamp, umodes, (SupportVHP(cptr) ? (IsHidden(sptr) ? sptr->user->virthost : realhost) : virthost), info); }