changes - bmf - bmf (Bayesian Mail Filter) 0.9.4 fork + patches
HTML git clone git://git.codemadness.org/bmf
DIR Log
DIR Files
DIR Refs
DIR README
DIR LICENSE
---
DIR commit e805a804b42a190f0b06d8c495fd0f29011b1329
DIR parent 4857ceba2cfedeafd8971a8e6e3db4ce2ea7f1b6
HTML Author: Hiltjo Posthuma <hiltjo@codemadness.org>
Date: Sat, 22 Sep 2018 17:57:54 +0200
changes
- remove -i option: reading from file.
- remove -f format option and db formats.
- initial pledge(2) support.
- remove bmfconv. only text "database" is supported.
Diffstat:
A .gitignore | 4 ++++
A Makefile | 45 +++++++++++++++++++++++++++++++
D Makefile.in | 81 ------------------------------
M bmf.1 | 13 +------------
M bmf.c | 37 ++++++-------------------------
D bmfconv.1 | 81 ------------------------------
D bmfconv.c | 169 -------------------------------
M config.h | 2 ++
D configure | 354 -------------------------------
M dbdb.c | 614 -------------------------------
M dbdb.h | 48 -------------------------------
M dbh.c | 7 -------
M dbh.h | 4 +---
D dbmysql.c | 545 -------------------------------
D dbmysql.h | 60 -------------------------------
15 files changed, 60 insertions(+), 2004 deletions(-)
---
DIR diff --git a/.gitignore b/.gitignore
@@ -0,0 +1,4 @@
+*.o
+*.core
+bmf
+bmfconv
DIR diff --git a/Makefile b/Makefile
@@ -0,0 +1,45 @@
+# Makefile for bmf
+
+BINDIR=/usr/bin
+MANDIR=/usr/share/man
+
+VERSION=0.9.4
+
+CFLAGS+=-DNDEBUG -D_UNIX -D_BSD=40 -Wall
+LDFLAGS+=
+SYSLIBS=
+
+all: bmf
+
+bmf: bmf.o filt.o dbdb.o dbtext.o dbh.o lex.o vec.o str.o dbg.o
+ $(CC) -o $@ bmf.o filt.o dbdb.o dbtext.o dbh.o lex.o vec.o str.o dbg.o $(LDFLAGS) $(SYSLIBS)
+
+bmf.o: bmf.c
+ $(CC) $(CFLAGS) -DPACKAGE=\"bmf\" -DVERSION=\"$(VERSION)\" -c $<
+
+install: checkroot bmf bmf.1
+ [ -d $(DESTDIR)$(BINDIR) ] || mkdir -p $(DESTDIR)$(BINDIR)
+ [ -d $(DESTDIR)$(MANDIR)/man1 ] || mkdir -p $(DESTDIR)$(MANDIR)/man1
+ cp bmf $(DESTDIR)$(BINDIR)
+ cp bmf.1 $(DESTDIR)$(MANDIR)/man1
+
+uninstall: checkroot
+ rm -f $(DESTDIR)$(BINDIR)/bmf
+ rm -f $(DESTDIR)$(MANDIR)/man1/bmf.1
+
+clean:
+ rm -f core *.o bmf
+
+distclean: clean
+ rm -f Makefile
+
+dist: tarball
+
+tarball: distclean
+ (cd ..; \
+ cp -ar bmf bmf-$(VERSION); \
+ tar czvf bmf-$(VERSION).tar.gz `find bmf-$(VERSION) -type f | egrep -v "CVS|debian"`; \
+ rm -rf bmf-$(VERSION); \
+ cd $(PWD))
+
+checkroot:
DIR diff --git a/Makefile.in b/Makefile.in
@@ -1,81 +0,0 @@
-# Makefile for bmf
-
-BINDIR=/usr/bin
-MANDIR=/usr/share/man
-
-VERSION=0.9.4
-
-CC=@CC@
-CFLAGS=@CFLAGS@
-LDFLAGS=@LDFLAGS@
-SYSLIBS=@SYSLIBS@
-
-# For creating rpm packages
-RPMROOT=/usr/src/rpm
-RPM = rpm
-RPMFLAGS = -ba
-ARCH=`arch|sed 's/i[4-9]86/i386/'`
-
-all: bmf bmfconv
-
-bmf: bmf.o filt.o dbmysql.o dbdb.o dbtext.o dbh.o lex.o vec.o str.o dbg.o
- $(CC) -o $@ bmf.o filt.o dbmysql.o dbdb.o dbtext.o dbh.o lex.o vec.o str.o dbg.o $(LDFLAGS) $(SYSLIBS)
-
-bmf.o: bmf.c
- $(CC) $(CFLAGS) -DPACKAGE=\"bmf\" -DVERSION=\"$(VERSION)\" -c $<
-
-bmfconv: bmfconv.o dbmysql.o dbdb.o dbtext.o dbh.o vec.o str.o dbg.o
- $(CC) -o $@ bmfconv.o dbmysql.o dbdb.o dbtext.o dbh.o vec.o str.o dbg.o $(LDFLAGS) $(SYSLIBS)
-
-bmfconv.o: bmfconv.c
- $(CC) $(CFLAGS) -DPACKAGE=\"bmfconv\" -DVERSION=\"$(VERSION)\" -c $<
-
-install: checkroot bmf bmf.1 bmfconv bmfconv.1
- [ -d $(DESTDIR)$(BINDIR) ] || mkdir -p $(DESTDIR)$(BINDIR)
- [ -d $(DESTDIR)$(MANDIR)/man1 ] || mkdir -p $(DESTDIR)$(MANDIR)/man1
- cp bmf $(DESTDIR)$(BINDIR)
- cp bmf.1 $(DESTDIR)$(MANDIR)/man1
- cp bmfconv $(DESTDIR)$(BINDIR)
- cp bmfconv.1 $(DESTDIR)$(MANDIR)/man1
-
-uninstall: checkroot
- rm -f $(DESTDIR)$(BINDIR)/bmf
- rm -f $(DESTDIR)$(MANDIR)/man1/bmf.1
- rm -f $(DESTDIR)$(BINDIR)/bmfconv
- rm -f $(DESTDIR)$(MANDIR)/man1/bmfconv.1
-
-clean:
- rm -f core *.o bmf bmfconv
-
-distclean: clean
- rm -f Makefile
-
-dist: tarball rpmpkg debpkg
-
-tarball: distclean
- (cd ..; \
- cp -ar bmf bmf-$(VERSION); \
- tar czvf bmf-$(VERSION).tar.gz `find bmf-$(VERSION) -type f | egrep -v "CVS|debian"`; \
- rm -rf bmf-$(VERSION); \
- cd $(PWD))
-
-debpkg: checkroot
- debian/rules binary
- rm -rf debian/tmp
-
-rpmpkg: checkroot
- (mkdir -p $(RPMROOT); \
- mkdir -p $(RPMROOT)/SOURCES; \
- mkdir -p $(RPMROOT)/SPECS; \
- mkdir -p $(RPMROOT)/RPMS; \
- mkdir -p $(RPMROOT)/SRPMS; \
- cp ../bmf-$(VERSION).tar.gz $(RPMROOT)/SOURCES; \
- cat bmf.spec.in | sed 's/VERSION/$(VERSION)/' > $(RPMROOT)/SPECS/bmf.spec; \
- cd $(RPMROOT)/SPECS; \
- $(RPM) $(RPMFLAGS) bmf.spec; \
- cp $(RPMROOT)/RPMS/$(ARCH)/bmf-$(VERSION)-*.rpm $(PWD)/..; \
- cp $(RPMROOT)/SRPMS/bmf-$(VERSION)-*.src.rpm $(PWD)/..; \
- cd $(PWD))
-
-checkroot:
- [ "`whoami`" = root ] || (echo Need root; exit 1)
DIR diff --git a/bmf.1 b/bmf.1
@@ -23,7 +23,7 @@ bmf \- efficient Bayesian mail filter
.SH "SYNOPSIS"
.nf
-\fBbmf\fR [-t] [-n] [-s] [-N] [-S] [-f fmt] [-d db] [-i file] [-k n] [-m type] [-p]
+\fBbmf\fR [-t] [-n] [-s] [-N] [-S] [-d db] [-k n] [-m type] [-p]
[-v] [-V] [-h]
.fi
@@ -62,9 +62,6 @@ Without command-line options, bmf processes the input, registers it as either "g
\fB-d db\fR Specify database or directory for loading and saving word lists. The default is \fI~/.bmf\fR in text mode.
.PP
-\fB-i file\fR Use file for input instead of stdin.
-
-.PP
\fB-k n\fR Specify the number of extrema (keepers) to use in the Bayes calculation. The default is 15.
.PP
@@ -119,14 +116,6 @@ List of good tokens for text mode.
\fI~/.bmf/spamlist.txt\fR
List of bad tokens for text mode.
-.TP
-\fI~/.bmf/goodlist.db\fR
-List of good tokens for libdb mode.
-
-.TP
-\fI~/.bmf/spamlist.db\fR
-List of bad tokens for libdb mode.
-
.SH "BUGS"
.PP
DIR diff --git a/bmf.c b/bmf.c
@@ -72,7 +72,7 @@ static void version( void )
int main( int argc, char** argv )
{
int ch;
- dbfmt_t dbfmt = db_db;
+ dbfmt_t dbfmt = db_text;
char* dbname = NULL;
bool_t rdonly;
@@ -93,17 +93,14 @@ int main( int argc, char** argv )
int fd = STDIN_FILENO;
char* infile = NULL;
+ if (pledge("stdio rpath wpath cpath tmppath", NULL) == -1)
+ err(1, "pledge");
+
srand(time(NULL));
atexit( dump_alloc_heap );
-#ifdef HAVE_LIBDB
- dbfmt = db_db;
-#else
- dbfmt = db_text;
-#endif
-
stats.keepers = DEF_KEEPERS;
- while( (ch = getopt( argc, argv, "NSVd:f:i:hk:m:npstv" )) != EOF )
+ while( (ch = getopt( argc, argv, "NSVd:hk:m:npstv" )) != EOF )
{
switch( ch )
{
@@ -120,31 +117,9 @@ int main( int argc, char** argv )
free( dbname );
dbname = strdup( optarg );
break;
- case 'f':
- if( strcasecmp( optarg, "text" ) == 0 )
- {
- dbfmt = db_text;
- }
- else if( strcasecmp( optarg, "db" ) == 0 )
- {
- dbfmt = db_db;
- }
- else if( strcasecmp( optarg, "mysql" ) == 0 )
- {
- dbfmt = db_mysql;
- }
- else
- {
- usage();
- }
- break;
case 'h':
usage();
break; /* notreached */
- case 'i':
- free( infile );
- infile = strdup( optarg );
- break;
case 'k':
stats.keepers = atoi( optarg );
break;
@@ -173,6 +148,8 @@ int main( int argc, char** argv )
break;
case 't':
mode = mode_test;
+ if (pledge("stdio rpath", NULL) == -1)
+ err(1, "pledge");
break;
case 'v':
g_verbose++;
DIR diff --git a/bmfconv.1 b/bmfconv.1
@@ -1,81 +0,0 @@
-.\"Generated by db2man.xsl. Don't modify this, modify the source.
-.de Sh \" Subsection
-.br
-.if t .Sp
-.ne 5
-.PP
-\fB\\$1\fR
-.PP
-..
-.de Sp \" Vertical space (when we can't use .PP)
-.if t .sp .5v
-.if n .sp
-..
-.de Ip \" List item
-.br
-.ie \\n(.$>=3 .ne \\$3
-.el .ne 3
-.IP "\\$1" \\$2
-..
-.TH "BMFCONV" 1 "" "" ""
-.SH NAME
-bmfconv \- Database converter for bmf
-.SH "SYNOPSIS"
-
-.nf
-\fBbmfconv\fR [-f fmt] [-d db] [-e] [-i] [-v] [-h]
-.fi
-
-.SH "DESCRIPTION"
-
-.PP
-bmfconv converts bmf token databases between the supported formats. It can import flat text files into databases and export databases into flat text files.
-
-.PP
-PLEASE NOTE that the text files used in import and export operations are read and written in the current directory.
-
-.SH "OPTIONS"
-
-.PP
-\fB-f fmt\fR Specify database format. Supported formats are "db" for libdb and "mysql" for MySQL.
-
-.PP
-\fB-d db\fR Specify database name.
-
-.PP
-\fB-e\fR Export the database to text files.
-
-.PP
-\fB-i\fR Import the database from text files.
-
-.PP
-\fB-v\fR Display version information.
-
-.PP
-\fB-h\fR Display usage information.
-
-.SH "RETURN VALUES"
-
-.PP
-0 if conversion succeeds, nonzero if conversion fails.
-
-.SH "FILES"
-
-.TP
-\fIgoodlist.txt\fR
-Text file for import or export of good tokens.
-
-.TP
-\fIspamlist.txt\fR
-Text file for import or export of spam tokens.
-
-.SH "BUGS"
-
-.PP
-Should be more robust.
-
-.SH "AUTHOR"
-
-.PP
-Tom Marshall <tommy@tig-grr.com>. bmfconv is a part of the bmf package.
-
DIR diff --git a/bmfconv.c b/bmfconv.c
@@ -1,169 +0,0 @@
-/* $Id: bmfconv.c,v 1.9 2002/10/20 18:19:17 tommy Exp $ */
-
-/*
- * Copyright (c) 2002 Tom Marshall <tommy@tig-grr.com>
- *
- * This program is free software. It may be distributed under the terms
- * in the file LICENSE, found in the top level of the distribution.
- *
- * bmfconv.c: bmf database converter
- */
-
-#include "config.h"
-#include "dbg.h"
-#include "str.h"
-#include "vec.h"
-#include "dbh.h"
-
-typedef enum
-{
- none,
- db2text,
- text2db
-} dir_t;
-
-static void usage( void )
-{
- printf( "\n"
- "Usage: " PACKAGE " [options]\n"
- "\t-f fmt\tSpecify database format (db|mysql).\n"
- "\t-d db\tSpecify database or directory name.\n"
- "\t-e\tExport to text files goodlist.txt and spamlist.txt.\n"
- "\t-i\tImport from text files goodlist.txt and spamlist.txt.\n"
- "\t-v\tShow version information and exit\n"
- "\t-h\tShow this message and exit\n"
- "\n" );
- exit( 2 );
-}
-
-static void version( void )
-{
- printf( "\n"
- PACKAGE " version " VERSION " - a Bayesian mail filter\n"
- "Copyright (c) 2002 Tom Marshall\n"
- "\n"
- PACKAGE " comes with ABSOLUTELY NO WARRANTY.\n"
- "This is free software. You are welcome to redistribute it under the terms\n"
- "of the GNU General Public License. See the file LICENSE in the source\n"
- "distribution, or visit http://www.gnu.org/licenses/gpl.html\n"
- "\n" );
- exit( 2 );
-}
-
-int main( int argc, char** argv )
-{
- int ch;
- dbfmt_t dbfmt = db_db;
- char* dbname = NULL;
- bool_t rdonly;
-
- dbh_t* pdb;
- dbt_t* ptable;
- dir_t dir = none;
-
- while( (ch = getopt( argc, argv, "d:ef:ihv" )) != EOF )
- {
- switch( ch )
- {
- case 'd':
- free( dbname );
- dbname = strdup( optarg );
- break;
- case 'e':
- dir = db2text;
- break;
- case 'f':
- if( strcasecmp( optarg, "db" ) == 0 )
- {
- dbfmt = db_db;
- }
- else if( strcasecmp( optarg, "mysql" ) == 0 )
- {
- dbfmt = db_mysql;
- }
- else
- {
- usage();
- }
- break;
- case 'h':
- usage();
- break; /* notreached */
- case 'i':
- dir = text2db;
- break;
- case 'v':
- version();
- break; /* notreached */
- default:
- usage();
- }
- }
- if( dir == none )
- {
- usage();
- }
-
- pdb = dbh_open( dbfmt, "localhost", dbname, DB_USER, DB_PASS );
- if( pdb == NULL )
- {
- fprintf( stderr, "cannot open database\n" );
- exit( 1 );
- }
- rdonly = (dir == db2text ? true : false);
-
- ptable = pdb->opentable( pdb, "spamlist", rdonly );
- if( ptable == NULL )
- {
- fprintf( stderr, "cannot open spamlist\n" );
- exit( 1 );
- }
- if( dir == db2text )
- {
- if( !ptable->export( ptable, "spamlist.txt" ) )
- {
- fprintf( stderr, "cannot export spamlist\n" );
- exit( 1 );
- }
- }
- else
- {
- if( !ptable->import( ptable, "spamlist.txt" ) )
- {
- fprintf( stderr, "cannot import spamlist\n" );
- exit( 1 );
- }
- }
- ptable->close( ptable );
- free( ptable );
-
- ptable = pdb->opentable( pdb, "goodlist", rdonly );
- if( ptable == NULL )
- {
- fprintf( stderr, "cannot open goodlist\n" );
- exit( 1 );
- }
- if( dir == db2text )
- {
- if( !ptable->export( ptable, "goodlist.txt" ) )
- {
- fprintf( stderr, "cannot export goodlist\n" );
- exit( 1 );
- }
- }
- else
- {
- if( !ptable->import( ptable, "goodlist.txt" ) )
- {
- fprintf( stderr, "cannot import goodlist\n" );
- exit( 1 );
- }
- }
- ptable->close( ptable );
- free( ptable );
-
- pdb->close( pdb );
- free( pdb );
-
- return 0;
-}
DIR diff --git a/config.h b/config.h
@@ -10,6 +10,8 @@
#ifndef _CONFIG_H
#define _CONFIG_H
+#include <err.h>
+
/**************************************
* Standard headers
*/
DIR diff --git a/configure b/configure
@@ -1,354 +0,0 @@
-#!/bin/sh
-
-echo ""
-
-# defaults
-DEBUG=no
-with_libdb=test
-with_mysql=test
-
-# parse options
-# --with/--without parsing copied from autoconf's output
-while [ $# -gt 0 ]; do
- case $1 in
- --with-*)
- ac_option=$1
- ac_optarg=`expr "x$ac_option" : 'x[^=]*=\(.*\)'`
- ac_package=`expr "x$ac_option" : 'x-*with-\([^=]*\)'`
- # Reject names that are not valid shell variable names.
- expr "x$ac_package" : ".*[^A-Za-z0-9_-]" >/dev/null &&
- { echo "error: invalid package name: $ac_package"; exit 1; }
- ac_package=`echo $ac_package | sed 's/-/_/g'`
- case $ac_option in
- *=*)
- ac_optarg=`echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"`
- ;;
- *)
- ac_optarg=yes
- ;;
- esac
- eval "with_$ac_package='$ac_optarg'"
- ;;
- --without-*)
- ac_option=$1
- ac_optarg=`expr "x$ac_option" : 'x[^=]*=\(.*\)'`
- ac_package=`expr "x$ac_option" : 'x-*without-\([^=]*\)'`
- # Reject names that are not valid shell variable names.
- expr "x$ac_package" : ".*[^A-Za-z0-9_-]" >/dev/null &&
- { echo "error: invalid package name: $ac_package"; exit 1; }
- ac_package=`echo $ac_package | sed 's/-/_/g'`
- eval "with_$ac_package=no"
- ;;
- --debug=yes|--debug|-d)
- echo "Debug mode enabled."
- with_debug=yes
- ;;
- --debug=no)
- echo "Debug mode disabled."
- with_debug=no
- ;;
- --help|-help|-h)
- echo "usage: $0 [ options ]"
- echo "available options:"
- echo " --debug=yes (or -d) Enable debugging support."
- echo " --debug=no Disable debugging support."
- echo " --with-package Enable support for package in default location."
- echo " --with-package=path Enable support for package installed in path."
- echo " --without-package Disable support for package."
- echo " --help (or -h) Show this message."
- echo ""
- echo "relevant packages:"
- echo " libdb = BerkeleyDB"
- echo " mysql = MySQL database"
- exit 1
- ;;
- *)
- echo "Unknown option '$1', try -h for help"
- exit 1
- ;;
- esac
- shift
-done
-
-echo "Examining system setup..."
-
-# Some known configs:
-#
-# uname -s uname -r uname -m uname -p
-# ======== =========== ======== ========
-# SunOS 5.6 sun4u sparc
-# Linux 2.2.17 i686 unknown
-# FreeBSD 4.1-RELEASE i386 i386
-
-UNAME_S=`uname -s`
-UNAME_R=`uname -r`
-
-case "$UNAME_S" in
- Linux)
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g"
- LDDBG="-g"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=gcc
- CFLAGS="$CCDBG -D_UNIX -D_LINUX -Wall"
- CXX=g++
- CXXFLAGS=${CFLAGS}
- AR=ar
- ARFLAGS="-rc"
- LD=gcc
- LDFLAGS="$LDDBG"
- SYSLIBS=""
- LIBDB_LIB="-ldb"
- MYSQL_LIB="-lmysqlclient"
- ;;
- FreeBSD)
- case "$UNAME_R" in
- 2.*)
- OSVER=20
- ;;
- 3.*)
- OSVER=30
- ;;
- 4.*)
- OSVER=40
- ;;
- *)
- # Assume 5.0 +
- OSVER=50
- ;;
- esac
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g"
- LDDBG="-g"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=gcc
- CFLAGS="$CCDBG -D_UNIX -D_BSD=$OSVER -Wall"
- CXX=g++
- CXXFLAGS=${CFLAGS}
- AR=ar
- ARFLAGS="-rc"
- LD=gcc
- LDFLAGS="$LDDBG"
- SYSLIBS=""
- LIBDB_LIB=""
- MYSQL_LIB="-lmysqlclient"
- ;;
- OpenBSD)
- # I'm guessing OpenBSD looks mostly like FreeBSD 4.x
- OSVER=40
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g"
- LDDBG="-g"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=gcc
- CFLAGS="$CCDBG -D_UNIX -D_BSD=$OSVER -Wall"
- CXX=g++
- CXXFLAGS=${CFLAGS}
- AR=ar
- ARFLAGS="-rc"
- LD=gcc
- LDFLAGS="$LDDBG"
- SYSLIBS=""
- LIBDB_LIB=""
- MYSQL_LIB="-lmysqlclient"
- ;;
- Darwin)
- # I'm guessing Darwin looks mostly like FreeBSD 4.x
- OSVER=40
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g"
- LDDBG="-g"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=cc
- CFLAGS="$CCDBG -D_UNIX -D_BSD=$OSVER -DNOLOCK -Wall"
- CXX=c++
- CXXFLAGS=${CFLAGS}
- AR=ar
- ARFLAGS="-rc"
- LD=cc
- LDFLAGS="$LDDBG"
- SYSLIBS=""
- LIBDB_LIB=""
- MYSQL_LIB="-lmysqlclient"
- ;;
- SunOS)
- case "$UNAME_R" in
- 5.6)
- OSVER=56
- ;;
- 5.7)
- OSVER=57
- ;;
- 5.8)
- OSVER=58
- ;;
- *)
- # Assume 9.0+
- OSVER=59
- ;;
- esac
- # Prefer gcc to the native cc here because I haven't tested with the
- # native compiler yet.
- type gcc >/dev/null 2>&1
- if [ $? -eq 0 ]; then
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g"
- LDDBG="-g"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=gcc
- CFLAGS="$CCDBG -D_UNIX -D_SOLARIS=$OSVER -Wall"
- CXX=g++
- CXXFLAGS=${CFLAGS}
- LD=gcc
- LDFLAGS="$LDDBG"
- else
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g"
- LDDBG="-g"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=cc
- CFLAGS="-DNDEBUG -D_UNIX -D_SOLARIS=$OSVER"
- CXX=c++
- CXXFLAGS=${CFLAGS}
- LD=ld
- LDFLAGS=""
- fi
- AR=ar
- ARFLAGS="-rc"
- SYSLIBS=""
- LIBDB_LIB="-ldb"
- MYSQL_LIB="-lmysqlclient"
- ;;
- OSF1)
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g2"
- LDDBG="-g2"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=cc
- CFLAGS="$CCDBG -D_UNIX -D_OSF"
- CXX=cxx
- CXXFLAGS="-noexceptions ${CFLAGS}"
- AR=ar
- ARFLAGS="-rc"
- LD=ld
- LDFLAGS=""
- SYSLIBS="-lm"
- LIBDB_LIB="-ldb"
- MYSQL_LIB="-lmysqlclient"
- ;;
- *)
- if [ "$with_debug" = "yes" ]; then
- CCDBG="-g"
- LDDBG="-g"
- else
- CCDBG="-DNDEBUG"
- LDDBG=""
- fi
- CC=cc
- CFLAGS="$CCDBG -DNDEBUG -D_UNIX"
- CXX=c++
- CXXFLAGS=${CFLAGS}
- AR=ar
- ARFLAGS="-rc"
- LD=ld
- LDFLAGS="$LDDBG"
- SYSLIBS=""
- LIBDB_LIB="-ldb"
- MYSQL_LIB="-lmysqlclient"
- ;;
-esac
-
-echo -n "Looking for compiler... "
-type $CC >/dev/null 2>&1
-if [ $? -ne 0 ]; then
- echo "compiler '$CC' not found!"
- exit 1
-else
- echo "$CC is executable."
-fi
-
-echo -n "Checking for BerkeleyDB... "
-if [ "$with_libdb" = "test" ]; then
- if [ -e /usr/local/BerkeleyDB.4.1/include/db.h ]; then
- with_libdb=/usr/local/BerkeleyDB.4.1
- LIBDB_LIB="-ldb"
- elif [ -e /usr/include/db.h -o \
- -e /usr/local/include/db.h ]; then
- with_libdb=yes
- else
- with_libdb=no
- fi
-fi
-if [ "$with_libdb" = "no" ]; then
- echo "disabled."
-else
- if [ "$with_libdb" != "yes" ]; then
- CFLAGS="$CFLAGS -I$with_libdb/include"
- LDFLAGS="$LDFLAGS -L$with_libdb/lib"
- fi
- CFLAGS="$CFLAGS -DHAVE_LIBDB"
- LDFLAGS="$LDFLAGS $LIBDB_LIB"
- echo "enabled."
-fi
-
-echo -n "Checking for MySQL... "
-if [ "$with_mysql" = "test" ]; then
- type mysql_config >/dev/null 2>&1
- if [ $? -eq 0 ]; then
- with_mysql=yes
- CFLAGS="$CFLAGS `mysql_config --cflags`"
- LDFLAGS="$LDFLAGS `mysql_config --libs`"
- # mysql_config will add -lmysqlclient, don't add it twice
- MYSQL_LIB=""
- else
- with_mysql=no
- fi
-fi
-if [ "$with_mysql" = "no" ]; then
- echo "disabled."
-else
- if [ "$with_mysql" != "yes" ]; then
- CFLAGS="$CFLAGS -I$with_mysql/include"
- LDFLAGS="$LDFLAGS -L$with_mysql/lib"
- fi
- CFLAGS="$CFLAGS -DHAVE_MYSQL"
- LDFLAGS="$LDFLAGS $MYSQL_LIB"
- echo "enabled."
-fi
-
-for D in .; do
- cat $D/Makefile.in | sed "s%@CC@%${CC}%g
- s%@CXX@%${CXX}%g
- s%@AR@%${AR}%g
- s%@LD@%${LD}%g
- s%@CFLAGS@%${CFLAGS}%g
- s%@CXXFLAGS@%${CXXFLAGS}%g
- s%@ARFLAGS@%${ARFLAGS}%g
- s%@LDFLAGS@%${LDFLAGS}%g
- s%@SYSLIBS@%${SYSLIBS}%" > $D/Makefile || exit 1
-done
-
-echo "Configuration successful."
-echo "Now run 'make all' and 'make install'."
-echo ""
DIR diff --git a/dbdb.c b/dbdb.c
@@ -18,625 +18,11 @@
#include "dbh.h"
#include "dbdb.h"
-#ifdef HAVE_LIBDB
-
-#define DBT_init( pdbt ) memset( pdbt, 0, sizeof(DBT) )
-
-#if !defined(DB_VERSION_MAJOR) /* v1 */
-#define dbx_get(dbp,kp,vp) dbp->get( dbp, kp, vp, 0 )
-#define dbx_put(dbp,kp,vp) dbp->put( dbp, kp, vp, 0 )
-#define dbx_fd(dbp,fd) fd = dbp->fd( dbp )
-#else /* v2+ */
-#define dbx_get(dbp,kp,vp) dbp->get( dbp, NULL, kp, vp, 0 )
-#define dbx_put(dbp,kp,vp) dbp->put( dbp, NULL, kp, vp, 0 )
-#define dbx_fd(dbp,fd) dbp->fd( dbp, &fd )
-#endif /* DB_VERSION_MAJOR */
-
-#if !defined(DB_VERSION_MAJOR) /* v1 */
-typedef DB DBC; /* no separate cursor type */
-#define dbx_createcursor(dbp,dbcp) ((dbcp = dbp) ? 0 : -1)
-#define dbx_destroycursor(dbcp) (dbcp = NULL)
-#define dbx_first(dbcp,kp,vp) dbcp->seq(dbcp,kp,vp,R_FIRST)
-#define dbx_next(dbcp,kp,vp) dbcp->seq(dbcp,kp,vp,R_NEXT)
-#define dbx_prev(dbcp,kp,vp) dbcp->seq(dbcp,kp,vp,R_PREV)
-#define dbx_last(dbcp,kp,vp) dbcp->seq(dbcp,kp,vp,R_LAST)
-#elif DB_VERSION_MAJOR == 2
-#define dbx_createcursor(dbp,dbcp) dbp->cursor(dbp,NULL,&csrp)
-#define dbx_destroycursor(dbcp) dbcp->c_close(dbcp)
-#define dbx_first(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_FIRST)
-#define dbx_next(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_NEXT)
-#define dbx_prev(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_PREV)
-#define dbx_last(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_LAST)
-#else /* v3+ */
-#define dbx_createcursor(dbp,dbcp) dbp->cursor(dbp,NULL,&csrp,0)
-#define dbx_destroycursor(dbcp) dbcp->c_close(dbcp)
-#define dbx_first(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_FIRST)
-#define dbx_next(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_NEXT)
-#define dbx_prev(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_PREV)
-#define dbx_last(dbcp,kp,vp) dbcp->c_get(dbcp,kp,vp,DB_LAST)
-#endif /* DB_VERSION_MAJOR */
-
-static void char2DBT( DBT* pdbt, char* p )
-{
- pdbt->data = p;
- pdbt->size = strlen(p);
-}
-
-static void uint2DBT( DBT* pdbt, uint* p )
-{
- pdbt->data = p;
- pdbt->size = sizeof(uint);
-}
-
-static uint DBT2uint( DBT* pdbt )
-{
- uint n;
- memcpy( &n, pdbt->data, sizeof(n) );
- return n;
-}
-
-dbh_t* dbdb_db_open( cpchar dbhost, cpchar dbname, cpchar dbuser, cpchar dbpass )
-{
- dbhdb_t* pthis;
-
- uint dirlen;
- cpchar phome;
- struct stat st;
-
- pthis = (dbhdb_t*)malloc( sizeof(dbhdb_t) );
- if( pthis == NULL )
- {
- goto bail;
- }
- pthis->close = dbdb_db_close;
- pthis->opentable = dbdb_db_opentable;
- if( dbname != NULL && *dbname != '\0' )
- {
- dirlen = strlen( dbname );
- pthis->dir = strdup( dbname );
- if( pthis->dir[dirlen-1] == '/' )
- {
- pthis->dir[dirlen-1] = '\0';
- }
- }
- else
- {
- phome = getenv( "HOME" );
- if( phome == NULL || *phome == '\0' )
- {
- phome = ".";
- }
- pthis->dir = (char*)malloc( strlen(phome)+5+1 );
- if( pthis->dir == NULL )
- {
- goto bail;
- }
- sprintf( pthis->dir, "%s/.bmf", phome );
- }
-
- /* ensure config directory exists */
- if( stat( pthis->dir, &st ) != 0 )
- {
- if( errno == ENOENT )
- {
- if( mkdir( pthis->dir, S_IRUSR|S_IWUSR|S_IXUSR ) != 0 )
- {
- goto bail;
- }
- }
- else
- {
- goto bail;
- }
- }
- else
- {
- if( !S_ISDIR( st.st_mode ) )
- {
- goto bail;
- }
- }
-
-#if !defined(DB_VERSION_MAJOR) || DB_VERSION_MAJOR < 3
- /* no initialization */
-#else /* DB_VERSION_MAJOR >= 3 */
- if( db_env_create( &pthis->envp, 0 ) != 0 )
- {
- goto bail;
- }
- if( pthis->envp->open( pthis->envp, pthis->dir, DB_INIT_LOCK|DB_INIT_MPOOL|DB_CREATE, 0644 ) != 0 )
- {
- goto bail;
- }
-#endif /* DB_VERSION_MAJOR */
-
- return (dbh_t*)pthis;
-
-bail:
- free( pthis );
- return NULL;
-}
-
-bool_t dbdb_db_close( dbhdb_t* pthis )
-{
-#if !defined(DB_VERSION_MAJOR) || DB_VERSION_MAJOR < 3
- /* no cleanup */
-#else /* DB_VERSION_MAJOR >= 3 */
- pthis->envp->close( pthis->envp, 0 );
-#endif /* DB_VERSION_MAJOR */
-
- free( pthis->dir );
- pthis->dir = NULL;
-
- return true;
-}
-
-dbt_t* dbdb_db_opentable( dbhdb_t* pthis, cpchar table, bool_t rdonly )
-{
- dbtdb_t* ptable;
- DB* dbp;
- DBT key;
- DBT val;
-
- char szpath[PATH_MAX];
-
- ptable = (dbtdb_t*)malloc( sizeof(dbtdb_t) );
- if( ptable == NULL )
- {
- return NULL;
- }
- ptable->close = dbdb_table_close;
- ptable->mergeclose = dbdb_table_mergeclose;
- ptable->unmergeclose = dbdb_table_unmergeclose;
- ptable->import = dbdb_table_import;
- ptable->export = dbdb_table_export;
- ptable->getmsgcount = dbdb_table_getmsgcount;
- ptable->getcount = dbdb_table_getcount;
- ptable->dbp = NULL;
-
- sprintf( szpath, "%s/%s.db", pthis->dir, table );
-#if !defined(DB_VERSION_MAJOR)
- if( (dbp = dbopen( szpath, O_CREAT|O_RDWR, 0644, DB_BTREE, NULL)) == NULL )
- {
- goto bail;
- }
-#elif DB_VERSION_MAJOR == 2
- if( db_open( szpath, DB_BTREE, DB_CREATE, 0644, NULL, NULL, &dbp ) != 0 )
- {
- goto bail;
- }
-#elif (DB_VERSION_MAJOR == 3) || (DB_VERSION_MAJOR == 4 && DB_VERSION_MINOR == 0)
- ptable->envp = pthis->envp;
- if( db_create( &dbp, NULL, 0 ) != 0 )
- {
- goto bail;
- }
- if( dbp->open( dbp, szpath, NULL, DB_BTREE, DB_CREATE, 0644 ) != 0 )
- {
- goto bail;
- }
-#else /* v4.1+ */
- ptable->envp = pthis->envp;
- if( db_create( &dbp, NULL, 0 ) != 0 )
- {
- goto bail;
- }
- if( dbp->open( dbp, NULL, szpath, NULL, DB_BTREE, DB_CREATE, 0644 ) != 0 )
- {
- goto bail;
- }
-#endif /* DB_VERSION_MAJOR */
- ptable->dbp = dbp;
-
- DBT_init( &key );
- DBT_init( &val );
- ptable->nmsgs = 0;
- char2DBT( &key, MSGCOUNT_KEY );
- if( dbx_get( dbp, &key, &val ) == 0 )
- {
- ptable->nmsgs = DBT2uint( &val );
- }
-
- return (dbt_t*)ptable;
-
-bail:
- free( ptable );
- return NULL;
-}
-
-static bool_t dbdb_table_lock( dbtdb_t* pthis )
-{
-#ifndef NOLOCK
- struct flock lock;
- int fd;
-
- dbx_fd( pthis->dbp, fd );
- memset( &lock, 0, sizeof(lock) );
- lock.l_type = F_WRLCK;
- lock.l_start = 0;
- lock.l_whence = SEEK_SET;
- lock.l_len = 0;
- if( fcntl( fd, F_SETLKW, &lock ) != 0 )
- {
- return false;
- }
-#endif /* ndef NOLOCK */
- return true;
-}
-
-static bool_t dbdb_table_unlock( dbtdb_t* pthis )
-{
-#ifndef NOLOCK
- struct flock lock;
- int fd;
-
- dbx_fd( pthis->dbp, fd );
- memset( &lock, 0, sizeof(lock) );
- lock.l_type = F_UNLCK;
- lock.l_start = 0;
- lock.l_whence = SEEK_SET;
- lock.l_len = 0;
- if( fcntl( fd, F_SETLK, &lock ) != 0 )
- {
- return false;
- }
-#endif /* ndef NOLOCK */
- return true;
-}
-
-bool_t dbdb_table_close( dbtdb_t* pthis )
-{
- DB* dbp = pthis->dbp;
-
- if( dbp != NULL )
- {
-#if !defined(DB_VERSION_MAJOR) /* v1 */
- dbp->close( dbp );
-#else /* v2+ */
- dbp->close( dbp, 0 );
-#endif /* DB_VERSION_MAJOR */
- pthis->dbp = NULL;
- }
-
- return true;
-}
-
-bool_t dbdb_table_mergeclose( dbtdb_t* pthis, vec_t* pmsg )
-{
- DB* dbp = pthis->dbp;
- DBT key;
- DBT val;
-
- char szword[MAXWORDLEN+1];
- uint count;
- veciter_t msgiter;
- str_t* pmsgstr;
-
- if( pthis->dbp == NULL )
- {
- return false;
- }
-
- if( !dbdb_table_lock( pthis ) )
- {
- return false;
- }
-
- pthis->nmsgs++;
-
- DBT_init( &key );
- DBT_init( &val );
-
- char2DBT( &key, MSGCOUNT_KEY );
- uint2DBT( &val, &pthis->nmsgs );
- dbx_put( dbp, &key, &val );
-
- vec_first( pmsg, &msgiter );
- pmsgstr = veciter_get( &msgiter );
-
- while( pmsgstr != NULL )
- {
- assert( pmsgstr->len <= MAXWORDLEN );
- strncpylwr( szword, pmsgstr->p, pmsgstr->len );
- szword[pmsgstr->len] = '\0';
- count = db_getnewcount( &msgiter );
-
- char2DBT( &key, szword );
- if( dbx_get( dbp, &key, &val ) == 0 )
- {
- count += DBT2uint( &val );
- }
- char2DBT( &key, szword );
- uint2DBT( &val, &count );
- if( dbx_put( dbp, &key, &val ) != 0 )
- {
- goto bail;
- }
-
- veciter_next( &msgiter );
- pmsgstr = veciter_get( &msgiter );
- }
-
- veciter_destroy( &msgiter );
- dbdb_table_unlock( pthis );
- return dbdb_table_close( pthis );
-
-bail:
- return false;
-}
-
-bool_t dbdb_table_unmergeclose( dbtdb_t* pthis, vec_t* pmsg )
-{
- DB* dbp = pthis->dbp;
- DBT key;
- DBT val;
-
- char szword[MAXWORDLEN+1];
- uint count;
- veciter_t msgiter;
- str_t* pmsgstr;
-
- if( pthis->dbp == NULL )
- {
- return false;
- }
-
- if( pthis->nmsgs > 0 )
- {
- pthis->nmsgs--;
- }
-
- if( !dbdb_table_lock( pthis ) )
- {
- return false;
- }
-
- DBT_init( &key );
- DBT_init( &val );
-
- char2DBT( &key, MSGCOUNT_KEY );
- uint2DBT( &val, &pthis->nmsgs );
- dbx_put( dbp, &key, &val );
-
- vec_first( pmsg, &msgiter );
- pmsgstr = veciter_get( &msgiter );
-
- while( pmsgstr != NULL )
- {
- assert( pmsgstr->len <= MAXWORDLEN );
- strncpylwr( szword, pmsgstr->p, pmsgstr->len );
- szword[pmsgstr->len] = '\0';
- count = db_getnewcount( &msgiter );
-
- char2DBT( &key, szword );
- if( dbx_get( dbp, &key, &val ) == 0 )
- {
- uint n = DBT2uint( &val );
- n = (n > count) ? (n - count) : 0;
- char2DBT( &key, szword );
- uint2DBT( &val, &n );
- if( dbx_put( dbp, &key, &val ) != 0 )
- {
- goto bail;
- }
- }
-
- veciter_next( &msgiter );
- pmsgstr = veciter_get( &msgiter );
- }
-
- veciter_destroy( &msgiter );
- dbdb_table_unlock( pthis );
- return dbdb_table_close( pthis );
-
-bail:
- return false;
-}
-
-bool_t dbdb_table_import( dbtdb_t* pthis, cpchar filename )
-{
- DB* dbp = pthis->dbp;
- int fd;
- struct stat st;
- char* pbuf;
- char* pbegin;
- char* pend;
- rec_t r;
- DBT key;
- DBT val;
- char szword[MAXWORDLEN+1];
-
- if( pthis->dbp == NULL )
- {
- return false;
- }
- if( (fd = open( filename, O_RDONLY, 0644 )) < 0 )
- {
- return false;
- }
- if( fstat( fd, &st ) != 0 )
- {
- goto bail;
- }
- if( st.st_size == 0 )
- {
- goto bail;
- }
- pbuf = (char*)malloc( st.st_size );
- if( pbuf == NULL )
- {
- goto bail;
- }
- if( read( fd, pbuf, st.st_size ) != st.st_size )
- {
- goto bail;
- }
-
- DBT_init( &key );
- DBT_init( &val );
-
- if( sscanf( pbuf, BOGOFILTER_HEADER, &pthis->nmsgs ) != 1 )
- {
- goto bail;
- }
- pbegin = pbuf;
- while( *pbegin != '\n' ) pbegin++;
- pbegin++;
-
- char2DBT( &key, MSGCOUNT_KEY );
- uint2DBT( &val, &pthis->nmsgs );
- if( dbx_put( dbp, &key, &val ) != 0 )
- {
- goto bail;
- }
-
- while( pbegin < pbuf + st.st_size )
- {
- pend = pbegin;
- r.w.p = pbegin;
- r.w.len = 0;
- r.n = 0;
-
- while( *pend != '\n' )
- {
- if( pend >= pbuf + st.st_size )
- {
- goto bail;
- }
- *pend = tolower(*pend);
- if( *pend == ' ' )
- {
- r.w.len = (pend-pbegin);
- r.n = strtol( pend+1, NULL, 10 );
- }
- pend++;
- }
- if( pend > pbegin && *pbegin != '#' && *pbegin != ';' )
- {
- if( r.w.len == 0 || r.w.len > MAXWORDLEN )
- {
- fprintf( stderr, "dbh_loadfile: bad file format\n" );
- goto bail;
- }
- strncpylwr( szword, r.w.p, r.w.len );
- szword[r.w.len] = '\0';
- char2DBT( &key, szword );
- uint2DBT( &val, &r.n );
- if( dbx_put( dbp, &key, &val ) != 0 )
- {
- goto bail;
- }
- }
- pbegin = pend+1;
- }
-
- free( pbuf );
- close( fd );
-
- return true;
-
-bail:
- return false;
-}
-
-bool_t dbdb_table_export( dbtdb_t* pthis, cpchar filename )
-{
- DB* dbp = pthis->dbp;
- int fd;
- char iobuf[IOBUFSIZE];
- char* p;
-
- DBC* csrp;
- int rc;
- DBT key;
- DBT val;
-
- if( (fd = open( filename, O_CREAT|O_WRONLY|O_TRUNC, 0644 )) < 0 )
- {
- goto bail;
- }
- if( dbx_createcursor( dbp, csrp ) != 0 )
- {
- goto bail;
- }
-
- DBT_init( &key );
- DBT_init( &val );
-
- p = iobuf;
- p += sprintf( p, BOGOFILTER_HEADER, pthis->nmsgs );
-
- rc = dbx_first( csrp, &key, &val );
- while( rc == 0 )
- {
- assert( key.data != NULL && key.size <= MAXWORDLEN );
- assert( val.data != NULL && val.size == sizeof(uint) );
- if( key.size != MSGCOUNT_KEY_LEN ||
- memcmp( key.data, MSGCOUNT_KEY, MSGCOUNT_KEY_LEN ) != 0 )
- {
- memcpy( p, key.data, key.size ); p += key.size;
- *p++ = ' ';
- p += sprintf( p, "%u\n", DBT2uint(&val) );
- if( p+TEXTDB_MAXLINELEN > (iobuf+1) )
- {
- write( fd, iobuf, p-iobuf );
- p = iobuf;
- }
- }
- rc = dbx_next( csrp, &key, &val );
- }
- dbx_destroycursor( csrp );
- if( p != iobuf )
- {
- write( fd, iobuf, p-iobuf );
- }
- close( fd );
- return true;
-
-bail:
- return false;
-}
-
-uint dbdb_table_getmsgcount( dbtdb_t* pthis )
-{
- return pthis->nmsgs;
-}
-
-uint dbdb_table_getcount( dbtdb_t* pthis, str_t* pword )
-{
- DB* dbp = pthis->dbp;
- DBT key;
- DBT val;
-
- char szword[MAXWORDLEN+1];
- uint count = 0;
-
- assert( pword->len <= MAXWORDLEN );
- strncpylwr( szword, pword->p, pword->len );
- szword[pword->len] = '\0';
- count = 0;
-
- DBT_init( &key );
- DBT_init( &val );
-
- char2DBT( &key, szword );
- if( dbx_get( dbp, &key, &val ) == 0 )
- {
- count = DBT2uint( &val );
- }
-
- return count;
-}
-
-#else /* def HAVE_LIBDB */
-
dbh_t* dbdb_db_open( cpchar dbhost, cpchar dbname, cpchar dbuser, cpchar dbpass )
{
return NULL;
}
-#endif /* def HAVE_LIBDB */
-
#ifdef UNIT_TEST
int main( int argc, char** argv )
{
DIR diff --git a/dbdb.h b/dbdb.h
@@ -10,52 +10,4 @@
#ifndef _DBDB_H
#define _DBDB_H
-#ifdef HAVE_LIBDB
-
-#include <db.h>
-
-typedef struct _dbtdb dbtdb_t;
-struct _dbtdb
-{
- bool_t (*close)(dbtdb_t*);
- bool_t (*mergeclose)(dbtdb_t*,vec_t*);
- bool_t (*unmergeclose)(dbtdb_t*,vec_t*);
- bool_t (*import)(dbtdb_t*,cpchar);
- bool_t (*export)(dbtdb_t*,cpchar);
- uint (*getmsgcount)(dbtdb_t*);
- uint (*getcount)(dbtdb_t*,str_t*);
-
- DB* dbp; /* db handle */
-#if defined(DB_VERSION_MAJOR) && DB_VERSION_MAJOR >= 3
- DB_ENV* envp; /* we don't own this */
-#endif /* DB_VERSION_MAJOR */
- uint nmsgs; /* number of messages in table (cached) */
-};
-
-typedef struct _dbhdb dbhdb_t;
-struct _dbhdb
-{
- bool_t (*close)(dbhdb_t*);
- dbt_t* (*opentable)(dbhdb_t*,cpchar,bool_t);
-
- char* dir; /* directory for db files */
-#if defined(DB_VERSION_MAJOR) && DB_VERSION_MAJOR >= 3
- DB_ENV* envp; /* db environment */
-#endif /* DB_VERSION_MAJOR */
-};
-
-dbh_t* dbdb_db_open( cpchar dbhost, cpchar dbname, cpchar dbuser, cpchar dbpass );
-bool_t dbdb_db_close( dbhdb_t* pthis );
-dbt_t* dbdb_db_opentable( dbhdb_t* pthis, cpchar table, bool_t rdonly );
-
-bool_t dbdb_table_close( dbtdb_t* pthis );
-bool_t dbdb_table_mergeclose( dbtdb_t* pthis, vec_t* pmsg );
-bool_t dbdb_table_unmergeclose( dbtdb_t* pthis, vec_t* pmsg );
-bool_t dbdb_table_import( dbtdb_t* pthis, cpchar filename );
-bool_t dbdb_table_export( dbtdb_t* pthis, cpchar filename );
-uint dbdb_table_getmsgcount( dbtdb_t* pthis );
-uint dbdb_table_getcount( dbtdb_t* pthis, str_t* pword );
-
-#endif /* def HAVE_LIBDB */
-
#endif /* ndef _DBDB_H */
DIR diff --git a/dbh.c b/dbh.c
@@ -18,7 +18,6 @@
#include "dbh.h"
#include "dbtext.h"
#include "dbdb.h"
-#include "dbmysql.h"
/*
* get count for new (incoming) word. there may be duplicate entries for the
@@ -60,12 +59,6 @@ dbh_t* dbh_open( dbfmt_t dbfmt, cpchar dbhost, cpchar dbname, cpchar dbuser, cpc
case db_text:
pdb = (dbh_t*)dbtext_db_open( dbhost, dbname, dbuser, dbpass );
break;
- case db_db:
- pdb = (dbh_t*)dbdb_db_open( dbhost, dbname, dbuser, dbpass );
- break;
- case db_mysql:
- pdb = (dbh_t*) dbmysql_db_open( dbhost, dbname, dbuser, dbpass );
- break;
default:
assert(false);
}
DIR diff --git a/dbh.h b/dbh.h
@@ -13,9 +13,7 @@
/* database formats */
typedef enum
{
- db_text, /* flat text */
- db_db, /* libdb */
- db_mysql /* mysql */
+ db_text /* flat text */
} dbfmt_t;
/* record/field structure */
DIR diff --git a/dbmysql.c b/dbmysql.c
@@ -1,545 +0,0 @@
-/* $Id: dbmysql.c,v 1.9 2002/10/14 07:09:51 tommy Exp $ */
-
-/*
- * Copyright (c) 2002 Tom Marshall <tommy@tig-grr.com>
- *
- * This program is free software. It may be distributed under the terms
- * in the file LICENSE, found in the top level of the distribution.
- *
- * dbmysql.c: mysql database handler
- */
-
-#include "config.h"
-#include "dbg.h"
-#include "str.h"
-#include "lex.h"
-#include "vec.h"
-
-#include "dbh.h"
-#include "dbmysql.h"
-
-#ifdef HAVE_MYSQL
-
-#define MAXQUERY 256
-
-static MYSQL* g_mysql = NULL;
-
-static void sql_escape( char* d, const char* s )
-{
- while( *s != '\0' )
- {
- if( *s == '\'' )
- {
- *d++ = '\'';
- }
- *d++ = tolower(*s++);
- }
-}
-
-dbh_t* dbmysql_db_open( cpchar dbhost, cpchar dbname, cpchar dbuser, cpchar dbpass )
-{
- dbhmysql_t* pthis;
-
- if( g_mysql == NULL )
- {
- g_mysql = mysql_init( NULL );
- if( g_mysql == NULL )
- {
- return NULL;
- }
- }
-
- pthis = (dbhmysql_t*)malloc( sizeof(dbhmysql_t) );
- if( pthis == NULL )
- {
- perror( "malloc()" );
- goto bail;
- }
- pthis->close = dbmysql_db_close;
- pthis->opentable = dbmysql_db_opentable;
-
- pthis->dbh = mysql_real_connect( g_mysql, dbhost, dbuser, dbpass, dbname, 0, NULL, 0 );
- if( pthis->dbh == NULL )
- {
- goto bail;
- }
-
-
- return (dbh_t*)pthis;
-
-bail:
- fprintf( stderr, "cannot open mysql database '%s': %s\n", dbname, mysql_error(g_mysql) );
- free( pthis );
- return NULL;
-}
-
-bool_t dbmysql_db_close( dbhmysql_t* pthis )
-{
- if( pthis->dbh != NULL )
- {
- mysql_close( pthis->dbh );
- pthis->dbh = NULL;
- }
- return true;
-}
-
-dbt_t* dbmysql_db_opentable( dbhmysql_t* pthis, cpchar table, bool_t rdonly )
-{
- dbtmysql_t* ptable;
-
- char query[MAXQUERY];
- MYSQL_RES* res;
- MYSQL_ROW row;
-
- ptable = (dbtmysql_t*)malloc( sizeof(dbtmysql_t) );
- if( ptable == NULL )
- {
- return NULL;
- }
- ptable->close = dbmysql_table_close;
- ptable->mergeclose = dbmysql_table_mergeclose;
- ptable->unmergeclose = dbmysql_table_unmergeclose;
- ptable->import = dbmysql_table_import;
- ptable->export = dbmysql_table_export;
- ptable->getmsgcount = dbmysql_table_getmsgcount;
- ptable->getcount = dbmysql_table_getcount;
- ptable->pdb = pthis;
- ptable->table = strdup( table );
- ptable->nmsgs = 0;
-
- sprintf( query, "SELECT count FROM %s WHERE name='%s'",
- table, MSGCOUNT_KEY );
- if( mysql_query( pthis->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( (res = mysql_store_result( pthis->dbh )) == NULL )
- {
- goto bail;
- }
- while( (row = mysql_fetch_row( res )) )
- {
- ptable->nmsgs = atoi( row[0] );
- }
-
- return (dbt_t*)ptable;
-
-bail:
- free( ptable->table );
- free( ptable );
- return NULL;
-}
-
-bool_t dbmysql_table_close( dbtmysql_t* pthis )
-{
- if( pthis->pdb != NULL )
- {
- free( pthis->table );
- pthis->table = NULL;
- pthis->pdb = NULL;
- }
- return true;
-}
-
-bool_t dbmysql_table_mergeclose( dbtmysql_t* pthis, vec_t* pmsg )
-{
- char szword[MAXWORDLEN+1];
- char szsqlword[MAXWORDLEN*2+1];
- veciter_t msgiter;
- str_t* pmsgstr;
-
- char query[MAXQUERY];
- uint count;
-
- if( pthis->pdb == NULL || pthis->pdb->dbh == NULL )
- {
- assert( false );
- return false;
- }
-
- pthis->nmsgs++;
-
- sprintf( query, "UPDATE %s SET count=%u WHERE name='%s'",
- pthis->table, pthis->nmsgs, MSGCOUNT_KEY );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- sprintf( query, "INSERT INTO %s ( name, count ) VALUES ( '%s', %u )",
- pthis->table, MSGCOUNT_KEY, pthis->nmsgs );
- mysql_query( pthis->pdb->dbh, query );
- }
-
- vec_first( pmsg, &msgiter );
- pmsgstr = veciter_get( &msgiter );
-
- while( pmsgstr != NULL )
- {
- assert( pmsgstr->len <= MAXWORDLEN );
- strncpylwr( szword, pmsgstr->p, pmsgstr->len );
- szword[pmsgstr->len] = '\0';
- sql_escape( szsqlword, szword );
- count = db_getnewcount( &msgiter );
-
- sprintf( query, "UPDATE %s SET count=count+%u WHERE name='%s'",
- pthis->table, count, szsqlword );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- sprintf( query, "INSERT INTO %s ( name, count ) VALUES ( '%s', %u )",
- pthis->table, szsqlword, count );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- goto bail;
- }
- }
-
- veciter_next( &msgiter );
- pmsgstr = veciter_get( &msgiter );
- }
-
- veciter_destroy( &msgiter );
- return dbmysql_table_close( pthis );
-
-bail:
- return false;
-}
-
-bool_t dbmysql_table_unmergeclose( dbtmysql_t* pthis, vec_t* pmsg )
-{
- char szword[MAXWORDLEN+1];
- char szsqlword[MAXWORDLEN*2+1];
- veciter_t msgiter;
- str_t* pmsgstr;
-
- char query[MAXQUERY];
- uint count;
-
- if( pthis->pdb == NULL || pthis->pdb->dbh == NULL )
- {
- assert( false );
- return false;
- }
-
- if( pthis->nmsgs > 0 )
- {
- pthis->nmsgs--;
- }
-
- sprintf( query, "UPDATE %s SET count=%u WHERE name='%s'",
- pthis->table, pthis->nmsgs, MSGCOUNT_KEY );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- sprintf( query, "INSERT INTO %s ( name, count ) VALUES ( '%s', %u )",
- pthis->table, MSGCOUNT_KEY, pthis->nmsgs );
- mysql_query( pthis->pdb->dbh, query );
- }
-
- vec_first( pmsg, &msgiter );
- pmsgstr = veciter_get( &msgiter );
-
- while( pmsgstr != NULL )
- {
- assert( pmsgstr->len <= MAXWORDLEN );
- strncpylwr( szword, pmsgstr->p, pmsgstr->len );
- szword[pmsgstr->len] = '\0';
- sql_escape( szsqlword, szword );
- count = db_getnewcount( &msgiter );
-
- sprintf( query, "UPDATE %s SET count=GREATEST(0,count-%u) WHERE name='%s'",
- pthis->table, count, szsqlword );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- /* this should not happen, so write with count=0 */
- sprintf( query, "INSERT INTO %s ( name, count ) VALUES ( '%s', 0 )",
- pthis->table, szsqlword );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- goto bail;
- }
- }
-
- veciter_next( &msgiter );
- pmsgstr = veciter_get( &msgiter );
- }
-
- veciter_destroy( &msgiter );
- return dbmysql_table_close( pthis );
-
-bail:
- return false;
-}
-
-bool_t dbmysql_table_import( dbtmysql_t* pthis, cpchar filename )
-{
- int fd;
- struct stat st;
- char* pbuf;
- char* pbegin;
- char* pend;
- rec_t r;
- char szword[MAXWORDLEN+1];
- char szsqlword[MAXWORDLEN*2+1];
- char query[MAXQUERY];
-
- if( pthis->pdb == NULL || pthis->pdb->dbh == NULL )
- {
- return false;
- }
- if( (fd = open( filename, O_RDONLY, 0644 )) < 0 )
- {
- return false;
- }
- if( fstat( fd, &st ) != 0 )
- {
- goto bail;
- }
- if( st.st_size == 0 )
- {
- goto bail;
- }
- pbuf = (char*)malloc( st.st_size );
- if( pbuf == NULL )
- {
- goto bail;
- }
- if( read( fd, pbuf, st.st_size ) != st.st_size )
- {
- goto bail;
- }
-
- if( sscanf( pbuf, BOGOFILTER_HEADER, &pthis->nmsgs ) != 1 )
- {
- goto bail;
- }
- pbegin = pbuf;
- while( *pbegin != '\n' ) pbegin++;
- pbegin++;
-
- sprintf( query, "INSERT INTO %s ( name, count ) VALUES ( '%s', %u )",
- pthis->table, MSGCOUNT_KEY, pthis->nmsgs );
- mysql_query( pthis->pdb->dbh, query );
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- goto bail;
- }
-
- while( pbegin < pbuf + st.st_size )
- {
- pend = pbegin;
- r.w.p = pbegin;
- r.w.len = 0;
- r.n = 0;
-
- while( *pend != '\n' )
- {
- if( pend >= pbuf + st.st_size )
- {
- goto bail;
- }
- *pend = tolower(*pend);
- if( *pend == ' ' )
- {
- r.w.len = (pend-pbegin);
- r.n = strtol( pend+1, NULL, 10 );
- }
- pend++;
- }
- if( pend > pbegin && *pbegin != '#' && *pbegin != ';' )
- {
- if( r.w.len == 0 || r.w.len > MAXWORDLEN )
- {
- fprintf( stderr, "dbh_loadfile: bad file format\n" );
- goto bail;
- }
- strncpylwr( szword, r.w.p, r.w.len );
- szword[r.w.len] = '\0';
- sql_escape( szsqlword, szword );
-
- sprintf( query, "INSERT INTO %s ( name, count ) VALUES ( '%s', %u )",
- pthis->table, szsqlword, r.n );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- goto bail;
- }
- }
- pbegin = pend+1;
- }
-
- return true;
-
-bail:
- return false;
-}
-
-bool_t dbmysql_table_export( dbtmysql_t* pthis, cpchar filename )
-{
- int fd;
- char iobuf[IOBUFSIZE];
- char* p;
-
- char query[MAXQUERY];
- MYSQL_RES* res;
- MYSQL_ROW row;
-
- if( (fd = open( filename, O_CREAT|O_WRONLY|O_TRUNC, 0644 )) < 0 )
- {
- return false;
- }
-
- p += sprintf( p, BOGOFILTER_HEADER, pthis->nmsgs );
-
- sprintf( query, "SELECT name, count FROM %s",
- pthis->table );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( mysql_affected_rows( pthis->pdb->dbh ) == 0 )
- {
- goto bail;
- }
-
- while( (row = mysql_fetch_row( res )) )
- {
- if( strcmp( row[0], MSGCOUNT_KEY ) == 0 )
- {
- continue;
- }
-
- p += sprintf( p, "%s %s\n", row[0], row[1] );
- if( p+TEXTDB_MAXLINELEN > (iobuf+1) )
- {
- write( fd, iobuf, p-iobuf );
- p = iobuf;
- }
- }
- if( p != iobuf )
- {
- write( fd, iobuf, p-iobuf );
- }
- close( fd );
-
- return true;
-
-bail:
- return false;
-}
-
-uint dbmysql_table_getmsgcount( dbtmysql_t* pthis )
-{
- return pthis->nmsgs;
-}
-
-uint dbmysql_table_getcount( dbtmysql_t* pthis, str_t* pword )
-{
- uint count = 0;
- char szword[MAXWORDLEN+1];
- char szsqlword[MAXWORDLEN*2+1];
-
- char query[MAXQUERY];
- MYSQL_RES* res;
- MYSQL_ROW row;
-
- assert( pword->len <= MAXWORDLEN );
- strncpylwr( szword, pword->p, pword->len );
- szword[pword->len] = '\0';
- sql_escape( szsqlword, szword );
- sprintf( query, "SELECT count FROM %s WHERE name='%s'",
- pthis->table, szsqlword );
- if( mysql_query( pthis->pdb->dbh, query ) != 0 )
- {
- goto bail;
- }
- if( (res = mysql_store_result( pthis->pdb->dbh )) == NULL )
- {
- goto bail;
- }
- while( (row = mysql_fetch_row( res )) )
- {
- count = atoi( row[0] );
- }
-
-bail:
- return count;
-}
-
-#else /* def HAVE_MYSQL */
-
-dbh_t* dbmysql_db_open( cpchar dbhost, cpchar dbname, cpchar dbuser, cpchar dbpass )
-{
- return NULL;
-}
-
-#endif /* def HAVE_MYSQL */
-
-#ifdef UNIT_TEST
-int main( int argc, char** argv )
-{
- dbh_t* pdb;
- veciter_t iter;
- str_t* pstr;
- uint n;
-
- if( argc != 2 )
- {
- fprintf( stderr, "usage: %s <file>\n", argv[0] );
- return 1;
- }
-
- for( n = 0; n < 100; n++ )
- {
- pdb = dbh_open( "testlist", true );
-
- vec_first( &db, &iter );
- while( (pstr = veciter_get( &iter )) != NULL )
- {
- char buf[MAXWORDLEN+32];
- char* p;
- if( pstr->len > 200 )
- {
- fprintf( stderr, "str too long: %u chars\n", pstr->len );
- break;
- }
- p = buf;
- strcpy( buf, "str: " );
- p += 6;
- memcpy( p, pstr->p, pstr->len );
- p += pstr->len;
- sprintf( p, " %u", pstr->count );
- puts( buf );
-
- veciter_next( &iter );
- }
-
- dbh_close( &db );
- }
-
- return 0;
-}
-#endif /* def UNIT_TEST */
DIR diff --git a/dbmysql.h b/dbmysql.h
@@ -1,60 +0,0 @@
-/* $Id: dbmysql.h,v 1.4 2002/10/06 06:46:53 tommy Exp $ */
-
-/*
- * Copyright (c) 2002 Tom Marshall <tommy@tig-grr.com>
- *
- * This program is free software. It may be distributed under the terms
- * in the file LICENSE, found in the top level of the distribution.
- */
-
-#ifndef _DBMYSQL_H
-#define _DBMYSQL_H
-
-#ifdef HAVE_MYSQL
-
-#include "mysql.h"
-
-typedef struct _dbtmysql dbtmysql_t;
-struct _dbtmysql
-{
- bool_t (*close)(dbtmysql_t*);
- bool_t (*mergeclose)(dbtmysql_t*,vec_t*);
- bool_t (*unmergeclose)(dbtmysql_t*,vec_t*);
- bool_t (*import)(dbtmysql_t*,cpchar);
- bool_t (*export)(dbtmysql_t*,cpchar);
- uint (*getmsgcount)(dbtmysql_t*);
- uint (*getcount)(dbtmysql_t*,str_t*);
-
- struct _dbhmysql* pdb;
- char* table; /* table name */
- uint nmsgs; /* number of messages in table (cached) */
-};
-
-typedef struct _dbhmysql dbhmysql_t;
-struct _dbhmysql
-{
- bool_t (*close)(dbhmysql_t*);
- dbt_t* (*opentable)(dbhmysql_t*,cpchar,bool_t);
-
- MYSQL* dbh; /* database handle, if currently open */
-};
-
-dbh_t* dbmysql_db_open( cpchar dbhost, cpchar dbname, cpchar dbuser, cpchar dbpass );
-bool_t dbmysql_db_close( dbhmysql_t* pthis );
-dbt_t* dbmysql_db_opentable( dbhmysql_t* pthis, cpchar table, bool_t rdonly );
-
-bool_t dbmysql_table_close( dbtmysql_t* pthis );
-bool_t dbmysql_table_mergeclose( dbtmysql_t* pthis, vec_t* pmsg );
-bool_t dbmysql_table_unmergeclose( dbtmysql_t* pthis, vec_t* pmsg );
-bool_t dbmysql_table_import( dbtmysql_t* pthis, cpchar filename );
-bool_t dbmysql_table_export( dbtmysql_t* pthis, cpchar filename );
-uint dbmysql_table_getmsgcount( dbtmysql_t* pthis );
-uint dbmysql_table_getcount( dbtmysql_t* pthis, str_t* pword );
-
-#else /* def HAVE_MYSQL */
-
-dbh_t* dbmysql_db_open( cpchar dbhost, cpchar dbname, cpchar dbuser, cpchar dbpass );
-
-#endif /* def HAVE_MYSQL */
-
-#endif /* ndef _DBMYSQL_H */