ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/svn/ircd-hybrid/trunk/src/conf_resv.c
(Generate patch)

Comparing:
ircd-hybrid/trunk/src/resv.c (file contents), Revision 1632 by michael, Sun Nov 4 15:37:10 2012 UTC vs.
ircd-hybrid/trunk/src/conf_resv.c (file contents), Revision 7288 by michael, Sun Feb 7 19:55:12 2016 UTC

# Line 1 | Line 1
1   /*
2 < *  ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
3 < *  resv.c: Functions to reserve(jupe) a nick/channel.
2 > *  ircd-hybrid: an advanced, lightweight Internet Relay Chat Daemon (ircd)
3   *
4 < *  Copyright (C) 2001-2002 Hybrid Development Team
4 > *  Copyright (c) 2001-2016 ircd-hybrid development team
5   *
6   *  This program is free software; you can redistribute it and/or modify
7   *  it under the terms of the GNU General Public License as published by
# Line 16 | Line 15
15   *
16   *  You should have received a copy of the GNU General Public License
17   *  along with this program; if not, write to the Free Software
18 < *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307
18 > *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301
19   *  USA
20 < *
21 < *  $Id$
20 > */
21 >
22 > /*! \file conf_resv.c
23 > * \brief Functions to reserve(jupe) a nick/channel.
24 > * \version $Id$
25   */
26  
27   #include "stdinc.h"
28   #include "list.h"
27 #include "ircd.h"
29   #include "send.h"
30 < #include "client.h"  
30 > #include "client.h"
31   #include "memory.h"
32 < #include "numeric.h"
32 < #include "resv.h"
33 < #include "hash.h"
32 > #include "ircd.h"
33   #include "irc_string.h"
34   #include "ircd_defs.h"
35 + #include "misc.h"
36   #include "conf.h"
37 < #include "conf_db.h"
38 <
39 < dlink_list resv_channel_list = { NULL, NULL, 0 };
40 <
37 > #include "conf_resv.h"
38 > #include "hostmask.h"
39  
42 /* create_channel_resv()
43 *
44 * inputs       - name of channel to create resv for
45 *              - reason for resv
46 *              - flag, 1 for from ircd.conf 0 from elsehwere
47 * output       - pointer to struct ResvChannel
48 * side effects -
49 */
50 struct MaskItem *
51 create_channel_resv(char *name, char *reason, int in_conf)
52 {
53  struct MaskItem *conf = NULL;
40  
41 <  if (name == NULL || reason == NULL)
42 <    return NULL;
41 > static dlink_list resv_chan_list;
42 > static dlink_list resv_nick_list;
43  
58  if (hash_find_resv(name))
59    return NULL;
44  
45 <  if (strlen(reason) > REASONLEN)
46 <    reason[REASONLEN] = '\0';
45 > const dlink_list *
46 > resv_chan_get_list(void)
47 > {
48 >  return &resv_chan_list;
49 > }
50  
51 <  conf = conf_make(CONF_CRESV);
51 > const dlink_list *
52 > resv_nick_get_list(void)
53 > {
54 >  return &resv_nick_list;
55 > }
56  
57 <  DupString(conf->name, name);
58 <  DupString(conf->reason, reason);
57 > void
58 > resv_delete(struct ResvItem *resv)
59 > {
60 >  while (resv->exempt_list.head)
61 >  {
62 >    struct ResvExemptItem *exempt = resv->exempt_list.head->data;
63  
64 <  dlinkAdd(conf, &conf->node, &resv_channel_list);
65 <  hash_add_resv(conf);
64 >    dlinkDelete(&exempt->node, &resv->exempt_list);
65 >    xfree(exempt->name);
66 >    xfree(exempt->user);
67 >    xfree(exempt->host);
68 >    xfree(exempt);
69 >  }
70  
71 <  return conf;
71 >  dlinkDelete(&resv->node, resv->list);
72 >  xfree(resv->mask);
73 >  xfree(resv->reason);
74 >  xfree(resv);
75   }
76  
77 < /* create_nick_resv()
77 > /* create_resv()
78   *
79   * inputs       - name of nick to create resv for
80   *              - reason for resv
# Line 80 | Line 82 | create_channel_resv(char *name, char *re
82   * output       - pointer to struct ResvNick
83   * side effects -
84   */
85 < struct MaskItem *
86 < create_nick_resv(char *name, char *reason, int in_conf)
85 > struct ResvItem *
86 > resv_make(const char *mask, const char *reason, const dlink_list *elist)
87   {
88 <  struct MaskItem *conf = NULL;
88 >  dlink_list *list;
89  
90 <  if (name == NULL || reason == NULL)
91 <    return NULL;
90 >  if (IsChanPrefix(*mask))
91 >    list = &resv_chan_list;
92 >  else
93 >    list = &resv_nick_list;
94  
95 <  if (find_matching_name_conf(CONF_NRESV, name, NULL, NULL, 0))
95 >  if (resv_find(mask, irccmp))
96      return NULL;
97  
98 <  if (strlen(reason) > REASONLEN)
99 <    reason[REASONLEN] = '\0';
98 >  struct ResvItem *resv = xcalloc(sizeof(*resv));
99 >  resv->list = list;
100 >  resv->mask = xstrdup(mask);
101 >  resv->reason = xstrndup(reason, IRCD_MIN(strlen(reason), REASONLEN));
102 >  dlinkAdd(resv, &resv->node, resv->list);
103  
104 <  conf = conf_make(CONF_NRESV);
104 >  if (elist)
105 >  {
106 >    dlink_node *node;
107  
108 <  DupString(conf->name, name);
109 <  DupString(conf->reason, reason);
108 >    DLINK_FOREACH(node, elist->head)
109 >    {
110 >      char nick[NICKLEN + 1];
111 >      char user[USERLEN + 1];
112 >      char host[HOSTLEN + 1];
113 >      struct split_nuh_item nuh;
114 >      char *s = node->data;
115 >
116 >      if (strlen(s) == 2 && IsAlpha(*(s + 1) && IsAlpha(*(s + 2))))
117 >      {
118 > #ifdef HAVE_LIBGEOIP
119 >        struct ResvExemptItem *exempt = xcalloc(sizeof(*exempt));
120 >        exempt->name = xstrdup(s);
121 >        exempt->country_id = GeoIP_id_by_code(s);
122 >        dlinkAdd(exempt, &exempt->node, &resv->exempt_list);
123 > #endif
124 >      }
125 >      else
126 >      {
127 >        nuh.nuhmask  = s;
128 >        nuh.nickptr  = nick;
129 >        nuh.userptr  = user;
130 >        nuh.hostptr  = host;
131 >
132 >        nuh.nicksize = sizeof(nick);
133 >        nuh.usersize = sizeof(user);
134 >        nuh.hostsize = sizeof(host);
135 >
136 >        split_nuh(&nuh);
137 >
138 >        struct ResvExemptItem *exempt = xcalloc(sizeof(*exempt));
139 >        exempt->name = xstrdup(nick);
140 >        exempt->user = xstrdup(user);
141 >        exempt->host = xstrdup(host);
142 >        exempt->type = parse_netmask(host, &exempt->addr, &exempt->bits);
143 >        dlinkAdd(exempt, &exempt->node, &resv->exempt_list);
144 >      }
145 >    }
146 >  }
147  
148 <  return conf;
148 >  return resv;
149   }
150  
151 < /* clear_conf_resv()
152 < *
107 < * inputs       - none
108 < * output       - none
109 < * side effects - All resvs are cleared out
110 < */
111 < void
112 < clear_conf_resv(void)
151 > struct ResvItem *
152 > resv_find(const char *name, int (*compare)(const char *, const char *))
153   {
154 <  dlink_node *ptr = NULL, *next_ptr = NULL;
154 >  dlink_node *node = NULL;
155 >  dlink_list *list = NULL;
156  
157 <  DLINK_FOREACH_SAFE(ptr, next_ptr, resv_channel_list.head)
157 >  if (IsChanPrefix(*name))
158 >    list = &resv_chan_list;
159 >  else
160 >    list = &resv_nick_list;
161 >
162 >  DLINK_FOREACH(node, list->head)
163    {
164 <    struct MaskItem *conf = ptr->data;
164 >    struct ResvItem *resv = node->data;
165  
166 <    if (!IsConfDatabase(conf))
167 <      delete_channel_resv(conf);
166 >    if (!compare(resv->mask, name))
167 >      return resv;
168    }
123 }
124
125 /* delete_channel_resv()
126 *
127 * inputs       - pointer to channel resv to delete
128 * output       - none
129 * side effects - given struct ResvChannel * is removed
130 */
131 int
132 delete_channel_resv(struct MaskItem *conf)
133 {
134  hash_del_resv(conf);
135  dlinkDelete(&conf->node, &resv_channel_list);
136  conf_free(conf);
169  
170 <  return 1;
170 >  return NULL;
171   }
172  
173 < /* match_find_resv()
174 < *
143 < * inputs       - pointer to name
144 < * output       - pointer to a struct ResvChannel
145 < * side effects - Finds a reserved channel whose name matches 'name',
146 < *                if can't find one returns NULL.
147 < */
148 < struct MaskItem *
149 < match_find_resv(const char *name)
173 > int
174 > resv_exempt_find(const struct Client *client_p, const struct ResvItem *resv)
175   {
176 <  dlink_node *ptr = NULL;
176 >  const dlink_node *node = NULL;
177  
178 <  if (EmptyString(name))
154 <    return NULL;
155 <
156 <  DLINK_FOREACH(ptr, resv_channel_list.head)
178 >  DLINK_FOREACH(node, resv->exempt_list.head)
179    {
180 <    struct MaskItem *conf = ptr->data;
180 >    const struct ResvExemptItem *exempt = node->data;
181  
182 <    if (match_chan(name, conf->name))
183 <      return conf;
182 >    if (exempt->country_id)
183 >    {
184 >      if (exempt->country_id == client_p->connection->country_id)
185 >        return 1;
186 >    }
187 >    else if (!match(exempt->name, client_p->name) && !match(exempt->user, client_p->username))
188 >    {
189 >      switch (exempt->type)
190 >      {
191 >        case HM_HOST:
192 >          if (!match(exempt->host, client_p->host) || !match(exempt->host, client_p->sockhost))
193 >            return 1;
194 >          break;
195 >        case HM_IPV4:
196 >          if (client_p->connection->aftype == AF_INET)
197 >            if (match_ipv4(&client_p->connection->ip, &exempt->addr, exempt->bits))
198 >              return 1;
199 >          break;
200 >        case HM_IPV6:
201 >          if (client_p->connection->aftype == AF_INET6)
202 >            if (match_ipv6(&client_p->connection->ip, &exempt->addr, exempt->bits))
203 >              return 1;
204 >          break;
205 >        default:
206 >          assert(0);
207 >      }
208 >    }
209    }
210  
211 <  return NULL;
211 >  return 0;
212   }
213  
167 /* report_resv()
168 *
169 * inputs       - pointer to client pointer to report to.
170 * output       - NONE
171 * side effects - report all resvs to client.
172 */
214   void
215 < report_resv(struct Client *source_p)
215 > resv_clear(void)
216   {
217 <  dlink_node *ptr = NULL;
177 <  struct MaskItem *conf = NULL;
217 >  dlink_list *tab[] = { &resv_chan_list, &resv_nick_list, NULL };
218  
219 <  DLINK_FOREACH(ptr, resv_channel_list.head)
219 >  for (dlink_list **list = tab; *list; ++list)
220    {
221 <    conf = ptr->data;
182 <    sendto_one(source_p, form_str(RPL_STATSQLINE),
183 <               me.name, source_p->name,
184 <               conf->hold ? 'q' : 'Q',
185 <               conf->name, conf->reason);
186 <  }
221 >    dlink_node *node = NULL, *node_next = NULL;
222  
223 <  DLINK_FOREACH(ptr, nresv_items.head)
224 <  {
225 <    conf = ptr->data;;
226 <    sendto_one(source_p, form_str(RPL_STATSQLINE),
227 <               me.name, source_p->name,
228 <               conf->hold ? 'q' : 'Q',
229 <               conf->name, conf->reason);
223 >    DLINK_FOREACH_SAFE(node, node_next, (*list)->head)
224 >    {
225 >      struct ResvItem *resv = node->data;
226 >
227 >      if (!resv->in_database)
228 >        resv_delete(resv);
229 >    }
230    }
231   }
232  
233 < /* valid_wild_card_simple()
234 < *
200 < * inputs       - data to check for sufficient non-wildcard characters
201 < * outputs      - 1 if valid, else 0
202 < * side effects - none
203 < */
204 < int
205 < valid_wild_card_simple(const char *data)
233 > void
234 > resv_expire(void)
235   {
236 <  const unsigned char *p = (const unsigned char *)data;
208 <  int nonwild = 0;
236 >  dlink_list *tab[] = { &resv_chan_list, &resv_nick_list, NULL };
237  
238 <  while (*p != '\0')
238 >  for (dlink_list **list = tab; *list; ++list)
239    {
240 <    if ((*p == '\\' && *++p) || (*p && !IsMWildChar(*p)))
213 <      if (++nonwild == ConfigFileEntry.min_nonwildcard_simple)
214 <        return 1;
215 <    if (*p != '\0')
216 <      ++p;
217 <  }
240 >    dlink_node *node = NULL, *node_next = NULL;
241  
242 <  return 0;
242 >    DLINK_FOREACH_SAFE(node, node_next, (*list)->head)
243 >    {
244 >      struct ResvItem *resv = node->data;
245 >
246 >      if (!resv->expire || resv->expire > CurrentTime)
247 >        continue;
248 >
249 >      if (ConfigGeneral.tkline_expire_notices)
250 >        sendto_realops_flags(UMODE_SERVNOTICE, L_ALL, SEND_NOTICE, "Temporary RESV for [%s] expired",
251 >                             resv->mask);
252 >      resv_delete(resv);
253 >    }
254 >  }
255   }

Diff Legend

Removed lines
+ Added lines
< Changed lines (old)
> Changed lines (new)