1 /*****
2 *
3 * Copyright (C) 2005-2015 CS-SI. All Rights Reserved.
4 * Author: Yoann Vandoorselaere <yoann.v@prelude-ids.com>
5 *
6 * This file is part of the Prelude library.
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2, or (at your option)
11 * any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License along
19 * with this program; if not, write to the Free Software Foundation, Inc.,
20 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
21 *
22 *****/
23
24 %begin %{
25 #include "config.h"
26 #include "../../libmissing/glthread/thread.h"
27 %}
28
29 /*
30 * Conversion not allowed
31 */
32 %ignore *::operator =;
33 %ignore *::operator int() const;
34 %ignore *::operator long() const;
35 %ignore *::operator int32_t() const;
36 %ignore *::operator uint32_t() const;
37 %ignore *::operator int64_t() const;
38 %ignore *::operator uint64_t() const;
39 %ignore *::operator float() const;
40 %ignore *::operator double() const;
41 %ignore *::operator Prelude::IDMEFTime() const;
42 %ignore *::operator const std::string() const;
43 %ignore *::operator const char *() const;
44
45
46 %header %{
47 #define TARGET_LANGUAGE_SELF SV *
48 #define TARGET_LANGUAGE_OUTPUT_TYPE SV **
49 %}
50
51 %fragment("IDMEFValueList_to_SWIG", "header") {
52 int IDMEFValue_to_SWIG(TARGET_LANGUAGE_SELF self, const Prelude::IDMEFValue &result, void *extra, TARGET_LANGUAGE_OUTPUT_TYPE ret);
53
IDMEFValueList_to_SWIG(TARGET_LANGUAGE_SELF self,const Prelude::IDMEFValue & value,void * extra)54 SV *IDMEFValueList_to_SWIG(TARGET_LANGUAGE_SELF self, const Prelude::IDMEFValue &value, void *extra)
55 {
56 int j = 0, ret;
57 std::vector<Prelude::IDMEFValue> result = value;
58 std::vector<Prelude::IDMEFValue>::const_iterator i;
59
60 AV *myav;
61 SV *svret, **svs = new SV*[result.size()];
62
63 for ( i = result.begin(); i != result.end(); i++ ) {
64 if ( (*i).isNull() ) {
65 SvREFCNT_inc(& PL_sv_undef);
66 svs[j++] = &PL_sv_undef;
67 } else {
68 ret = IDMEFValue_to_SWIG(self, *i, NULL, &svs[j++]);
69 if ( ret < 0 )
70 return NULL;
71 }
72 }
73
74 myav = av_make(result.size(), svs);
75 delete[] svs;
76
77 svret = newRV_noinc((SV*) myav);
78 sv_2mortal(svret);
79
80 return svret;
81 }
82 }
83
84 /* tell squid not to cast void * value */
85 %typemap(in) void *nocast_p {
86 $1 = $input;
87 }
88
89 %fragment("TransitionFunc", "header") {
90 static SV *__prelude_log_func;
91 static gl_thread_t __initial_thread;
92
93
_cb_perl_log(int level,const char * str)94 static void _cb_perl_log(int level, const char *str)
95 {
96 if ( (gl_thread_t) gl_thread_self() != __initial_thread )
97 return;
98
99 dSP;
100 ENTER;
101 SAVETMPS;
102
103 PUSHMARK(SP);
104 XPUSHs(SWIG_From_int(level));
105 XPUSHs(SWIG_FromCharPtr(str));
106 PUTBACK;
107
108 perl_call_sv(__prelude_log_func, G_VOID);
109
110 FREETMPS;
111 LEAVE;
112 }
113
114
_cb_perl_write(prelude_msgbuf_t * fd,prelude_msg_t * msg)115 static int _cb_perl_write(prelude_msgbuf_t *fd, prelude_msg_t *msg)
116 {
117 ssize_t ret;
118 PerlIO *io = (PerlIO *) prelude_msgbuf_get_data(fd);
119
120 ret = PerlIO_write(io, (const char *) prelude_msg_get_message_data(msg), prelude_msg_get_len(msg));
121 if ( ret != prelude_msg_get_len(msg) )
122 return prelude_error_from_errno(errno);
123
124 prelude_msg_recycle(msg);
125
126 return 0;
127 }
128
129
_cb_perl_read(prelude_io_t * fd,void * buf,size_t size)130 static ssize_t _cb_perl_read(prelude_io_t *fd, void *buf, size_t size)
131 {
132 int ret;
133 PerlIO *io = (PerlIO *) prelude_io_get_fdptr(fd);
134
135 ret = PerlIO_read(io, buf, size);
136 if ( ret < 0 )
137 ret = prelude_error_from_errno(errno);
138
139 else if ( ret == 0 )
140 ret = prelude_error(PRELUDE_ERROR_EOF);
141
142 return ret;
143 }
144 };
145
146 %typemap(in, fragment="TransitionFunc") void (*log_cb)(int level, const char *log) {
147 if ( __prelude_log_func )
148 SvREFCNT_dec(__prelude_log_func);
149
150 __prelude_log_func = $input;
151 SvREFCNT_inc($input);
152
153 $1 = _cb_perl_log;
154 };
155
156
157 %exception read(void *nocast_p) {
158 try {
159 $action
catch(Prelude::PreludeError & e)160 } catch(Prelude::PreludeError &e) {
161 if ( e.getCode() == PRELUDE_ERROR_EOF )
162 result = 0;
163 else
164 SWIG_exception_fail(SWIG_RuntimeError, e.what());
165 }
166 }
167
168
169 %extend Prelude::IDMEF {
write(void * nocast_p)170 void write(void *nocast_p) {
171 PerlIO *io = IoIFP(sv_2io((SV *) nocast_p));
172 self->_genericWrite(_cb_perl_write, io);
173 }
174
read(void * nocast_p)175 int read(void *nocast_p) {
176 PerlIO *io = IoIFP(sv_2io((SV *) nocast_p));
177 self->_genericRead(_cb_perl_read, io);
178 return 1;
179 }
180 }
181
182
183 %typemap(out, fragment="IDMEFValue_to_SWIG") Prelude::IDMEFValue {
184 int ret;
185
186 if ( $1.isNull() ) {
187 SvREFCNT_inc (& PL_sv_undef);
188 $result = &PL_sv_undef;
189 } else {
190 SV *mysv;
191
192 ret = IDMEFValue_to_SWIG(NULL, $1, NULL, &mysv);
193 if ( ret < 0 ) {
194 std::stringstream s;
195 s << "IDMEFValue typemap does not handle value of type '" << idmef_value_type_to_string((idmef_value_type_id_t) $1.getType()) << "'";
196 SWIG_exception_fail(SWIG_ValueError, s.str().c_str());
197 }
198
199 $result = mysv;
200 }
201
202 argvi++;
203 };
204
205
206 %init {
207 STRLEN len;
208 char **argv;
209 int j, argc = 1, ret;
210 AV *pargv = get_av("ARGV", FALSE);
211
212 __initial_thread = (gl_thread_t) gl_thread_self();
213
214 ret = av_len(pargv);
215 if ( ret >= 0 )
216 argc += ret + 1;
217
218 if ( argc + 1 < 0 )
219 throw PreludeError("Invalide argc length");
220
221 argv = (char **) malloc((argc + 1) * sizeof(char *));
222 if ( ! argv )
223 throw PreludeError("Allocation failure");
224
225 argv[0] = SvPV(get_sv("0", FALSE), len);
226
227 for ( j = 0; j < ret + 1; j++ )
228 argv[j + 1] = SvPV(*av_fetch(pargv, j, FALSE), len);
229
230 argv[j + 1] = NULL;
231
232 ret = prelude_init(&argc, argv);
233 if ( ret < 0 ) {
234 free(argv);
235 throw PreludeError(ret);
236 }
237
238 free(argv);
239 }
240