source: code/cmd.c@ a785c27

Last change on this file since a785c27 was e3a7f9b, checked in by Mike Belopuhov <mike.belopuhov@…>, 15 years ago

drop rcsids

  • Property mode set to 100644
File size: 5.7 KB
RevLine 
[cd7b81d]1/*
2 * Copyright (c) 2009, 2010 Mike Belopuhov
3 *
4 * Permission to use, copy, modify, and distribute this software for any
5 * purpose with or without fee is hereby granted, provided that the above
6 * copyright notice and this permission notice appear in all copies.
7 *
8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */
16
17#include <sys/param.h>
18#include <sys/queue.h>
19#include <stdio.h>
20#include <stdlib.h>
21#include <string.h>
22#include <syslog.h>
23#include <unistd.h>
24#include <event.h>
25
26#include "icb.h"
27
28extern int creategroups;
29
30void icb_cmd_boot(struct icb_session *, char *);
31void icb_cmd_change(struct icb_session *, char *);
32void icb_cmd_name(struct icb_session *, char *);
33void icb_cmd_personal(struct icb_session *, char *);
34void icb_cmd_pass(struct icb_session *, char *);
35void icb_cmd_topic(struct icb_session *, char *);
36void icb_cmd_who(struct icb_session *, char *);
37
38void *
39icb_cmd_lookup(char *cmd)
40{
41 struct {
42 const char *cmd;
43 void (*handler)(struct icb_session *, char *);
44 } cmdtab[] = {
45 { "boot", icb_cmd_boot },
46 { "g", icb_cmd_change },
47 { "m", icb_cmd_personal },
48 { "msg", icb_cmd_personal },
49 { "name", icb_cmd_name },
50 { "pass", icb_cmd_pass },
51 { "topic", icb_cmd_topic },
52 { "w", icb_cmd_who },
53 { NULL, NULL }
54 };
55 int i;
56
57 for (i = 0; cmdtab[i].cmd != NULL; i++)
58 if (strcasecmp(cmdtab[i].cmd, cmd) == 0)
59 return (cmdtab[i].handler);
60 return (NULL);
61}
62
63void
64icb_cmd_boot(struct icb_session *is, char *arg)
65{
66 struct icb_group *ig;
67 struct icb_session *s;
68
69 /* to boot or not to boot, that is the question */
70 ig = is->group;
71 if (!icb_ismoder(ig, is)) {
72 icb_status(is, STATUS_NOTIFY, "Sorry, booting is a privilege "
73 "you don't possess");
74 return;
75 }
76
77 /* who would be a target then? */
78 LIST_FOREACH(s, &ig->sess, entry) {
79 if (strcmp(s->nick, arg) == 0)
80 break;
81 }
82 if (s == NULL) {
83 icb_status(is, STATUS_NOTIFY, "No such user");
84 return;
85 }
86
87 /* okay, here we go, but first, be polite and notify a user */
88 icb_status(s, STATUS_BOOT, "%s booted you", is->nick);
89 icb_status_group(s->group, s, STATUS_BOOT, "%s was booted", s->nick);
90 icb_drop(s, "booted");
91}
92
93void
94icb_cmd_change(struct icb_session *is, char *arg)
95{
96 struct icb_group *ig;
97 struct icb_session *s;
98 int changing = 0;
99
100 if (strlen(arg) == 0) {
101 icb_error(is, "Invalid group");
102 return;
103 }
104
105 LIST_FOREACH(ig, &groups, entry) {
106 if (strcmp(ig->name, arg) == 0)
107 break;
108 }
109 if (ig == NULL) {
110 if (!creategroups) {
111 icb_error(is, "Invalid group");
112 return;
113 } else {
114 if ((ig = icb_addgroup(is, arg, NULL)) == NULL) {
115 icb_error(is, "Can't create group");
116 return;
117 }
118 icb_log(NULL, LOG_DEBUG, "%s created group %s",
119 is->nick, arg);
120 }
121 }
122
123 /* changing to the same group is strictly prohibited */
124 if (is->group && is->group == ig) {
125 icb_error(is, "Huh?");
126 return;
127 }
128
129 LIST_FOREACH(s, &ig->sess, entry) {
130 if (strcmp(s->nick, is->nick) == 0) {
131 icb_error(is, "Nick is already in use");
132 return;
133 }
134 }
135
136 if (is->group) {
137 changing = 1;
138 if (icb_ismoder(is->group, is))
139 (void)icb_pass(is->group, is, NULL);
140 LIST_REMOVE(is, entry);
141 icb_status_group(is->group, NULL, STATUS_DEPART,
142 "%s (%s@%s) just left", is->nick, is->client, is->host);
143 }
144
145 is->group = ig;
146 LIST_INSERT_HEAD(&ig->sess, is, entry);
147
148 /* notify group */
149 icb_status_group(ig, is, changing ? STATUS_ARRIVE : STATUS_SIGNON,
150 "%s (%s@%s) entered group", is->nick, is->client, is->host);
151
152 /* acknowledge successful join */
153 icb_status(is, STATUS_STATUS, "You are now in group %s%s", ig->name,
154 icb_ismoder(ig, is) ? " as moderator" : "");
155
156 /* send user a topic name */
157 if (strlen(ig->topic) > 0)
158 icb_status(is, STATUS_TOPIC, "The topic is: %s", ig->topic);
159}
160
161void
162icb_cmd_name(struct icb_session *is, char *arg)
163{
164 struct icb_group *ig = is->group;
165 struct icb_session *s;
166
167 if (strlen(arg) == 0) {
168 icb_status(is, STATUS_NAME, "Your nickname is %s",
169 is->nick);
170 return;
171 }
172 if (strcasecmp(arg, "admin") == 0) {
173 icb_error(is, "Wuff wuff!");
174 return;
175 }
176 /* sanitize user input */
177 if (strlen(arg) > ICB_MAXNICKLEN)
178 arg[ICB_MAXNICKLEN - 1] = '\0';
179 LIST_FOREACH(s, &ig->sess, entry) {
180 if (strcmp(s->nick, arg) == 0) {
181 icb_error(is, "Nick is already in use");
182 return;
183 }
184 }
185 icb_status_group(ig, NULL, STATUS_NAME,
186 "%s changed nickname to %s", is->nick, arg);
187 strlcpy(is->nick, arg, sizeof is->nick);
188}
189
190void
191icb_cmd_personal(struct icb_session *is, char *arg)
192{
193 char *p;
194
195 if ((p = strchr(arg, ' ')) == 0) {
196 icb_error(is, "Empty message");
197 return;
198 }
199 *p = '\0';
200 icb_privmsg(is, arg, ++p);
201}
202
203void
204icb_cmd_pass(struct icb_session *is, char *arg __attribute__((unused)))
205{
206 if (!icb_ismoder(is->group, is))
207 (void)icb_pass(is->group, is->group->moder, is);
208}
209
210void
211icb_cmd_topic(struct icb_session *is, char *arg)
212{
213 struct icb_group *ig = is->group;
214
215 if (strlen(arg) == 0) { /* querying the topic */
216 if (strlen(ig->topic) > 0)
217 icb_status(is, STATUS_TOPIC, "The topic is: %s",
218 ig->topic);
219 else
220 icb_status(is, STATUS_TOPIC, "The topic is not set.");
221 } else { /* setting the topic */
222 strlcpy(ig->topic, arg, sizeof ig->topic);
223 icb_status_group(ig, NULL, STATUS_TOPIC,
224 "%s changed the topic to \"%s\"", is->nick, ig->topic);
225 }
226}
227
228void
229icb_cmd_who(struct icb_session *is, char *arg __attribute__((unused)))
230{
231 icb_who(is, NULL);
232}
Note: See TracBrowser for help on using the repository browser.