-/*
- * m_rping -- by Run
- *
- * parv[0] = sender (sptr->name thus)
- * if sender is a person: (traveling towards start server)
- * parv[1] = pinged server[mask]
- * parv[2] = start server (current target)
- * parv[3] = optional remark
- * if sender is a server: (traveling towards pinged server)
- * parv[1] = pinged server (current target)
- * parv[2] = original sender (person)
- * parv[3] = start time in s
- * parv[4] = start time in us
- * parv[5] = the optional remark
- */
-int m_rping(aClient *cptr, aClient *sptr, int parc, char *parv[])
-{
- aClient *acptr;
-
- if (!IsPrivileged(sptr))
- return 0;
-
- if (parc < (IsAnOper(sptr) ? (MyConnect(sptr) ? 2 : 3) : 6))
- {
- sendto_one(sptr, err_str(ERR_NEEDMOREPARAMS), me.name, parv[0], "RPING");
- return 0;
- }
- if (MyUser(sptr))
- {
- if (parc == 2)
- parv[parc++] = me.name;
- else if (!(acptr = find_match_server(parv[2])))
- {
- parv[3] = parv[2];
- parv[2] = me.name;
- parc++;
- }
- else
- parv[2] = acptr->name;
- if (parc == 3)
- parv[parc++] = "<No client start time>";
- }
-
- if (IsAnOper(sptr))
- {
- if (hunt_server(1, cptr, sptr, ":%s RPING %s %s :%s", 2, parc, parv) !=
- HUNTED_ISME)
- return 0;
- if (!(acptr = find_match_server(parv[1])) || !IsServer(acptr))
- {
- sendto_one(sptr, err_str(ERR_NOSUCHSERVER), me.name, parv[0], parv[1]);
- return 0;
- }
- if (Protocol(acptr->from) < 10)
- sendto_one(acptr, ":%s RPING %s %s %s :%s",
- me.name, acptr->name, sptr->name, militime(NULL, NULL), parv[3]);
- else
- sendto_one(acptr, ":%s RPING %s %s %s :%s",
- me.name, NumServ(acptr), sptr->name, militime(NULL, NULL), parv[3]);
- }
- else
- {
- if (hunt_server(1, cptr, sptr, ":%s RPING %s %s %s %s :%s", 1, parc, parv)
- != HUNTED_ISME)
- return 0;
- sendto_one(cptr, ":%s RPONG %s %s %s %s :%s", me.name, parv[0],
- parv[2], parv[3], parv[4], parv[5]);
- }
- return 0;
-}
-
-/*
- * m_rpong -- by Run too :)
- *
- * parv[0] = sender prefix
- * parv[1] = from pinged server: start server; from start server: sender
- * parv[2] = from pinged server: sender; from start server: pinged server
- * parv[3] = pingtime in ms
- * parv[4] = client info (for instance start time)
- */
-int m_rpong(aClient *UNUSED(cptr), aClient *sptr, int parc, char *parv[])
-{
- aClient *acptr;
-
- if (!IsServer(sptr))
- return 0;
-
- if (parc < 5)
- {
- sendto_one(sptr, err_str(ERR_NEEDMOREPARAMS), me.name, parv[0], "RPING");
- return 0;
- }
-
- if (!(acptr = FindClient(parv[1])))
- return 0;
-
- if (!IsMe(acptr))
- {
- if (IsServer(acptr) && parc > 5)
- {
- sendto_one(acptr, ":%s RPONG %s %s %s %s :%s",
- parv[0], parv[1], parv[2], parv[3], parv[4], parv[5]);
- return 0;
- }
- }
- else
- {
- parv[1] = parv[2];
- parv[2] = sptr->name;
- parv[0] = me.name;
- parv[3] = militime(parv[3], parv[4]);
- parv[4] = parv[5];
- if (!(acptr = FindUser(parv[1])))
- return 0; /* No bouncing between servers ! */
- }
-
- sendto_one(acptr, ":%s RPONG %s %s %s :%s",
- parv[0], parv[1], parv[2], parv[3], parv[4]);
- return 0;
-}
-
-#if defined(OPER_REHASH) || defined(LOCOP_REHASH)
-/*
- * m_rehash
- */
-int m_rehash(aClient *cptr, aClient *sptr, int parc, char *parv[])
-{
-#ifndef LOCOP_REHASH
- if (!MyUser(sptr) || !IsOper(sptr))
-#else
-#ifdef OPER_REHASH
- if (!MyUser(sptr) || !IsAnOper(sptr))
-#else
- if (!MyUser(sptr) || !IsLocOp(sptr))
-#endif
-#endif
- {
- sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
- return 0;
- }
- sendto_one(sptr, rpl_str(RPL_REHASHING), me.name, parv[0], configfile);
- sendto_ops("%s is rehashing Server config file", parv[0]);
-#ifdef USE_SYSLOG
- syslog(LOG_INFO, "REHASH From %s\n", get_client_name(sptr, FALSE));
-#endif
- return rehash(cptr, (parc > 1) ? ((*parv[1] == 'q') ? 2 : 0) : 0);
-}
-#endif
-
-#if defined(OPER_RESTART) || defined(LOCOP_RESTART)
-/*
- * m_restart
- */
-int m_restart(aClient *UNUSED(cptr), aClient *sptr, int UNUSED(parc),
- char *parv[])
-{
-#ifndef LOCOP_RESTART
- if (!MyUser(sptr) || !IsOper(sptr))
-#else
-#ifdef OPER_RESTART
- if (!MyUser(sptr) || !IsAnOper(sptr))
-#else
- if (!MyUser(sptr) || !IsLocOp(sptr))
-#endif
-#endif
- {
- sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
- return 0;
- }
-#ifdef USE_SYSLOG
- syslog(LOG_WARNING, "Server RESTART by %s\n", get_client_name(sptr, FALSE));
-#endif
- server_reboot();
- return 0;
-}
-#endif
-
-/*
- * m_trace
- *
- * parv[0] = sender prefix
- * parv[1] = nick or servername
- * parv[2] = 'target' servername
- */
-int m_trace(aClient *cptr, aClient *sptr, int parc, char *parv[])
-{
- Reg1 int i;
- Reg2 aClient *acptr;
- aConfClass *cltmp;
- char *tname;
- int doall, link_s[MAXCONNECTIONS], link_u[MAXCONNECTIONS];
- int cnt = 0, wilds, dow;
-
- if (parc < 2 || BadPtr(parv[1]))
- {
- /* just "TRACE" without parameters. Must be from local client */
- parc = 1;
- acptr = &me;
- tname = me.name;
- i = HUNTED_ISME;
- }
- else if (parc < 3 || BadPtr(parv[2]))
- {
- /* No target specified. Make one before propagating. */
- parc = 2;
- tname = parv[1];
- if ((acptr = find_match_server(parv[1])) ||
- ((acptr = FindClient(parv[1])) && !MyUser(acptr)))
- {
- if (IsUser(acptr))
- parv[2] = acptr->user->server->name;
- else
- parv[2] = acptr->name;
- parc = 3;
- parv[3] = NULL;
- if ((i = hunt_server(IsServer(acptr), cptr, sptr,
- ":%s TRACE %s :%s", 2, parc, parv)) == HUNTED_NOSUCH)
- return 0;
- }
- else
- i = HUNTED_ISME;
- }
- else
- {
- /* Got "TRACE <tname> :<target>" */
- parc = 3;
- if (MyUser(sptr) || Protocol(cptr) < 10)
- acptr = find_match_server(parv[2]);
- else
- acptr = FindNServer(parv[2]);
- if ((i = hunt_server(0, cptr, sptr,
- ":%s TRACE %s :%s", 2, parc, parv)) == HUNTED_NOSUCH)
- return 0;
- tname = parv[1];
- }
-
- if (i == HUNTED_PASS)
- {
- if (!acptr)
- acptr = next_client(client, tname);
- else
- acptr = acptr->from;
- sendto_one(sptr, rpl_str(RPL_TRACELINK), me.name, parv[0],
-#ifndef GODMODE
- version, debugmode, tname, acptr ? acptr->from->name : "<No_match>");
-#else /* GODMODE */
- version, debugmode, tname, acptr ? acptr->from->name : "<No_match>",
- (acptr && acptr->from->serv) ? acptr->from->serv->timestamp : 0);
-#endif /* GODMODE */
- return 0;
- }
-
- doall = (parv[1] && (parc > 1)) ? !match(tname, me.name) : TRUE;
- wilds = !parv[1] || strchr(tname, '*') || strchr(tname, '?');
- dow = wilds || doall;
-
- /* Don't give (long) remote listings to lusers */
- if (dow && !MyConnect(sptr) && !IsAnOper(sptr))
- return 0;
-
- for (i = 0; i < MAXCONNECTIONS; i++)
- link_s[i] = 0, link_u[i] = 0;
-
- if (doall)
- {
- for (acptr = client; acptr; acptr = acptr->next)
- if (IsUser(acptr))
- link_u[acptr->from->fd]++;
- else if (IsServer(acptr))
- link_s[acptr->from->fd]++;
- }
-
- /* report all direct connections */
-
- for (i = 0; i <= highest_fd; i++)
- {
- unsigned int conClass;
-
- if (!(acptr = loc_clients[i])) /* Local Connection? */
- continue;
- if (IsInvisible(acptr) && dow && !(MyConnect(sptr) && IsOper(sptr)) &&
- !IsAnOper(acptr) && (acptr != sptr))
- continue;
- if (!doall && wilds && match(tname, acptr->name))
- continue;
- if (!dow && strCasediff(tname, acptr->name))
- continue;
- conClass = get_client_class(acptr);
-
- switch (acptr->status)
- {
- case STAT_CONNECTING:
- sendto_one(sptr, rpl_str(RPL_TRACECONNECTING),
- me.name, parv[0], conClass, acptr->name);
- cnt++;
- break;
- case STAT_HANDSHAKE:
- sendto_one(sptr, rpl_str(RPL_TRACEHANDSHAKE),
- me.name, parv[0], conClass, acptr->name);
- cnt++;
- break;
- case STAT_ME:
- break;
- case STAT_UNKNOWN:
- case STAT_UNKNOWN_USER:
- sendto_one(sptr, rpl_str(RPL_TRACEUNKNOWN),
- me.name, parv[0], conClass, get_client_name(acptr, FALSE));
- cnt++;
- break;
- case STAT_UNKNOWN_SERVER:
- sendto_one(sptr, rpl_str(RPL_TRACEUNKNOWN),
- me.name, parv[0], conClass, acptr->name);
- cnt++;
- break;
- case STAT_USER:
- /* Only opers see users if there is a wildcard
- but anyone can see all the opers. */
- if ((IsAnOper(sptr) && (MyUser(sptr) ||
- !(dow && IsInvisible(acptr)))) || !dow || IsAnOper(acptr))
- {
- if (IsAnOper(acptr))
- sendto_one(sptr, rpl_str(RPL_TRACEOPERATOR),
- me.name, parv[0], conClass, get_client_name(acptr, FALSE), now - acptr->lasttime);
- else
- sendto_one(sptr, rpl_str(RPL_TRACEUSER),
- me.name, parv[0], conClass, get_client_name(acptr, FALSE), now - acptr->lasttime);
- cnt++;
- }
- break;
- /*
- * Connection is a server
- *
- * Serv <class> <nS> <nC> <name> <ConnBy> <last> <age>
- *
- * class Class the server is in
- * nS Number of servers reached via this link
- * nC Number of clients reached via this link
- * name Name of the server linked
- * ConnBy Who established this link
- * last Seconds since we got something from this link
- * age Seconds this link has been alive
- *
- * Additional comments etc...... -Cym-<cym@acrux.net>
- */
-
- case STAT_SERVER:
- if (acptr->serv->user)
- sendto_one(sptr, rpl_str(RPL_TRACESERVER),
- me.name, parv[0], conClass, link_s[i],
- link_u[i], acptr->name, acptr->serv->by,
- acptr->serv->user->username,
- acptr->serv->user->host,
- now - acptr->lasttime, now - acptr->serv->timestamp);
- else
- sendto_one(sptr, rpl_str(RPL_TRACESERVER),
- me.name, parv[0], conClass, link_s[i],
- link_u[i], acptr->name, *(acptr->serv->by) ?
- acptr->serv->by : "*", "*", me.name,
- now - acptr->lasttime, now - acptr->serv->timestamp);
- cnt++;
- break;
- case STAT_LOG:
- sendto_one(sptr, rpl_str(RPL_TRACELOG),
- me.name, parv[0], LOGFILE, acptr->port);
- cnt++;
- break;
- case STAT_PING:
- sendto_one(sptr, rpl_str(RPL_TRACEPING), me.name,
- parv[0], acptr->name, (acptr->acpt) ? acptr->acpt->name : "<null>");
- break;
- default: /* We actually shouldn't come here, -msa */
- sendto_one(sptr, rpl_str(RPL_TRACENEWTYPE), me.name, parv[0], acptr->name);
- cnt++;
- break;
- }
- }
- /*
- * Add these lines to summarize the above which can get rather long
- * and messy when done remotely - Avalon
- */
- if (!IsAnOper(sptr) || !cnt)
- {
- if (!cnt)
- /* let the user have some idea that its at the end of the trace */
- sendto_one(sptr, rpl_str(RPL_TRACESERVER),
- me.name, parv[0], 0, link_s[me.fd],
- link_u[me.fd], "<No_match>", *(me.serv->by) ?
- me.serv->by : "*", "*", me.name, 0, 0);
- return 0;
- }
- for (cltmp = FirstClass(); doall && cltmp; cltmp = NextClass(cltmp))
- if (Links(cltmp) > 0)
- sendto_one(sptr, rpl_str(RPL_TRACECLASS), me.name,
- parv[0], ConClass(cltmp), Links(cltmp));
- return 0;
-}
-
-/*
- * m_close - added by Darren Reed Jul 13 1992.
- */
-int m_close(aClient *cptr, aClient *sptr, int UNUSED(parc), char *parv[])
-{
- Reg1 aClient *acptr;
- Reg2 int i;
- int closed = 0;
-
- if (!MyOper(sptr))
- {
- sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
- return 0;
- }
-
- for (i = highest_fd; i; i--)
- {
- if (!(acptr = loc_clients[i]))
- continue;
- if (!IsUnknown(acptr) && !IsConnecting(acptr) && !IsHandshake(acptr))
- continue;
- sendto_one(sptr, rpl_str(RPL_CLOSING), me.name, parv[0],
- get_client_name(acptr, FALSE), acptr->status);
- exit_client(cptr, acptr, &me, "Oper Closing");
- closed++;
- }
- sendto_one(sptr, rpl_str(RPL_CLOSEEND), me.name, parv[0], closed);
- return 0;
-}
-
-#if defined(OPER_DIE) || defined(LOCOP_DIE)
-/*
- * m_die
- */
-int m_die(aClient *UNUSED(cptr), aClient *sptr, int UNUSED(parc), char *parv[])
-{
- Reg1 aClient *acptr;
- Reg2 int i;
-
-#ifndef LOCOP_DIE
- if (!MyUser(sptr) || !IsOper(sptr))
-#else
-#ifdef OPER_DIE
- if (!MyUser(sptr) || !IsAnOper(sptr))
-#else
- if (!MyUser(sptr) || !IsLocOp(sptr))
-#endif
-#endif
- {
- sendto_one(sptr, err_str(ERR_NOPRIVILEGES), me.name, parv[0]);
- return 0;
- }
-
- for (i = 0; i <= highest_fd; i++)
- {
- if (!(acptr = loc_clients[i]))
- continue;
- if (IsUser(acptr))
- sendto_one(acptr, ":%s NOTICE %s :Server Terminating. %s",
- me.name, acptr->name, get_client_name(sptr, FALSE));
- else if (IsServer(acptr))
- sendto_one(acptr, ":%s ERROR :Terminated by %s",
- me.name, get_client_name(sptr, FALSE));
- }
-#ifdef __cplusplus
- s_die(0);
-#else
- s_die();
-#endif
- return 0;
-}
-#endif
-
-static void add_gline(aClient *sptr, int ip_mask, char *host, char *comment,
- char *user, time_t expire, int local)
-{
- aClient *acptr;
- aGline *agline;
- int fd,gtype=0;
-
-#ifdef BADCHAN
- if(*host=='#' || *host == '&' || *host == '+')
- gtype=1; /* BAD CHANNEL */
-#endif
- /* Inform ops */
- sendto_op_mask(SNO_GLINE,
- "%s adding %s%s for %s@%s, expiring at " TIME_T_FMT ": %s", sptr->name,
- local ? "local " : "",
- gtype ? "BADCHAN":"GLINE", user, host, expire, comment);
-
-#ifdef GPATH
- write_log(GPATH,
- "# " TIME_T_FMT " %s adding %s %s for %s@%s, expiring at " TIME_T_FMT
- ": %s\n", TStime(), sptr->name, local ? "local" : "global",
- gtype ? "BADCHAN" : "GLINE", user, host, expire, comment);
-
- /* this can be inserted into the conf */
- if(!gtype)
- write_log(GPATH, "%c:%s:%s:%s\n", ip_mask ? 'k' : 'K', host, comment,
- user);
-#endif /* GPATH */
-
- agline = make_gline(ip_mask, host, comment, user, expire);
- if (local)
- SetGlineIsLocal(agline);
-
-#ifdef BADCHAN
- if(gtype) return;
-#endif
-
- for (fd = highest_fd; fd >= 0; --fd) /* get the users! */
- if ((acptr = loc_clients[fd]) && !IsMe(acptr))
- {
-
- if (!acptr->user || strlen(acptr->sockhost) > (size_t)HOSTLEN ||
- (acptr->user->username ? strlen(acptr->user->username) : 0) >
- (size_t)HOSTLEN)
- continue; /* these tests right out of
- find_kill for safety's sake */
-
- if ((GlineIsIpMask(agline) ?
- match(agline->host, inetntoa(acptr->ip)) :
- match(agline->host, acptr->sockhost)) == 0 &&
- (!acptr->user->username ||
- match(agline->name, acptr->user->username) == 0))
- {
-
- /* ok, he was the one that got G-lined */
- sendto_one(acptr, ":%s %d %s :*** %s.", me.name,
- ERR_YOUREBANNEDCREEP, acptr->name, agline->reason);
-
- /* let the ops know about my first kill */
- sendto_op_mask(SNO_GLINE, "G-line active for %s",
- get_client_name(acptr, FALSE));
-
- /* and get rid of him */
- if (sptr != acptr)
- exit_client(sptr->from, acptr, &me, "G-lined");
- }
- }
-}
-
-/*
- * m_gline
- *
- * parv[0] = Send prefix
- *
- * From server:
- *
- * parv[1] = Target: server numeric
- * parv[2] = [+|-]<G-line mask>
- * parv[3] = Expiration offset
- * parv[4] = Comment
- *
- * From client:
- *
- * parv[1] = [+|-]<G-line mask>
- * parv[2] = Expiration offset
- * parv[3] = Comment
- *
- */
-int m_gline(aClient *cptr, aClient *sptr, int parc, char *parv[])
-{
- aClient *acptr = NULL; /* Init. to avoid compiler warning. */
-
- aGline *agline, *a2gline;
- char *user, *host;
- int active, ip_mask,gtype = 0;
- time_t expire = 0;
-
- /* Remove expired G-lines */
- for (agline = gline, a2gline = NULL; agline; agline = agline->next)
- {
- if (agline->expire <= TStime())
- {
- free_gline(agline, a2gline);
- agline = a2gline ? a2gline : gline;
- if (!agline)
- break;
- continue;
- }
- a2gline = agline;
- }
-
-#ifdef BADCHAN
- /* Remove expired bad channels */
- for (agline = badchan, a2gline = NULL; agline; agline = agline->next)
- {
- if (agline->expire <= TStime())
- {
- free_gline(agline, a2gline);
- agline = a2gline ? a2gline : badchan;
- if (!agline)
- break;
- continue;
- }
- a2gline = agline;
- }
-#endif
-
-
- if (IsServer(cptr))
- {
- if (find_conf_host(cptr->confs, sptr->name, CONF_UWORLD))
- {
- if (parc < 3 || (*parv[2] != '-' && (parc < 5 || *parv[4] == '\0')))
- {
- sendto_one(sptr, err_str(ERR_NEEDMOREPARAMS), me.name, parv[0],
- "GLINE");
- return 0;
- }
-
- if (*parv[2] == '-') /* add mode or delete mode? */
- active = 0;
- else
- active = 1;
-
- if (*parv[2] == '+' || *parv[2] == '-')
- parv[2]++; /* step past mode indicator */
-
- /* forward the message appropriately */
- if (!strCasediff(parv[1], "*")) /* global! */
- sendto_serv_butone(cptr, active ? ":%s GLINE %s +%s %s :%s" :
- ":%s GLINE %s -%s", parv[0], parv[1], parv[2], parv[3], parv[4]);
- else if ((
-#if 1
- /*
- * REMOVE THIS after all servers upgraded to 2.10.01 and
- * Uworld uses a numeric too
- */
- (strlen(parv[1]) != 1 && !(acptr = FindClient(parv[1])))) ||
- (strlen(parv[1]) == 1 &&
-#endif
- !(acptr = FindNServer(parv[1]))))
- return 0; /* no such server/user exists; forget it */
- else
-#if 1
-/*
- * REMOVE THIS after all servers upgraded to 2.10.01 and
- * Uworld uses a numeric too
- */
- if (IsServer(acptr) || !MyConnect(acptr))
-#endif
- {
- sendto_one(acptr, active ? ":%s GLINE %s +%s %s :%s" :
- ":%s GLINE %s -%s", parv[0], parv[1], parv[2], parv[3], parv[4]); /* single destination */
- return 0; /* only the intended destination
- should add this gline */
- }
-
- if (!(host = strchr(parv[2], '@')))
- { /* convert user@host */
- user = "*"; /* no @'s; assume username is '*' */
- host = parv[2];
- }
- else
- {
- user = parv[2];
- *(host++) = '\0'; /* break up string at the '@' */
- }
- ip_mask = check_if_ipmask(host); /* Store this boolean */
-#ifdef BADCHAN
- if(*host=='#' || *host == '&' || *host == '+')
- gtype=1; /* BAD CHANNEL GLINE */
-#endif
-
- for (agline = (gtype)?badchan:gline, a2gline = NULL; agline;
- agline = agline->next)
- {
- if (!strCasediff(agline->name, user)
- && !strCasediff(agline->host, host))
- break;
- a2gline = agline;
- }
-
- if (!active && agline)
- { /* removing the gline */
- /* notify opers */
- sendto_op_mask(SNO_GLINE, "%s removing %s for %s@%s", parv[0],
- gtype?"BADCHAN":"GLINE",agline->name, agline->host);
-
-#ifdef GPATH
- write_log(GPATH, "# " TIME_T_FMT " %s removing %s for %s@%s\n",
- TStime(), parv[0], gtype?"BADCHAN":"GLINE",agline->name,
- agline->host);
-#endif /* GPATH */
-
- free_gline(agline, a2gline); /* remove the gline */
- }
- else if (active)
- { /* must be adding a gline */
- expire = atoi(parv[3]) + TStime(); /* expire time? */
- if (agline && agline->expire < expire)
- { /* new expire time? */
- /* yes, notify the opers */
- sendto_op_mask(SNO_GLINE,
- "%s resetting expiration time on %s for %s@%s to " TIME_T_FMT,
- parv[0], gtype?"BADCHAN":"GLINE",agline->name, agline->host,
- expire);
-
-#ifdef GPATH
- write_log(GPATH, "# " TIME_T_FMT " %s resetting expiration time "
- "on %s for %s@%s to " TIME_T_FMT "\n",
- TStime(), parv[0], gtype?"BADCHAN":"GLINE",
- agline->name, agline->host, expire);
-#endif /* GPATH */
-
- agline->expire = expire; /* reset the expire time */
- }
- else if (!agline)
- { /* create gline */
- for (agline = gtype?badchan:gline; agline; agline = agline->next)
- if (!mmatch(agline->name, user) &&
- (ip_mask ? GlineIsIpMask(agline) : !GlineIsIpMask(agline)) &&
- !mmatch(agline->host, host))
- return 0; /* found an existing G-line that matches */
-
- /* add the line: */
- add_gline(sptr, ip_mask, host, parv[4], user, expire, 0);
- }
- }
- }
- }
- else if (parc < 2 || *parv[1] == '\0')
- {
- /* Not enough args and a user; list glines */
- for (agline = gline; agline; agline = agline->next)
- sendto_one(cptr, rpl_str(RPL_GLIST), me.name, parv[0],
- agline->name, agline->host, agline->expire, agline->reason,
- GlineIsActive(agline) ? (GlineIsLocal(agline) ? " (local)" : "") :
- " (Inactive)");
- sendto_one(cptr, rpl_str(RPL_ENDOFGLIST), me.name, parv[0]);
- }
- else
- {
- int priv;
-
-#ifdef LOCOP_LGLINE
- priv = IsAnOper(cptr);
-#else
- priv = IsOper(cptr);
-#endif
-
- if (priv)
- { /* non-oper not permitted to change things */
- if (*parv[1] == '-')
- { /* oper wants to deactivate the gline */
- active = 0;
- parv[1]++;
- }
- else if (*parv[1] == '+')
- { /* oper wants to activate inactive gline */
- active = 1;
- parv[1]++;
- }
- else
- active = -1;
-
- if (parc > 2)
- expire = atoi(parv[2]) + TStime(); /* oper wants to reset
- expire TS */
- }
- else
- active = -1;
-
- if (!(host = strchr(parv[1], '@')))
- {
- user = "*"; /* no @'s; assume username is '*' */
- host = parv[1];
- }
- else
- {
- user = parv[1];
- *(host++) = '\0'; /* break up string at the '@' */
- }
- ip_mask = check_if_ipmask(host); /* Store this boolean */
-#ifdef BADCHAN
- if(*host=='#' || *host == '&' || *host == '+')
-#ifndef LOCAL_BADCHAN
- return 0;
-#else
- gtype=1; /* BAD CHANNEL */
-#endif
-#endif
-
- for (agline = gtype?badchan:gline, a2gline = NULL; agline;
- agline = agline->next)
- {
- if (!mmatch(agline->name, user) &&
- (ip_mask ? GlineIsIpMask(agline) : !GlineIsIpMask(agline)) &&
- !mmatch(agline->host, host))
- break;
- a2gline = agline;
- }
-
- if (!agline)
- {
-#ifdef OPER_LGLINE
- if (priv && active && expire > now)
- {
- /* Add local G-line */
- if (parc < 4 || !strchr(parv[3], ' '))
- {
- sendto_one(sptr, err_str(ERR_NEEDMOREPARAMS),
- me.name, parv[0], "GLINE");
- return 0;
- }
- add_gline(sptr, ip_mask, host, parv[3], user, expire, 1);
- }
- else
-#endif
- sendto_one(cptr, err_str(ERR_NOSUCHGLINE), me.name, parv[0], user,
- host);
-
- return 0;
- }
-
- if (expire <= agline->expire)
- expire = 0;
-
- if ((active == -1 ||
- (active ? GlineIsActive(agline) : !GlineIsActive(agline))) &&
- expire == 0)
- {
- /* oper wants a list of one gline only */
- sendto_one(cptr, rpl_str(RPL_GLIST), me.name, parv[0], agline->name,
- agline->host, agline->expire, agline->reason,
- GlineIsActive(agline) ? "" : " (Inactive)");
- sendto_one(cptr, rpl_str(RPL_ENDOFGLIST), me.name, parv[0]);
- return 0;
- }
-
- if (active != -1 &&
- (active ? !GlineIsActive(agline) : GlineIsActive(agline)))
- {
- if (active) /* reset activation on gline */
- SetActive(agline);
-#ifdef OPER_LGLINE
- else if (GlineIsLocal(agline))
- {
- /* Remove local G-line */
- sendto_op_mask(SNO_GLINE, "%s removed local %s for %s@%s",
- parv[0], gtype?"BADCHAN":"GLINE",agline->name, agline->host);
-#ifdef GPATH
- write_log(GPATH, "# " TIME_T_FMT
- " %s!%s@%s removed local %s for %s@%s\n",
- TStime(), parv[0], cptr->user->username, cptr->user->host,
- gtype?"BADCHAN":"GLINE",
- agline->name, agline->host);
-#endif /* GPATH */
- free_gline(agline, a2gline); /* remove the gline */
- return 0;
- }
-#endif
- else
- ClearActive(agline);
- }
- else
- active = -1; /* for later sendto_ops and logging functions */
-
- if (expire)
- agline->expire = expire; /* reset expiration time */
-
- /* inform the operators what's up */
- if (active != -1)
- { /* changing the activation */
- sendto_op_mask(SNO_GLINE, !expire ? "%s %sactivating %s for %s@%s" :
- "%s %sactivating %s for %s@%s and "
- "resetting expiration time to " TIME_T_FMT,
- parv[0], active ? "re" : "de", gtype?"BADCHAN":"GLINE",agline->name,
- agline->host, agline->expire);
-#ifdef GPATH
- write_log(GPATH, !expire ? "# " TIME_T_FMT " %s!%s@%s %sactivating "
- "%s for %s@%s\n" : "# " TIME_T_FMT " %s!%s@%s %sactivating %s "
- "for %s@%s and resetting expiration time to " TIME_T_FMT "\n",
- TStime(), parv[0], cptr->user->username, cptr->user->host,
- active ? "re" : "de", gtype?"BADCHAN":"GLINE",agline->name,
- agline->host, agline->expire);
-#endif /* GPATH */
-
- }
- else if (expire)
- { /* changing only the expiration */
- sendto_op_mask(SNO_GLINE,
- "%s resetting expiration time on %s for %s@%s to " TIME_T_FMT,
- parv[0], gtype?"BADCHAN":"GLINE",agline->name, agline->host,
- agline->expire);
-#ifdef GPATH
- write_log(GPATH, "# " TIME_T_FMT " %s!%s@%s resetting expiration "
- "time on %s for %s@%s to " TIME_T_FMT "\n", TStime(), parv[0],
- cptr->user->username, cptr->user->host,gtype?"BADCHAN":"GLINE",
- agline->name, agline->host, agline->expire);
-#endif /* GPATH */
- }
- }
-
- return 0;
-}