Merged with Irssi 0.8.6.
[silc.git] / apps / irssi / src / perl / common / Core.xs
1 #include "module.h"
2 #include "irssi-version.h"
3 #include "core.h"
4
5 #include "pidwait.h"
6
7 #define DEFAULT_COMMAND_CATEGORY "Perl scripts' commands"
8
9 void perl_signal_add_hash(int priority, SV *sv)
10 {
11         HV *hv;
12         HE *he;
13         I32 len;
14
15         if (!is_hvref(sv))
16                 croak("Usage: Irssi::signal_add(hash)");
17
18         hv = hvref(sv);
19         hv_iterinit(hv);
20         while ((he = hv_iternext(hv)) != NULL)
21                 perl_signal_add_full(hv_iterkey(he, &len), HeVAL(he), priority);
22 }
23
24 static void perl_command_bind_add_hash(int priority, SV *sv, char *category)
25 {
26         HV *hv;
27         HE *he;
28         I32 len;
29
30         hv = hvref(sv);
31         hv_iterinit(hv);
32         while ((he = hv_iternext(hv)) != NULL)
33                 perl_command_bind_to(hv_iterkey(he, &len), category, HeVAL(he), priority);
34 }
35
36 static void handle_command_bind(int priority, int items, SV *p0, SV *p1, SV *p2)
37 {
38         char *category;
39         int hash;
40
41         hash = items > 0 && is_hvref(p0);
42         if (!hash) {
43                 if (items < 2 || items > 3)
44                         croak("Usage: Irssi::command_bind(signal, func, category)");
45         } else if (items > 2)
46                 croak("Usage: Irssi::command_bind(signals_hash, category)");
47
48         if (!hash) {
49                 category = items < 3 ? DEFAULT_COMMAND_CATEGORY :
50                         (char *)SvPV(p2, PL_na);
51                 perl_command_bind_to((char *)SvPV(p0, PL_na), category, p1, priority);
52         } else {
53                 category = items < 2 ? DEFAULT_COMMAND_CATEGORY :
54                         (char *)SvPV(p1, PL_na);
55                 perl_command_bind_add_hash(priority, p0, category);
56         }
57 }
58
59 MODULE = Irssi::Core  PACKAGE = Irssi
60 PROTOTYPES: ENABLE
61
62 void
63 signal_emit(signal, ...)
64         char *signal
65 CODE:
66         void *p[SIGNAL_MAX_ARGUMENTS];
67         int n;
68
69         memset(p, 0, sizeof(p));
70         for (n = 1; n < items && n < SIGNAL_MAX_ARGUMENTS+1; n++) {
71                 if (SvPOKp(ST(n)))
72                         p[n-1] = SvPV(ST(n), PL_na);
73                 else if (irssi_is_ref_object(ST(n)))
74                         p[n-1] = irssi_ref_object(ST(n));
75                 else if (SvROK(ST(n)))
76                         p[n-1] = (void *) SvIV((SV*)SvRV(ST(n)));
77                 else
78                         p[n-1] = NULL;
79         }
80         signal_emit(signal, items-1, p[0], p[1], p[2], p[3], p[4], p[5]);
81
82 void
83 signal_continue(...)
84 CODE:
85         void *p[SIGNAL_MAX_ARGUMENTS];
86         int n;
87
88         memset(p, 0, sizeof(p));
89         for (n = 0; n < items && n < SIGNAL_MAX_ARGUMENTS; n++) {
90                 if (SvPOKp(ST(n)))
91                         p[n] = SvPV(ST(n), PL_na);
92                 else if (irssi_is_ref_object(ST(n)))
93                         p[n] = irssi_ref_object(ST(n));
94                 else if (SvROK(ST(n)))
95                         p[n] = (void *) SvIV((SV*)SvRV(ST(n)));
96                 else
97                         p[n] = NULL;
98         }
99         signal_continue(items, p[0], p[1], p[2], p[3], p[4], p[5]);
100
101 void
102 signal_add(...)
103 CODE:
104         if (items != 1 && items != 2)
105                 croak("Usage: Irssi::signal_add(signal, func)");
106         if (items == 2)
107                 perl_signal_add_full((char *)SvPV(ST(0),PL_na), ST(1),
108                                      SIGNAL_PRIORITY_DEFAULT);
109         else
110                 perl_signal_add_hash(SIGNAL_PRIORITY_DEFAULT, ST(0));
111
112 void
113 signal_add_first(...)
114 CODE:
115         if (items != 1 && items != 2)
116                 croak("Usage: Irssi::signal_add_first(signal, func)");
117         if (items == 2)
118                 perl_signal_add_full((char *)SvPV(ST(0),PL_na), ST(1),
119                                      SIGNAL_PRIORITY_HIGH);
120         else
121                 perl_signal_add_hash(SIGNAL_PRIORITY_HIGH, ST(0));
122
123 void
124 signal_add_last(...)
125 CODE:
126         if (items != 1 && items != 2)
127                 croak("Usage: Irssi::signal_add_last(signal, func)");
128         if (items == 2)
129                 perl_signal_add_full((char *)SvPV(ST(0),PL_na), ST(1),
130                                      SIGNAL_PRIORITY_LOW);
131         else
132                 perl_signal_add_hash(SIGNAL_PRIORITY_LOW, ST(0));
133
134 void
135 signal_add_priority(...)
136 CODE:
137         if (items != 2 && items != 3)
138                 croak("Usage: Irssi::signal_add_priority(signal, func, priority)");
139         if (items == 3)
140                 perl_signal_add_full((char *)SvPV(ST(0),PL_na), ST(1), SvIV(ST(2)));
141         else
142                 perl_signal_add_hash(SvIV(ST(0)), ST(1));
143
144 int
145 SIGNAL_PRIORITY_LOW()
146 CODE:
147         RETVAL = SIGNAL_PRIORITY_LOW;
148 OUTPUT:
149         RETVAL
150
151 int
152 SIGNAL_PRIORITY_DEFAULT()
153 CODE:
154         RETVAL = SIGNAL_PRIORITY_DEFAULT;
155 OUTPUT:
156         RETVAL
157
158 int
159 SIGNAL_PRIORITY_HIGH()
160 CODE:
161         RETVAL = SIGNAL_PRIORITY_HIGH;
162 OUTPUT:
163         RETVAL
164
165 void
166 signal_remove(signal, func)
167         char *signal
168         SV *func
169 CODE:
170         perl_signal_remove(signal, func);
171
172 void
173 signal_stop()
174
175 void
176 signal_stop_by_name(signal)
177         char *signal
178
179 char *
180 signal_get_emitted()
181 CODE:
182         RETVAL = (char *) signal_get_emitted();
183 OUTPUT:
184         RETVAL
185
186 int
187 signal_get_emitted_id()
188
189 int
190 timeout_add(msecs, func, data)
191         int msecs
192         SV *func
193         SV *data
194 CODE:
195         if (msecs < 10) {
196                 croak("Irssi::timeout() : msecs must be >= 10");
197                 RETVAL = -1;
198         } else {
199                 RETVAL = perl_timeout_add(msecs, func, data, FALSE);
200         }
201 OUTPUT:
202         RETVAL
203
204 int
205 timeout_add_once(msecs, func, data)
206         int msecs
207         SV *func
208         SV *data
209 CODE:
210         if (msecs < 10) {
211                 croak("Irssi::timeout_once() : msecs must be >= 10");
212                 RETVAL = -1;
213         } else {
214                 RETVAL = perl_timeout_add(msecs, func, data, TRUE);
215         }
216 OUTPUT:
217         RETVAL
218
219 void
220 timeout_remove(tag)
221         int tag
222 CODE:
223         perl_source_remove(tag);
224
225
226 int
227 INPUT_READ()
228 CODE:
229         RETVAL = G_INPUT_READ;
230 OUTPUT:
231         RETVAL
232
233 int
234 INPUT_WRITE()
235 CODE:
236         RETVAL = G_INPUT_WRITE;
237 OUTPUT:
238         RETVAL
239
240 int
241 input_add(source, condition, func, data)
242         int source
243         int condition
244         SV *func
245         SV *data
246 CODE:
247         RETVAL = perl_input_add(source, condition, func, data, FALSE);
248 OUTPUT:
249         RETVAL
250
251 void
252 input_remove(tag)
253         int tag
254 CODE:
255         perl_source_remove(tag);
256
257 # maybe there's some easier way than this..? :)
258 int
259 MSGLEVEL_CRAP()
260 CODE:
261         RETVAL = MSGLEVEL_CRAP;
262 OUTPUT:
263         RETVAL
264
265 int
266 MSGLEVEL_MSGS()
267 CODE:
268         RETVAL = MSGLEVEL_MSGS;
269 OUTPUT:
270         RETVAL
271
272 int
273 MSGLEVEL_PUBLIC()
274 CODE:
275         RETVAL = MSGLEVEL_PUBLIC;
276 OUTPUT:
277         RETVAL
278
279 int
280 MSGLEVEL_NOTICES()
281 CODE:
282         RETVAL = MSGLEVEL_NOTICES;
283 OUTPUT:
284         RETVAL
285
286 int
287 MSGLEVEL_SNOTES()
288 CODE:
289         RETVAL = MSGLEVEL_SNOTES;
290 OUTPUT:
291         RETVAL
292
293 int
294 MSGLEVEL_CTCPS()
295 CODE:
296         RETVAL = MSGLEVEL_CTCPS;
297 OUTPUT:
298         RETVAL
299
300 int
301 MSGLEVEL_ACTIONS()
302 CODE:
303         RETVAL = MSGLEVEL_ACTIONS;
304 OUTPUT:
305         RETVAL
306
307 int
308 MSGLEVEL_JOINS()
309 CODE:
310         RETVAL = MSGLEVEL_JOINS;
311 OUTPUT:
312         RETVAL
313
314 int
315 MSGLEVEL_PARTS()
316 CODE:
317         RETVAL = MSGLEVEL_PARTS;
318 OUTPUT:
319         RETVAL
320
321 int
322 MSGLEVEL_QUITS()
323 CODE:
324         RETVAL = MSGLEVEL_QUITS;
325 OUTPUT:
326         RETVAL
327
328 int
329 MSGLEVEL_KICKS()
330 CODE:
331         RETVAL = MSGLEVEL_KICKS;
332 OUTPUT:
333         RETVAL
334
335 int
336 MSGLEVEL_MODES()
337 CODE:
338         RETVAL = MSGLEVEL_MODES;
339 OUTPUT:
340         RETVAL
341
342 int
343 MSGLEVEL_TOPICS()
344 CODE:
345         RETVAL = MSGLEVEL_TOPICS;
346 OUTPUT:
347         RETVAL
348
349 int
350 MSGLEVEL_WALLOPS()
351 CODE:
352         RETVAL = MSGLEVEL_WALLOPS;
353 OUTPUT:
354         RETVAL
355
356 int
357 MSGLEVEL_INVITES()
358 CODE:
359         RETVAL = MSGLEVEL_INVITES;
360 OUTPUT:
361         RETVAL
362
363 int
364 MSGLEVEL_NICKS()
365 CODE:
366         RETVAL = MSGLEVEL_NICKS;
367 OUTPUT:
368         RETVAL
369
370 int
371 MSGLEVEL_DCC()
372 CODE:
373         RETVAL = MSGLEVEL_DCC;
374 OUTPUT:
375         RETVAL
376
377 int
378 MSGLEVEL_DCCMSGS()
379 CODE:
380         RETVAL = MSGLEVEL_DCCMSGS;
381 OUTPUT:
382         RETVAL
383
384 int
385 MSGLEVEL_CLIENTNOTICE()
386 CODE:
387         RETVAL = MSGLEVEL_CLIENTNOTICE;
388 OUTPUT:
389         RETVAL
390
391 int
392 MSGLEVEL_CLIENTCRAP()
393 CODE:
394         RETVAL = MSGLEVEL_CLIENTCRAP;
395 OUTPUT:
396         RETVAL
397
398 int
399 MSGLEVEL_CLIENTERROR()
400 CODE:
401         RETVAL = MSGLEVEL_CLIENTERROR;
402 OUTPUT:
403         RETVAL
404
405 int
406 MSGLEVEL_HILIGHT()
407 CODE:
408         RETVAL = MSGLEVEL_HILIGHT;
409 OUTPUT:
410         RETVAL
411
412 int
413 MSGLEVEL_ALL()
414 CODE:
415         RETVAL = MSGLEVEL_ALL;
416 OUTPUT:
417         RETVAL
418
419 int
420 MSGLEVEL_NOHILIGHT()
421 CODE:
422         RETVAL = MSGLEVEL_NOHILIGHT;
423 OUTPUT:
424         RETVAL
425
426 int
427 MSGLEVEL_NO_ACT()
428 CODE:
429         RETVAL = MSGLEVEL_NO_ACT;
430 OUTPUT:
431         RETVAL
432
433 int
434 MSGLEVEL_NEVER()
435 CODE:
436         RETVAL = MSGLEVEL_NEVER;
437 OUTPUT:
438         RETVAL
439
440 int
441 MSGLEVEL_LASTLOG()
442 CODE:
443         RETVAL = MSGLEVEL_LASTLOG;
444 OUTPUT:
445         RETVAL
446
447 int
448 level2bits(str)
449         char *str
450
451 void
452 bits2level(bits)
453         int bits
454 PREINIT:
455         char *ret;
456 PPCODE:
457         ret = bits2level(bits);
458         XPUSHs(sv_2mortal(new_pv(ret)));
459         g_free(ret);
460
461 int
462 combine_level(level, str)
463         int level
464         char *str
465
466 void
467 command(cmd)
468         char *cmd
469 CODE:
470         perl_command(cmd, NULL, NULL);
471
472 void
473 commands()
474 PREINIT:
475         GSList *tmp;
476 PPCODE:
477         for (tmp = commands; tmp != NULL; tmp = tmp->next) {
478                 XPUSHs(sv_2mortal(plain_bless(tmp->data, "Irssi::Command")));
479         }
480
481 void
482 command_bind_first(...)
483 CODE:
484         handle_command_bind(SIGNAL_PRIORITY_HIGH, items, ST(0), ST(1), ST(2));
485
486 void
487 command_bind(...)
488 CODE:
489         handle_command_bind(SIGNAL_PRIORITY_DEFAULT, items, ST(0), ST(1), ST(2));
490
491 void
492 command_bind_last(...)
493 CODE:
494         handle_command_bind(SIGNAL_PRIORITY_LOW, items, ST(0), ST(1), ST(2));
495
496 void
497 command_runsub(cmd, data, server, item)
498         char *cmd
499         char *data
500         Irssi::Server server
501         Irssi::Windowitem item
502 CODE:
503         perl_command_runsub(cmd, data, server, item);
504
505 void
506 command_unbind(cmd, func)
507         char *cmd
508         SV *func
509 CODE:
510         perl_command_unbind(cmd, func);
511
512 void
513 command_set_options(cmd, options)
514         char *cmd
515         char *options
516
517 void
518 pidwait_add(pid)
519         int pid
520
521 void 
522 pidwait_remove(pid)
523         int pid
524
525 void
526 parse_special(cmd, data="", flags=0)
527         char *cmd
528         char *data
529         int flags
530 PREINIT:
531         char *ret;
532 PPCODE:
533         ret = parse_special_string(cmd, NULL, NULL, data, NULL, flags);
534         XPUSHs(sv_2mortal(new_pv(ret)));
535         g_free_not_null(ret);
536
537 char *
538 get_irssi_dir()
539 CODE:
540         RETVAL = (char *) get_irssi_dir();
541 OUTPUT:
542         RETVAL
543
544 char *
545 get_irssi_config()
546 CODE:
547         RETVAL = (char *) get_irssi_config();
548 OUTPUT:
549         RETVAL
550
551 char *
552 version()
553 PREINIT:
554         char version[100];
555 CODE:
556         g_snprintf(version, sizeof(version), "%d.%04d",
557                    IRSSI_VERSION_DATE, IRSSI_VERSION_TIME);
558         RETVAL = version;
559 OUTPUT:
560         RETVAL
561
562 int
563 get_gui()
564 CODE:
565         RETVAL = irssi_gui;
566 OUTPUT:
567         RETVAL
568
569 int
570 IRSSI_GUI_NONE()
571 CODE:
572         RETVAL = IRSSI_GUI_NONE;
573 OUTPUT:
574         RETVAL
575
576 int
577 IRSSI_GUI_TEXT()
578 CODE:
579         RETVAL = IRSSI_GUI_TEXT;
580 OUTPUT:
581         RETVAL
582
583 int
584 IRSSI_GUI_GTK()
585 CODE:
586         RETVAL = IRSSI_GUI_GTK;
587 OUTPUT:
588         RETVAL
589
590 int
591 IRSSI_GUI_GNOME()
592 CODE:
593         RETVAL = IRSSI_GUI_GNOME;
594 OUTPUT:
595         RETVAL
596
597 int
598 IRSSI_GUI_QT()
599 CODE:
600         RETVAL = IRSSI_GUI_QT;
601 OUTPUT:
602         RETVAL
603
604 int
605 IRSSI_GUI_KDE()
606 CODE:
607         RETVAL = IRSSI_GUI_KDE;
608 OUTPUT:
609         RETVAL
610
611 #*******************************
612 MODULE = Irssi::Core    PACKAGE = Irssi::Server
613 #*******************************
614
615 void
616 parse_special(server, cmd, data="", flags=0)
617         Irssi::Server server
618         char *cmd
619         char *data
620         int flags
621 PREINIT:
622         char *ret;
623 PPCODE:
624         ret = parse_special_string(cmd, server, NULL, data, NULL, flags);
625         XPUSHs(sv_2mortal(new_pv(ret)));
626         g_free_not_null(ret);
627
628 void
629 command(server, cmd)
630         Irssi::Server server
631         char *cmd
632 CODE:
633         perl_command(cmd, server, NULL);
634
635
636 #*******************************
637 MODULE = Irssi::Core    PACKAGE = Irssi::Windowitem
638 #*******************************
639
640 void
641 parse_special(item, cmd, data="", flags=0)
642         Irssi::Windowitem item
643         char *cmd
644         char *data
645         int flags
646 PREINIT:
647         char *ret;
648 PPCODE:
649         ret = parse_special_string(cmd, item->server, item, data, NULL, flags);
650         XPUSHs(sv_2mortal(new_pv(ret)));
651         g_free_not_null(ret);
652
653 void
654 command(item, cmd)
655         Irssi::Windowitem item
656         char *cmd
657 CODE:
658         perl_command(cmd, item->server, item);
659