ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/ermyth/modules/global/main.C
Revision: 1.9
Committed: Sat Sep 22 14:27:27 2007 UTC (16 years, 8 months ago) by pippijn
Content type: text/plain
Branch: MAIN
CVS Tags: HEAD
Changes since 1.8: +3 -3 lines
Log Message:
split up ermyth into ermyth-modules, libermyth (currently just ermyth-util) and ermyth-core

File Contents

# Content
1 /**
2 * main.C: This file contains the main() routine.
3 *
4 * Copyright © 2007 Pippijn van Steenhoven / The Ermyth Team
5 * Rights to this code are as documented in COPYING.
6 *
7 *
8 * Portions of this file were derived from sources bearing the following license:
9 * Copyright © 2005 Atheme Development Group
10 * Rights to this code are documented in doc/pod/license.pod.
11 *
12 * $Id: main.C,v 1.8 2007-09-16 18:54:43 pippijn Exp $
13 */
14
15 #include "atheme.h"
16 #include "confparse.h"
17 #include <ermyth/module.h>
18 #include "uplink.h" /* XXX direct use of protocol_handler::notice_global_sts () */
19
20 static char const rcsid[] = "$Id: main.C,v 1.8 2007-09-16 18:54:43 pippijn Exp $";
21
22 REGISTER_MODULE ("global/main", false, "The Ermyth Team <http://ermyth.xinutec.org>");
23
24 static void on_config_ready (void);
25
26 cmdvec g_cmdtree;
27 E cmdvec os_cmdtree;
28 helpvec g_helptree;
29 E helpvec os_helptree;
30
31 static void g_cmd_global (sourceinfo_t *si, const int parc, char *parv[]);
32 static void g_cmd_help (sourceinfo_t *si, const int parc, char *parv[]);
33
34 command_t const g_help = { "HELP", N_("Displays contextual help information."), PRIV_GLOBAL, 1, g_cmd_help };
35 command_t const g_global = { "GLOBAL", N_("Sends a global notice."), PRIV_GLOBAL, 1, g_cmd_global };
36
37 /* HELP <command> [params] */
38 static void
39 g_cmd_help (sourceinfo_t *si, const int parc, char *parv[])
40 {
41 char *command = parv[0];
42
43 if (!command)
44 {
45 command_help (si, g_cmdtree);
46 command_success_nodata (si, "For more specific help use \2HELP \37command\37\2.");
47
48 return;
49 }
50
51 /* take the command through the hash table */
52 help_display (si, command, g_helptree);
53 }
54
55 /* GLOBAL <parameters>|SEND|CLEAR */
56 static void
57 g_cmd_global (sourceinfo_t *si, const int parc, char *parv[])
58 {
59 char *message;
60 static list_t globlist;
61 node_t *n, *tn;
62 char *params = parv[0];
63 static char *sender = NULL;
64 bool isfirst;
65 char buf[BUFSIZE];
66
67 if (!params)
68 {
69 command_fail (si, fault::needmoreparams, STR_INSUFFICIENT_PARAMS, "GLOBAL");
70 command_fail (si, fault::needmoreparams, _("Syntax: GLOBAL <parameters>|SEND|CLEAR"));
71 return;
72 }
73
74 if (!strcasecmp ("CLEAR", params))
75 {
76 if (!globlist.count)
77 {
78 command_fail (si, fault::nochange, _("No message to clear."));
79 return;
80 }
81
82 /* destroy the list we made */
83 LIST_FOREACH_SAFE (n, tn, globlist.head)
84 {
85 message = static_cast<char *> (n->data);
86 node_del (n, &globlist);
87 node_free (n);
88 sfree (message);
89 }
90
91 sfree (sender);
92 sender = NULL;
93
94 command_success_nodata (si, "The pending message has been deleted.");
95
96 return;
97 }
98
99 if (!strcasecmp ("SEND", params))
100 {
101 if (!globlist.count)
102 {
103 command_fail (si, fault::nosuch_target, _("No message to send."));
104 return;
105 }
106
107 isfirst = true;
108 LIST_FOREACH (n, globlist.head)
109 {
110 message = static_cast<char *> (n->data);
111
112 snprintf (buf, sizeof buf, "[Network Notice] %s%s%s", isfirst ? si->su->nick : "", isfirst ? " - " : "", message);
113 /* Cannot use si->service->me here, global notices
114 * should come from global even if /os global was
115 * used. */
116 phandler->notice_global_sts (globsvs.me->me, "*", buf);
117 isfirst = false;
118 /* log everything */
119 logcommand (si, CMDLOG_ADMIN, "GLOBAL %s", message);
120 }
121 logcommand (si, CMDLOG_ADMIN, "GLOBAL (%d lines sent)", LIST_LENGTH (&globlist));
122
123 /* destroy the list we made */
124 LIST_FOREACH_SAFE (n, tn, globlist.head)
125 {
126 message = static_cast<char *> (n->data);
127 node_del (n, &globlist);
128 node_free (n);
129 sfree (message);
130 }
131
132 sfree (sender);
133 sender = NULL;
134
135 snoop ("GLOBAL: \2%s\2", get_oper_name (si));
136
137 command_success_nodata (si, "The global notice has been sent.");
138
139 return;
140 }
141
142 if (!sender)
143 sender = sstrdup (si->su->nick);
144
145 if (irccasecmp (sender, si->su->nick))
146 {
147 command_fail (si, fault::noprivs, _("There is already a GLOBAL in progress by \2%s\2."), sender);
148 return;
149 }
150
151 message = sstrdup (params);
152
153 n = node_create ();
154 node_add (message, n, &globlist);
155
156 command_success_nodata (si, "Stored text to be sent as line %d. Use \2GLOBAL SEND\2 "
157 "to send message, \2GLOBAL CLEAR\2 to delete the pending message, "
158 "or \2GLOBAL\2 to store additional lines.", globlist.count);
159 }
160
161 /* main services client routine */
162 static void
163 global (sourceinfo_t *si, int parc, char *parv[])
164 {
165 char orig[BUFSIZE];
166 char *cmd;
167 char *text;
168
169 /* this should never happen */
170 if (parv[0][0] == '&')
171 {
172 slog (LG_ERROR, "services(): got parv with local channel: %s", parv[0]);
173 return;
174 }
175
176 /* make a copy of the original for debugging */
177 strlcpy (orig, parv[parc - 1], BUFSIZE);
178
179 /* lets go through this to get the command */
180 cmd = strtok (parv[parc - 1], " ");
181 text = strtok (NULL, "");
182
183 if (!cmd)
184 return;
185 if (*cmd == '\001')
186 {
187 handle_ctcp_common (si, cmd, text);
188 return;
189 }
190
191 command_exec_split (si->service, si, cmd, text, g_cmdtree);
192 }
193
194 static void
195 on_config_ready (void)
196 {
197 if (globsvs.me)
198 del_service (globsvs.me);
199
200 globsvs.me = add_service (globsvs.nick, globsvs.user, globsvs.host, globsvs.real, global, g_cmdtree);
201 globsvs.disp = globsvs.me->disp;
202 }
203
204 bool
205 _modinit (module *m)
206 {
207 ConfTable::callback.ready.attach (on_config_ready);
208
209 if (!cold_start)
210 {
211 globsvs.me = add_service (globsvs.nick, globsvs.user, globsvs.host, globsvs.real, global, g_cmdtree);
212 globsvs.disp = globsvs.me->disp;
213 }
214
215 g_cmdtree << g_global;
216 os_cmdtree << g_global;
217
218 help_addentry (os_helptree, "GLOBAL", "help/global/global", NULL);
219 help_addentry (g_helptree, "HELP", "help/global/help", NULL);
220 help_addentry (g_helptree, "GLOBAL", "help/global/global", NULL);
221
222 g_cmdtree << g_help;
223
224 return true;
225 }
226
227 void
228 _moddeinit ()
229 {
230 if (globsvs.me)
231 {
232 del_service (globsvs.me);
233 globsvs.me = NULL;
234 }
235
236 g_cmdtree >> g_global;
237 os_cmdtree >> g_global;
238
239 help_delentry (os_helptree, "GLOBAL");
240
241 help_delentry (g_helptree, "GLOBAL");
242 help_delentry (g_helptree, "HELP");
243
244 g_cmdtree >> g_help;
245
246 ConfTable::callback.ready.detach (on_config_ready);
247 }