This problem was discussed here before, but there was no solution:

http://www.mail-archive.com/[email protected]/msg00533.html

nfacctd from pmacct 0.11.3 with mysql plugin segfaults in
sql_handlers.c:MY_count_ip_proto_handler() on FreeBSD-i386 5.2.1:

$ gdb nfacctd nfacctd.core
GNU gdb 5.2.1 (FreeBSD)
...
Program terminated with signal 11, Segmentation fault.
...
#0  0x283223f8 in __vfprintf () from /lib/libc.so.5
(gdb) bt
#0  0x283223f8 in __vfprintf () from /lib/libc.so.5
#1  0x2831e3a3 in snprintf () from /lib/libc.so.5
#2  0x0807832c in MY_count_ip_proto_handler (cache_elem=0x842aba0,
    idata=0xbfbdc980, num=5, ptr_values=0xbfbdc4ac, ptr_where=0xbfbdc4a8)
    at sql_handlers.c:151
#3  0x08070c22 in MY_cache_dbop (db=0x80ba4dc, cache_elem=0x842aba0,
    idata=0xbfbdc980) at mysql_plugin.c:294
#4  0x08076e72 in sql_query (bed=0x80c3ac0, elem=0x842aba0, idata=0xbfbdc980)
    at sql_common.c:1109
#5  0x080712c9 in MY_cache_purge (queue=0x8437000, index=929, idata=0xbfbdc980)
    at mysql_plugin.c:426
#6  0x08070821 in mysql_plugin (pipe_fd=5, cfgptr=0x80c6908, ptr=0x80ab2e0)
    at mysql_plugin.c:199
#7  0x0805760b in load_plugins (req=0xbfbfed9f) at plugin_hooks.c:173
#8  0x08052fba in main (argc=3, argv=0xbfbfedd4, envp=0xbfbfede4)
    at nfacctd.c:471
#9  0x08051a62 in _start ()
(gdb) up 2
#2  0x0807832c in MY_count_ip_proto_handler (cache_elem=0x842aba0,
    idata=0xbfbdc980, num=5, ptr_values=0xbfbdc4ac, ptr_where=0xbfbdc4a8)
    at sql_handlers.c:151
151     snprintf(*ptr_where, SPACELEFT(where_clause), where[num].string, 
cache_elem->primitives.proto);
(gdb) p where[num].string
$1 = " AND ip_proto='%s'", '\0' <repeats 237 times>
(gdb) pt cache_elem->primitives.proto
type = unsigned char
(gdb) p cache_elem->primitives.proto
$2 = 139 '\213'

I.e. wrong argument type is used for snprintf format string (unsigned
char is used where pointer to a string expected). This happens when
protocol number is not found in number->name mapping table. Example
patch is included below.

The first part of the patch adds "#include <pthread.h>" to pmacct.h
to help compile pmacct on older FreeBSD 5.x systems and shouldn't hurt
other systems.

I'm also wondering, what's that strange IP packet:

(gdb) p/x *cache_elem
$3 = {primitives = {eth_dhost = {0x0, 0x0, 0x0, 0x0, 0x0, 0x0}, eth_shost = {
      0x0, 0x0, 0x0, 0x0, 0x0, 0x0}, vlan_id = 0x0, src_ip = {family = 0x2,
      address = {ipv4 = {s_addr = 0xff******}}}, dst_ip = {family = 0x2,
      address = {ipv4 = {s_addr = 0xffffffff}}}, src_as = 0x0, dst_as = 0x0,
    src_port = 0x0, dst_port = 0x0, tos = 0x0, proto = 0x8b, id = 0x0,
    class = 0x0}, bytes_counter = 0x64, packet_counter = 0x2,
  flows_counter = 0x0, tentatives = 0x0, basetime = 0x460c6cc8, valid = 0x1,
  signature = 0x32a9ae34, chained = 0x0, prev = 0x0, next = 0x0,
  start_tag = 0x460c6d77, lru_tag = 0x460c6d77, lru_prev = 0x0, lru_next = 0x0}

i.e. from A.B.C.255 to 255.255.255.255 proto (not port!) 139 (hex 0x8b)?

Patch:

Index: src/pmacct.h
===================================================================
RCS file: /home/repo/pmacct/src/pmacct.h,v
retrieving revision 1.3
diff -u -d -p -r1.3 pmacct.h
--- src/pmacct.h        25 Jan 2007 22:57:47 -0000      1.3
+++ src/pmacct.h        30 Mar 2007 03:30:51 -0000
@@ -55,6 +55,7 @@
 #include <sys/select.h>
 #include <signal.h>
 #include <syslog.h>
+#include <pthread.h>
 
 #include <sys/mman.h>
 #if !defined (MAP_ANONYMOUS)
Index: src/sql_handlers.c
===================================================================
RCS file: /home/repo/pmacct/src/sql_handlers.c,v
retrieving revision 1.2
diff -u -d -p -r1.2 sql_handlers.c
--- src/sql_handlers.c  25 Jan 2007 22:57:47 -0000      1.2
+++ src/sql_handlers.c  30 Mar 2007 03:30:51 -0000
@@ -148,8 +148,10 @@ void MY_count_ip_proto_handler(const str
     snprintf(*ptr_values, SPACELEFT(values_clause), values[num].string, 
_protocols[cache_elem->primitives.proto].name);
   }
   else {
-    snprintf(*ptr_where, SPACELEFT(where_clause), where[num].string, 
cache_elem->primitives.proto);
-    snprintf(*ptr_values, SPACELEFT(values_clause), values[num].string, 
cache_elem->primitives.proto);
+    char proto_str[PROTO_LEN];
+    snprintf(proto_str, sizeof(proto_str), "%d", cache_elem->primitives.proto);
+    snprintf(*ptr_where, SPACELEFT(where_clause), where[num].string, 
proto_str);
+    snprintf(*ptr_values, SPACELEFT(values_clause), values[num].string, 
proto_str);
   }
   *ptr_where += strlen(*ptr_where);
   *ptr_values += strlen(*ptr_values);

    wbr&w, dmitry.
-- 
Dmitry Frolov <[EMAIL PROTECTED]>
RISS-Telecom Network, Novosibirsk, Russia
[EMAIL PROTECTED], +7 383 2278800, DVF-RIPE

_______________________________________________
pmacct-discussion mailing list
http://www.pmacct.net/#mailinglists

Reply via email to