ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/cvsroot/ermyth/src/uplink.C
Revision: 1.7
Committed: Sun Sep 9 20:05:53 2007 UTC (19 years, 1 month ago) by pippijn
Content type: text/plain
Branch: MAIN
Changes since 1.6: +2 -1 lines
Log Message:
- changed configurations to the c++ stdlib
- more #defines to enum
- removed getopt.h and link.h from the system as they were unused
- reworked logstreams
- added an itoa with old syntax
- made klines objects
- moved some global variables into appropriate classes
- fixed boost.foreach's compiler workaround #if's
- allow other files to add exceptions with ADD_EXCEPTION
- changed mynick_t to c++ object
- moved servers.h out of atheme.h
- corrected PING from inspircd 1.2

File Contents

# User Rev Content
1 pippijn 1.1 /*
2     * uplink.C: Uplink management.
3 pippijn 1.2 * Rights to this code are documented in doc/pod/license.pod.
4 pippijn 1.1 *
5 pippijn 1.4 * Copyright © 2005-2007 Atheme Project (http://www.atheme.org)
6 pippijn 1.1 */
7    
8 pippijn 1.7 static char const rcsid[] = "$Id: uplink.C,v 1.6 2007-08-30 19:56:26 pippijn Exp $";
9 pippijn 1.5
10     #include <boost/foreach.hpp>
11 pippijn 1.1
12     #include "atheme.h"
13 pippijn 1.7 #include "servers.h"
14 pippijn 1.1 #include "datastream.h"
15     #include "uplink.h"
16 pippijn 1.6 #include "connection.h"
17 pippijn 1.1
18     list_t uplinks;
19     uplink_t *curr_uplink;
20    
21     static void uplink_close (connection_t *cptr);
22    
23     void
24     init_uplinks (void)
25     {
26 pippijn 1.4 #if 0
27 pippijn 1.1 uplink_heap = BlockHeapCreate (sizeof (uplink_t), 4);
28 pippijn 1.4 #endif
29 pippijn 1.1 }
30    
31     uplink_t *
32     uplink_add (char *name, char *host, char *password, char *vhost, int port)
33     {
34     uplink_t *u;
35     node_t *n;
36    
37     slog (LG_DEBUG, "uplink_add(): %s -> %s:%d", me.name, name, port);
38    
39     if ((u = uplink_find (name)))
40     {
41     if (u->flags & UPF_ILLEGAL)
42     {
43     u->flags &= ~UPF_ILLEGAL;
44 pippijn 1.4 sfree (u->name);
45     sfree (u->host);
46     sfree (u->pass);
47     sfree (u->vhost);
48 pippijn 1.1 }
49     else
50     {
51     slog (LG_INFO, "Duplicate uplink %s.", name);
52     return NULL;
53     }
54     }
55     else
56     {
57 pippijn 1.4 u = new uplink_t;
58 pippijn 1.1 n = node_create ();
59     u->node = n;
60     node_add (u, n, &uplinks);
61     cnt.uplink++;
62     }
63    
64     u->name = sstrdup (name);
65     u->host = sstrdup (host);
66     u->pass = sstrdup (password);
67     if (vhost)
68     u->vhost = sstrdup (vhost);
69     else
70     u->vhost = sstrdup ("0.0.0.0");
71     u->port = port;
72    
73     return u;
74     }
75    
76     void
77     uplink_delete (uplink_t *u)
78     {
79     node_t *n = node_find (u, &uplinks);
80    
81 pippijn 1.4 sfree (u->name);
82     sfree (u->host);
83     sfree (u->pass);
84     sfree (u->vhost);
85 pippijn 1.1
86     node_del (n, &uplinks);
87     node_free (n);
88    
89 pippijn 1.4 delete u;
90 pippijn 1.1 cnt.uplink--;
91     }
92    
93     uplink_t *
94     uplink_find (char *name)
95     {
96     node_t *n;
97    
98     LIST_FOREACH (n, uplinks.head)
99     {
100     uplink_t *u = static_cast<uplink_t *> (n->data);
101    
102     if (!strcasecmp (u->name, name))
103     return u;
104     }
105    
106     return NULL;
107     }
108    
109     void
110     uplink_connect (void)
111     {
112     uplink_t *u;
113    
114     if (curr_uplink == NULL)
115     {
116     if (uplinks.head == NULL)
117     {
118     slog (LG_ERROR, "uplink_connect(): no uplinks configured, exiting. Make sure to have at least one uplink{} block in your configuration file.");
119     exit (EXIT_FAILURE);
120     }
121     curr_uplink = static_cast<uplink_t *> (uplinks.head->data);
122     slog (LG_INFO, "uplink_connect(): connecting to first entry %s[%s]:%d.", curr_uplink->name, curr_uplink->host, curr_uplink->port);
123     }
124     else if (curr_uplink->node->next)
125     {
126     u = static_cast<uplink_t *> (curr_uplink->node->next->data);
127    
128     curr_uplink = u;
129     slog (LG_INFO, "uplink_connect(): trying alternate uplink %s[%s]:%d", curr_uplink->name, curr_uplink->host, curr_uplink->port);
130     }
131     else
132     {
133     curr_uplink = static_cast<uplink_t *> (uplinks.head->data);
134     slog (LG_INFO, "uplink_connect(): trying again first entry %s[%s]:%d", curr_uplink->name, curr_uplink->host, curr_uplink->port);
135     }
136    
137     u = curr_uplink;
138    
139 pippijn 1.6 curr_uplink->conn = connection_t::open_tcp (u->host, u->vhost, u->port, recvq_put, sendq_flush);
140 pippijn 1.1 if (curr_uplink->conn != NULL)
141     curr_uplink->conn->close_handler = uplink_close;
142     else
143     event_add_once ("reconn", reconn, NULL, me.recontime);
144     }
145    
146     /*
147     * uplink_close()
148     *
149     * inputs:
150     * connection pointer of current uplink
151     * triggered by callback close_handler
152     *
153     * outputs:
154     * none
155     *
156     * side effects:
157     * reconnection is scheduled
158     * uplink marked dead
159     * uplink deleted if it had been removed from configuration
160     */
161     static void
162     uplink_close (connection_t *cptr)
163     {
164     event_add_once ("reconn", reconn, NULL, me.recontime);
165    
166     me.connected = false;
167    
168     if (curr_uplink->flags & UPF_ILLEGAL)
169     {
170     slog (LG_INFO, "uplink_close(): %s was removed from configuration, deleting", curr_uplink->name);
171     uplink_delete (curr_uplink);
172     if (uplinks.head == NULL)
173     {
174     slog (LG_ERROR, "uplink_close(): last uplink deleted, exiting.");
175     exit (EXIT_FAILURE);
176     }
177     curr_uplink = static_cast<uplink_t *> (uplinks.head->data);
178     }
179     curr_uplink->conn = NULL;
180    
181     slog (LG_DEBUG, "uplink_close(): ----------------------- clearing -----------------------");
182    
183     /* we have to kill everything.
184     * we do not clear users here because when you delete a server,
185     * it deletes its users
186     */
187     if (me.actual != NULL)
188     server_delete (me.actual);
189     me.actual = NULL;
190     /* remove all the channels left */
191 pippijn 1.5 foreach (channel_pair &cp, chanlist)
192     channel_delete (cp.second);
193 pippijn 1.1 /* this leaves me.me and all users on it (i.e. services) */
194    
195     slog (LG_DEBUG, "uplink_close(): ------------------------- done -------------------------");
196     }