ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/svn/ircd-hybrid/branches/8.2.x/modules/m_connect.c
Revision: 10180
Committed: Wed Jul 6 15:40:57 2022 UTC (3 years, 1 month ago) by michael
Content type: text/x-csrc
File size: 6998 byte(s)
Log Message:
- m_connect.c:mo_connect(): replace test on `parc` with `EmptyString`

File Contents

# Content
1 /*
2 * ircd-hybrid: an advanced, lightweight Internet Relay Chat Daemon (ircd)
3 *
4 * Copyright (c) 1997-2022 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
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301
19 * USA
20 */
21
22 /*! \file m_connect.c
23 * \brief Includes required functions for processing the CONNECT command.
24 * \version $Id$
25 */
26
27 #include "stdinc.h"
28 #include "client.h"
29 #include "ircd.h"
30 #include "irc_string.h"
31 #include "numeric.h"
32 #include "conf.h"
33 #include "log.h"
34 #include "server.h"
35 #include "send.h"
36 #include "parse.h"
37 #include "hash.h"
38 #include "modules.h"
39
40
41 /*! \brief CONNECT command handler
42 *
43 * \param source_p Pointer to allocated Client struct from which the message
44 * originally comes from. This can be a local or remote client.
45 * \param parc Integer holding the number of supplied arguments.
46 * \param parv Argument vector where parv[0] .. parv[parc-1] are non-NULL
47 * pointers.
48 * \note Valid arguments for this command are:
49 * - parv[0] = command
50 * - parv[1] = target server
51 * - parv[2] = unused/ignored
52 * - parv[3] = nickname/servername
53 */
54 static void
55 mo_connect(struct Client *source_p, int parc, char *parv[])
56 {
57 const char *const name = parv[1];
58
59 if (!EmptyString(parv[3]))
60 {
61 if (!HasOFlag(source_p, OPER_FLAG_CONNECT_REMOTE))
62 {
63 sendto_one_numeric(source_p, &me, ERR_NOPRIVS, "connect:remote");
64 return;
65 }
66
67 if (server_hunt(source_p, ":%s CONNECT %s %s :%s", 3, parv)->ret != HUNTED_ISME)
68 return;
69 }
70
71 if (!HasOFlag(source_p, OPER_FLAG_CONNECT))
72 {
73 sendto_one_numeric(source_p, &me, ERR_NOPRIVS, "connect");
74 return;
75 }
76
77 /*
78 * Try to find the name. If it fails, notify and bail.
79 */
80 struct MaskItem *conf = connect_find(name, match);
81 if (conf == NULL)
82 {
83 sendto_one_notice(source_p, &me, ":Connect: Server %s not listed in configuration file", name);
84 return;
85 }
86
87 const struct Client *target_p = hash_find_server(conf->name);
88 if (target_p)
89 {
90 sendto_one_notice(source_p, &me, ":Connect: Server %s already exists from %s",
91 target_p->name, target_p->from->name);
92 return;
93 }
94
95 if (find_servconn_in_progress(conf->name))
96 {
97 sendto_one_notice(source_p, &me, ":Connect: a connection to %s is already in progress",
98 conf->name);
99 return;
100 }
101
102 ilog(LOG_TYPE_IRCD, "CONNECT %s %u from %s",
103 name, conf->port, get_oper_name(source_p));
104
105 /*
106 * At this point we should be calling connect_server with a valid
107 * connect{} block and a valid port in the connect{} block
108 */
109 if (server_connect(conf, source_p) == true)
110 {
111 if (ConfigServerHide.hide_server_ips == 0 && HasUMode(source_p, UMODE_ADMIN))
112 sendto_one_notice(source_p, &me, ":*** Connecting to %s[%s].%u",
113 conf->name, conf->host, conf->port);
114 else
115 sendto_one_notice(source_p, &me, ":*** Connecting to %s.%u",
116 conf->name, conf->port);
117 }
118 else
119 sendto_one_notice(source_p, &me, ":*** Couldn't connect to %s.%u",
120 conf->name, conf->port);
121
122 /*
123 * Client is either connecting with all the data it needs or has been
124 * destroyed
125 */
126 }
127
128 /*! \brief CONNECT command handler
129 *
130 * \param source_p Pointer to allocated Client struct from which the message
131 * originally comes from. This can be a local or remote client.
132 * \param parc Integer holding the number of supplied arguments.
133 * \param parv Argument vector where parv[0] .. parv[parc-1] are non-NULL
134 * pointers.
135 * \note Valid arguments for this command are:
136 * - parv[0] = command
137 * - parv[1] = target server
138 * - parv[2] = unused/ignored
139 * - parv[3] = nickname/servername
140 */
141 static void
142 ms_connect(struct Client *source_p, int parc, char *parv[])
143 {
144 const char *const name = parv[1];
145
146 if (server_hunt(source_p, ":%s CONNECT %s %s :%s", 3, parv)->ret != HUNTED_ISME)
147 return;
148
149 /*
150 * Try to find the name. If it fails, notify and bail.
151 */
152 struct MaskItem *conf = connect_find(name, match);
153 if (conf == NULL)
154 {
155 sendto_one_notice(source_p, &me, ":Connect: Server %s not listed in configuration file", name);
156 return;
157 }
158
159 const struct Client *target_p = hash_find_server(conf->name);
160 if (target_p)
161 {
162 sendto_one_notice(source_p, &me, ":Connect: Server %s already exists from %s",
163 target_p->name, target_p->from->name);
164 return;
165 }
166
167 if (find_servconn_in_progress(conf->name))
168 {
169 sendto_one_notice(source_p, &me, ":Connect: a connection to %s is already in progress",
170 conf->name);
171 return;
172 }
173
174 /*
175 * Notify all operators about remote connect requests
176 */
177 sendto_realops_flags(UMODE_SERVNOTICE, L_ALL, SEND_GLOBAL, "from %s: Remote CONNECT %s %u from %s",
178 me.name, name, conf->port, get_oper_name(source_p));
179 sendto_server(NULL, 0, 0, ":%s GLOBOPS :Remote CONNECT %s %u from %s",
180 me.id, name, conf->port, get_oper_name(source_p));
181
182 ilog(LOG_TYPE_IRCD, "Remote CONNECT %s %u from %s",
183 name, conf->port, get_oper_name(source_p));
184
185 /*
186 * At this point we should be calling connect_server with a valid
187 * connect{} block and a valid port in the connect{} block
188 */
189 if (server_connect(conf, source_p) == true)
190 sendto_one_notice(source_p, &me, ":*** Connecting to %s.%u",
191 conf->name, conf->port);
192 else
193 sendto_one_notice(source_p, &me, ":*** Couldn't connect to %s.%u",
194 conf->name, conf->port);
195
196 /*
197 * Client is either connecting with all the data it needs or has been
198 * destroyed
199 */
200 }
201
202 static struct Message connect_msgtab =
203 {
204 .cmd = "CONNECT",
205 .handlers[UNREGISTERED_HANDLER] = { .handler = m_unregistered },
206 .handlers[CLIENT_HANDLER] = { .handler = m_not_oper },
207 .handlers[SERVER_HANDLER] = { .handler = ms_connect, .args_min = 4 },
208 .handlers[ENCAP_HANDLER] = { .handler = m_ignore },
209 .handlers[OPER_HANDLER] = { .handler = mo_connect, .args_min = 2 }
210 };
211
212 static void
213 module_init(void)
214 {
215 mod_add_cmd(&connect_msgtab);
216 }
217
218 static void
219 module_exit(void)
220 {
221 mod_del_cmd(&connect_msgtab);
222 }
223
224 struct module module_entry =
225 {
226 .version = "$Revision$",
227 .modinit = module_init,
228 .modexit = module_exit,
229 };

Properties

Name Value
svn:eol-style native
svn:keywords Id Revision