Compare commits

...

12 Commits

Author SHA1 Message Date
Olaf Rempel 521a911110 fix configfile 2007-04-17 14:27:25 +02:00
Olaf Rempel be2726a22f subdirs 2007-04-17 14:23:19 +02:00
Olaf Rempel aee280ca5c ildm6 update 2006-12-20 20:47:47 +01:00
Olaf Rempel ce59a8853e rewrite 2006-11-24 21:53:25 +01:00
Olaf Rempel 2363f1de47 drop autotools 2006-11-24 21:52:14 +01:00
Olaf Rempel bfd2d35260 added .gitignore, fix permissions 2006-03-05 14:23:19 +01:00
Olaf Rempel 464d0b352d Version 0.64
- added Quake4 support (d3engine)
- added CoD2 support (q3engine)
- added Rune support (gamespy1)
2006-02-02 16:52:26 +01:00
Olaf Rempel 5c2fc7d1a6 Version 0.63
- added ut2k4 plugin (native scan)
- added Battlefield2 support (gs2 query/host ports)
- added Swat4 Support (gs2)
- fix quake2 plugin
2006-02-02 16:51:01 +01:00
Olaf Rempel 9b62806411 Version 0.62
- use c99 inttypes
- added new Halflife scan (halflife)
- added Battlefield2 support (gamespy2)
2006-02-02 16:49:14 +01:00
Olaf Rempel ddc42a0968 Version 0.61
- reduce per thread stack from 8MB to 64kB (strange pthread_create() defaults..)
2006-02-02 16:48:33 +01:00
Olaf Rempel 90d33bffbf Version 0.60
- added receive-queue
- changed plugin_helper api from void* to uint offsets
- gamespy1 multi-packet response support
- q3engine plugin rewrite
- added halflife plugin
2006-02-02 16:47:20 +01:00
Olaf Rempel 861d41be08 Version 0.53
- code cleanup (mostly doxygen tags)
- added doxygen file
2006-02-02 16:44:46 +01:00
64 changed files with 2364 additions and 43827 deletions

6
.gitignore vendored Normal file
View File

@ -0,0 +1,6 @@
*.d
*.o
*.so
masterquery
hlswmaster
hlswmaster.log

View File

@ -1,3 +1,36 @@
* Thu 22 Dec 2005 Olaf Rempel <razzor@kopf-tisch.de> 0.64
(after Northern LAN Convention Winter 2005, www.northcon.de)
- added Quake4 support (d3engine)
- added CoD2 support (q3engine)
- added Rune support (gamespy1)
* Thu 08 Sep 2005 Olaf Rempel <razzor@kopf-tisch.de> 0.63
(after The Summit 5, www.the-summit.de)
- added ut2k4 plugin (native scan)
- added Battlefield2 support (gs2 query/host ports)
- added Swat4 Support (gs2)
- fix quake2 plugin
* Thu 25 Aug 2005 Olaf Rempel <razzor@kopf-tisch.de> 0.62
(after Multimadness Summer 2005, www.multimadness.de)
- use c99 inttypes
- added new Halflife scan (halflife)
- added Battlefield2 support (gamespy2)
* Sun 05 Jun 2005 Olaf Rempel <razzor@kopf-tisch.de> 0.61
- reduce per thread stack from 8MB to 64kB (strange pthread_create() defaults..)
* Sun 15 May 2005 Olaf Rempel <razzor@kopf-tisch.de> 0.60
- added receive-queue
- changed plugin_helper api from void* to uint offsets
- gamespy1 multi-packet response support
- q3engine plugin rewrite
- added halflife plugin
* Tue 19 Apr 2005 Olaf Rempel <razzor@kopf-tisch.de> 0.53
- code cleanup
- added doxygen file
* Thu 31 Mar 2005 Olaf Rempel <razzor@kopf-tisch.de> 0.52
- games added: avp2, bfv, igi2, jk2, jk3, rtcw, ut2k3, ut2k4
- sendqueue removed (no need to do ratelimiting)

182
INSTALL
View File

@ -1,182 +0,0 @@
Basic Installation
==================
These are generic installation instructions.
The `configure' shell script attempts to guess correct values for
various system-dependent variables used during compilation. It uses
those values to create a `Makefile' in each directory of the package.
It may also create one or more `.h' files containing system-dependent
definitions. Finally, it creates a shell script `config.status' that
you can run in the future to recreate the current configuration, a file
`config.cache' that saves the results of its tests to speed up
reconfiguring, and a file `config.log' containing compiler output
(useful mainly for debugging `configure').
If you need to do unusual things to compile the package, please try
to figure out how `configure' could check whether to do them, and mail
diffs or instructions to the address given in the `README' so they can
be considered for the next release. If at some point `config.cache'
contains results you don't want to keep, you may remove or edit it.
The file `configure.in' is used to create `configure' by a program
called `autoconf'. You only need `configure.in' if you want to change
it or regenerate `configure' using a newer version of `autoconf'.
The simplest way to compile this package is:
1. `cd' to the directory containing the package's source code and type
`./configure' to configure the package for your system. If you're
using `csh' on an old version of System V, you might need to type
`sh ./configure' instead to prevent `csh' from trying to execute
`configure' itself.
Running `configure' takes awhile. While running, it prints some
messages telling which features it is checking for.
2. Type `make' to compile the package.
3. Optionally, type `make check' to run any self-tests that come with
the package.
4. Type `make install' to install the programs and any data files and
documentation.
5. You can remove the program binaries and object files from the
source code directory by typing `make clean'. To also remove the
files that `configure' created (so you can compile the package for
a different kind of computer), type `make distclean'. There is
also a `make maintainer-clean' target, but that is intended mainly
for the package's developers. If you use it, you may have to get
all sorts of other programs in order to regenerate files that came
with the distribution.
Compilers and Options
=====================
Some systems require unusual options for compilation or linking that
the `configure' script does not know about. You can give `configure'
initial values for variables by setting them in the environment. Using
a Bourne-compatible shell, you can do that on the command line like
this:
CC=c89 CFLAGS=-O2 LIBS=-lposix ./configure
Or on systems that have the `env' program, you can do it like this:
env CPPFLAGS=-I/usr/local/include LDFLAGS=-s ./configure
Compiling For Multiple Architectures
====================================
You can compile the package for more than one kind of computer at the
same time, by placing the object files for each architecture in their
own directory. To do this, you must use a version of `make' that
supports the `VPATH' variable, such as GNU `make'. `cd' to the
directory where you want the object files and executables to go and run
the `configure' script. `configure' automatically checks for the
source code in the directory that `configure' is in and in `..'.
If you have to use a `make' that does not supports the `VPATH'
variable, you have to compile the package for one architecture at a time
in the source code directory. After you have installed the package for
one architecture, use `make distclean' before reconfiguring for another
architecture.
Installation Names
==================
By default, `make install' will install the package's files in
`/usr/local/bin', `/usr/local/man', etc. You can specify an
installation prefix other than `/usr/local' by giving `configure' the
option `--prefix=PATH'.
You can specify separate installation prefixes for
architecture-specific files and architecture-independent files. If you
give `configure' the option `--exec-prefix=PATH', the package will use
PATH as the prefix for installing programs and libraries.
Documentation and other data files will still use the regular prefix.
In addition, if you use an unusual directory layout you can give
options like `--bindir=PATH' to specify different values for particular
kinds of files. Run `configure --help' for a list of the directories
you can set and what kinds of files go in them.
If the package supports it, you can cause programs to be installed
with an extra prefix or suffix on their names by giving `configure' the
option `--program-prefix=PREFIX' or `--program-suffix=SUFFIX'.
Optional Features
=================
Some packages pay attention to `--enable-FEATURE' options to
`configure', where FEATURE indicates an optional part of the package.
They may also pay attention to `--with-PACKAGE' options, where PACKAGE
is something like `gnu-as' or `x' (for the X Window System). The
`README' should mention any `--enable-' and `--with-' options that the
package recognizes.
For packages that use the X Window System, `configure' can usually
find the X include and library files automatically, but if it doesn't,
you can use the `configure' options `--x-includes=DIR' and
`--x-libraries=DIR' to specify their locations.
Specifying the System Type
==========================
There may be some features `configure' can not figure out
automatically, but needs to determine by the type of host the package
will run on. Usually `configure' can figure that out, but if it prints
a message saying it can not guess the host type, give it the
`--host=TYPE' option. TYPE can either be a short name for the system
type, such as `sun4', or a canonical name with three fields:
CPU-COMPANY-SYSTEM
See the file `config.sub' for the possible values of each field. If
`config.sub' isn't included in this package, then this package doesn't
need to know the host type.
If you are building compiler tools for cross-compiling, you can also
use the `--target=TYPE' option to select the type of system they will
produce code for and the `--build=TYPE' option to select the type of
system on which you are compiling the package.
Sharing Defaults
================
If you want to set default values for `configure' scripts to share,
you can create a site shell script called `config.site' that gives
default values for variables like `CC', `cache_file', and `prefix'.
`configure' looks for `PREFIX/share/config.site' if it exists, then
`PREFIX/etc/config.site' if it exists. Or, you can set the
`CONFIG_SITE' environment variable to the location of the site script.
A warning: not all `configure' scripts look for a site script.
Operation Controls
==================
`configure' recognizes the following options to control how it
operates.
`--cache-file=FILE'
Use and save the results of the tests in FILE instead of
`./config.cache'. Set FILE to `/dev/null' to disable caching, for
debugging `configure'.
`--help'
Print a summary of the options to `configure', and exit.
`--quiet'
`--silent'
`-q'
Do not print messages saying which checks are being made. To
suppress all normal output, redirect it to `/dev/null' (any error
messages will still be shown).
`--srcdir=DIR'
Look for the package's source code in directory DIR. Usually
`configure' can determine that directory automatically.
`--version'
Print the version of Autoconf used to generate the `configure'
script, and exit.
`configure' also accepts some other, not widely useful, options.

29
Makefile Normal file
View File

@ -0,0 +1,29 @@
VERSION := v2.00
CFLAGS := -O2 -pipe -Wall -Iinclude -DVERSION='"$(VERSION)"'
LDFLAGS := -ldl -rdynamic
OBJS := configfile.o event.o gamelist.o logging.o netpkt.o plugin.o \
plugin_helper.o scanner.o server.o
all: hlswmaster masterquery
make -C plugins all
hlswmaster: $(OBJS) hlswmaster.o
$(CC) $(CFLAGS) $^ $(LDFLAGS) -o $@
masterquery: masterquery.o
$(CC) $(CFLAGS) $^ -o $@
%.o: %.c
$(CC) $(CFLAGS) -c $< -o $@
%.d: %.c
$(CC) $(CFLAGS) -MM -c $< -o $@
clean:
rm -f hlswmaster masterquery *.d *.o *.log
make -C plugins clean
DEPS := $(wildcard *.c)
-include $(DEPS:.c=.d)

View File

@ -1,5 +0,0 @@
AUTOMAKE_OPTIONS = foreign no-dependencies
SUBDIRS = src plugins tools
EXTRA_DIST = TODO autogen.sh hlswmaster.conf

View File

@ -1,602 +0,0 @@
# Makefile.in generated by automake 1.9.4 from Makefile.am.
# @configure_input@
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
# 2003, 2004 Free Software Foundation, Inc.
# This Makefile.in is free software; the Free Software Foundation
# gives unlimited permission to copy and/or distribute it,
# with or without modifications, as long as this notice is preserved.
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
# PARTICULAR PURPOSE.
@SET_MAKE@
srcdir = @srcdir@
top_srcdir = @top_srcdir@
VPATH = @srcdir@
pkgdatadir = $(datadir)/@PACKAGE@
pkglibdir = $(libdir)/@PACKAGE@
pkgincludedir = $(includedir)/@PACKAGE@
top_builddir = .
am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
INSTALL = @INSTALL@
install_sh_DATA = $(install_sh) -c -m 644
install_sh_PROGRAM = $(install_sh) -c
install_sh_SCRIPT = $(install_sh) -c
INSTALL_HEADER = $(INSTALL_DATA)
transform = $(program_transform_name)
NORMAL_INSTALL = :
PRE_INSTALL = :
POST_INSTALL = :
NORMAL_UNINSTALL = :
PRE_UNINSTALL = :
POST_UNINSTALL = :
build_triplet = @build@
host_triplet = @host@
DIST_COMMON = README $(am__configure_deps) $(srcdir)/Makefile.am \
$(srcdir)/Makefile.in $(srcdir)/config.h.in \
$(top_srcdir)/configure AUTHORS COPYING ChangeLog INSTALL NEWS \
TODO config.guess config.sub install-sh ltmain.sh missing
subdir = .
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
am__aclocal_m4_deps = $(top_srcdir)/configure.in
am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
$(ACLOCAL_M4)
am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \
configure.lineno configure.status.lineno
mkinstalldirs = $(install_sh) -d
CONFIG_HEADER = config.h
CONFIG_CLEAN_FILES =
depcomp =
am__depfiles_maybe =
SOURCES =
DIST_SOURCES =
RECURSIVE_TARGETS = all-recursive check-recursive dvi-recursive \
html-recursive info-recursive install-data-recursive \
install-exec-recursive install-info-recursive \
install-recursive installcheck-recursive installdirs-recursive \
pdf-recursive ps-recursive uninstall-info-recursive \
uninstall-recursive
ETAGS = etags
CTAGS = ctags
DIST_SUBDIRS = $(SUBDIRS)
DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
distdir = $(PACKAGE)-$(VERSION)
top_distdir = $(distdir)
am__remove_distdir = \
{ test ! -d $(distdir) \
|| { find $(distdir) -type d ! -perm -200 -exec chmod u+w {} ';' \
&& rm -fr $(distdir); }; }
DIST_ARCHIVES = $(distdir).tar.gz
GZIP_ENV = --best
distuninstallcheck_listfiles = find . -type f -print
distcleancheck_listfiles = find . -type f -print
ACLOCAL = @ACLOCAL@
AMDEP_FALSE = @AMDEP_FALSE@
AMDEP_TRUE = @AMDEP_TRUE@
AMTAR = @AMTAR@
AR = @AR@
AUTOCONF = @AUTOCONF@
AUTOHEADER = @AUTOHEADER@
AUTOMAKE = @AUTOMAKE@
AWK = @AWK@
CC = @CC@
CCDEPMODE = @CCDEPMODE@
CFLAGS = @CFLAGS@
CPP = @CPP@
CPPFLAGS = @CPPFLAGS@
CXX = @CXX@
CXXCPP = @CXXCPP@
CXXDEPMODE = @CXXDEPMODE@
CXXFLAGS = @CXXFLAGS@
CYGPATH_W = @CYGPATH_W@
DEFS = @DEFS@
DEPDIR = @DEPDIR@
ECHO = @ECHO@
ECHO_C = @ECHO_C@
ECHO_N = @ECHO_N@
ECHO_T = @ECHO_T@
EGREP = @EGREP@
EXEEXT = @EXEEXT@
F77 = @F77@
FFLAGS = @FFLAGS@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_SCRIPT = @INSTALL_SCRIPT@
INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
LDFLAGS = @LDFLAGS@
LIBOBJS = @LIBOBJS@
LIBS = @LIBS@
LIBTOOL = @LIBTOOL@
LN_S = @LN_S@
LTLIBOBJS = @LTLIBOBJS@
MAINT = @MAINT@
MAINTAINER_MODE_FALSE = @MAINTAINER_MODE_FALSE@
MAINTAINER_MODE_TRUE = @MAINTAINER_MODE_TRUE@
MAKEINFO = @MAKEINFO@
OBJEXT = @OBJEXT@
PACKAGE = @PACKAGE@
PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
PACKAGE_NAME = @PACKAGE_NAME@
PACKAGE_STRING = @PACKAGE_STRING@
PACKAGE_TARNAME = @PACKAGE_TARNAME@
PACKAGE_VERSION = @PACKAGE_VERSION@
PATH_SEPARATOR = @PATH_SEPARATOR@
RANLIB = @RANLIB@
SET_MAKE = @SET_MAKE@
SHELL = @SHELL@
STRIP = @STRIP@
VERSION = @VERSION@
ac_ct_AR = @ac_ct_AR@
ac_ct_CC = @ac_ct_CC@
ac_ct_CXX = @ac_ct_CXX@
ac_ct_F77 = @ac_ct_F77@
ac_ct_RANLIB = @ac_ct_RANLIB@
ac_ct_STRIP = @ac_ct_STRIP@
am__fastdepCC_FALSE = @am__fastdepCC_FALSE@
am__fastdepCC_TRUE = @am__fastdepCC_TRUE@
am__fastdepCXX_FALSE = @am__fastdepCXX_FALSE@
am__fastdepCXX_TRUE = @am__fastdepCXX_TRUE@
am__include = @am__include@
am__leading_dot = @am__leading_dot@
am__quote = @am__quote@
am__tar = @am__tar@
am__untar = @am__untar@
bindir = @bindir@
build = @build@
build_alias = @build_alias@
build_cpu = @build_cpu@
build_os = @build_os@
build_vendor = @build_vendor@
datadir = @datadir@
exec_prefix = @exec_prefix@
host = @host@
host_alias = @host_alias@
host_cpu = @host_cpu@
host_os = @host_os@
host_vendor = @host_vendor@
includedir = @includedir@
infodir = @infodir@
install_sh = @install_sh@
libdir = @libdir@
libexecdir = @libexecdir@
localstatedir = @localstatedir@
mandir = @mandir@
mkdir_p = @mkdir_p@
oldincludedir = @oldincludedir@
prefix = @prefix@
program_transform_name = @program_transform_name@
sbindir = @sbindir@
sharedstatedir = @sharedstatedir@
sysconfdir = @sysconfdir@
target_alias = @target_alias@
AUTOMAKE_OPTIONS = foreign no-dependencies
SUBDIRS = src plugins tools
EXTRA_DIST = TODO autogen.sh hlswmaster.conf
all: config.h
$(MAKE) $(AM_MAKEFLAGS) all-recursive
.SUFFIXES:
am--refresh:
@:
$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps)
@for dep in $?; do \
case '$(am__configure_deps)' in \
*$$dep*) \
echo ' cd $(srcdir) && $(AUTOMAKE) --foreign '; \
cd $(srcdir) && $(AUTOMAKE) --foreign \
&& exit 0; \
exit 1;; \
esac; \
done; \
echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign Makefile'; \
cd $(top_srcdir) && \
$(AUTOMAKE) --foreign Makefile
.PRECIOUS: Makefile
Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
@case '$?' in \
*config.status*) \
echo ' $(SHELL) ./config.status'; \
$(SHELL) ./config.status;; \
*) \
echo ' cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe)'; \
cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe);; \
esac;
$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
$(SHELL) ./config.status --recheck
$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
cd $(srcdir) && $(AUTOCONF)
$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
cd $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS)
config.h: stamp-h1
@if test ! -f $@; then \
rm -f stamp-h1; \
$(MAKE) stamp-h1; \
else :; fi
stamp-h1: $(srcdir)/config.h.in $(top_builddir)/config.status
@rm -f stamp-h1
cd $(top_builddir) && $(SHELL) ./config.status config.h
$(srcdir)/config.h.in: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
cd $(top_srcdir) && $(AUTOHEADER)
rm -f stamp-h1
touch $@
distclean-hdr:
-rm -f config.h stamp-h1
mostlyclean-libtool:
-rm -f *.lo
clean-libtool:
-rm -rf .libs _libs
distclean-libtool:
-rm -f libtool
uninstall-info-am:
# This directory's subdirectories are mostly independent; you can cd
# into them and run `make' without going through this Makefile.
# To change the values of `make' variables: instead of editing Makefiles,
# (1) if the variable is set in `config.status', edit `config.status'
# (which will cause the Makefiles to be regenerated when you run `make');
# (2) otherwise, pass the desired values on the `make' command line.
$(RECURSIVE_TARGETS):
@set fnord $$MAKEFLAGS; amf=$$2; \
dot_seen=no; \
target=`echo $@ | sed s/-recursive//`; \
list='$(SUBDIRS)'; for subdir in $$list; do \
echo "Making $$target in $$subdir"; \
if test "$$subdir" = "."; then \
dot_seen=yes; \
local_target="$$target-am"; \
else \
local_target="$$target"; \
fi; \
(cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \
|| case "$$amf" in *=*) exit 1;; *k*) fail=yes;; *) exit 1;; esac; \
done; \
if test "$$dot_seen" = "no"; then \
$(MAKE) $(AM_MAKEFLAGS) "$$target-am" || exit 1; \
fi; test -z "$$fail"
mostlyclean-recursive clean-recursive distclean-recursive \
maintainer-clean-recursive:
@set fnord $$MAKEFLAGS; amf=$$2; \
dot_seen=no; \
case "$@" in \
distclean-* | maintainer-clean-*) list='$(DIST_SUBDIRS)' ;; \
*) list='$(SUBDIRS)' ;; \
esac; \
rev=''; for subdir in $$list; do \
if test "$$subdir" = "."; then :; else \
rev="$$subdir $$rev"; \
fi; \
done; \
rev="$$rev ."; \
target=`echo $@ | sed s/-recursive//`; \
for subdir in $$rev; do \
echo "Making $$target in $$subdir"; \
if test "$$subdir" = "."; then \
local_target="$$target-am"; \
else \
local_target="$$target"; \
fi; \
(cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \
|| case "$$amf" in *=*) exit 1;; *k*) fail=yes;; *) exit 1;; esac; \
done && test -z "$$fail"
tags-recursive:
list='$(SUBDIRS)'; for subdir in $$list; do \
test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) tags); \
done
ctags-recursive:
list='$(SUBDIRS)'; for subdir in $$list; do \
test "$$subdir" = . || (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) ctags); \
done
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
mkid -fID $$unique
tags: TAGS
TAGS: tags-recursive $(HEADERS) $(SOURCES) config.h.in $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
if ($(ETAGS) --etags-include --version) >/dev/null 2>&1; then \
include_option=--etags-include; \
empty_fix=.; \
else \
include_option=--include; \
empty_fix=; \
fi; \
list='$(SUBDIRS)'; for subdir in $$list; do \
if test "$$subdir" = .; then :; else \
test ! -f $$subdir/TAGS || \
tags="$$tags $$include_option=$$here/$$subdir/TAGS"; \
fi; \
done; \
list='$(SOURCES) $(HEADERS) config.h.in $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
test -n "$$unique" || unique=$$empty_fix; \
$(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
$$tags $$unique; \
fi
ctags: CTAGS
CTAGS: ctags-recursive $(HEADERS) $(SOURCES) config.h.in $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
list='$(SOURCES) $(HEADERS) config.h.in $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
test -z "$(CTAGS_ARGS)$$tags$$unique" \
|| $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
$$tags $$unique
GTAGS:
here=`$(am__cd) $(top_builddir) && pwd` \
&& cd $(top_srcdir) \
&& gtags -i $(GTAGS_ARGS) $$here
distclean-tags:
-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
distdir: $(DISTFILES)
$(am__remove_distdir)
mkdir $(distdir)
@srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; \
topsrcdirstrip=`echo "$(top_srcdir)" | sed 's|.|.|g'`; \
list='$(DISTFILES)'; for file in $$list; do \
case $$file in \
$(srcdir)/*) file=`echo "$$file" | sed "s|^$$srcdirstrip/||"`;; \
$(top_srcdir)/*) file=`echo "$$file" | sed "s|^$$topsrcdirstrip/|$(top_builddir)/|"`;; \
esac; \
if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
dir=`echo "$$file" | sed -e 's,/[^/]*$$,,'`; \
if test "$$dir" != "$$file" && test "$$dir" != "."; then \
dir="/$$dir"; \
$(mkdir_p) "$(distdir)$$dir"; \
else \
dir=''; \
fi; \
if test -d $$d/$$file; then \
if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
fi; \
cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
else \
test -f $(distdir)/$$file \
|| cp -p $$d/$$file $(distdir)/$$file \
|| exit 1; \
fi; \
done
list='$(DIST_SUBDIRS)'; for subdir in $$list; do \
if test "$$subdir" = .; then :; else \
test -d "$(distdir)/$$subdir" \
|| $(mkdir_p) "$(distdir)/$$subdir" \
|| exit 1; \
distdir=`$(am__cd) $(distdir) && pwd`; \
top_distdir=`$(am__cd) $(top_distdir) && pwd`; \
(cd $$subdir && \
$(MAKE) $(AM_MAKEFLAGS) \
top_distdir="$$top_distdir" \
distdir="$$distdir/$$subdir" \
distdir) \
|| exit 1; \
fi; \
done
-find $(distdir) -type d ! -perm -777 -exec chmod a+rwx {} \; -o \
! -type d ! -perm -444 -links 1 -exec chmod a+r {} \; -o \
! -type d ! -perm -400 -exec chmod a+r {} \; -o \
! -type d ! -perm -444 -exec $(SHELL) $(install_sh) -c -m a+r {} {} \; \
|| chmod -R a+r $(distdir)
dist-gzip: distdir
tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz
$(am__remove_distdir)
dist-bzip2: distdir
tardir=$(distdir) && $(am__tar) | bzip2 -9 -c >$(distdir).tar.bz2
$(am__remove_distdir)
dist-tarZ: distdir
tardir=$(distdir) && $(am__tar) | compress -c >$(distdir).tar.Z
$(am__remove_distdir)
dist-shar: distdir
shar $(distdir) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).shar.gz
$(am__remove_distdir)
dist-zip: distdir
-rm -f $(distdir).zip
zip -rq $(distdir).zip $(distdir)
$(am__remove_distdir)
dist dist-all: distdir
tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz
$(am__remove_distdir)
# This target untars the dist file and tries a VPATH configuration. Then
# it guarantees that the distribution is self-contained by making another
# tarfile.
distcheck: dist
case '$(DIST_ARCHIVES)' in \
*.tar.gz*) \
GZIP=$(GZIP_ENV) gunzip -c $(distdir).tar.gz | $(am__untar) ;;\
*.tar.bz2*) \
bunzip2 -c $(distdir).tar.bz2 | $(am__untar) ;;\
*.tar.Z*) \
uncompress -c $(distdir).tar.Z | $(am__untar) ;;\
*.shar.gz*) \
GZIP=$(GZIP_ENV) gunzip -c $(distdir).shar.gz | unshar ;;\
*.zip*) \
unzip $(distdir).zip ;;\
esac
chmod -R a-w $(distdir); chmod a+w $(distdir)
mkdir $(distdir)/_build
mkdir $(distdir)/_inst
chmod a-w $(distdir)
dc_install_base=`$(am__cd) $(distdir)/_inst && pwd | sed -e 's,^[^:\\/]:[\\/],/,'` \
&& dc_destdir="$${TMPDIR-/tmp}/am-dc-$$$$/" \
&& cd $(distdir)/_build \
&& ../configure --srcdir=.. --prefix="$$dc_install_base" \
$(DISTCHECK_CONFIGURE_FLAGS) \
&& $(MAKE) $(AM_MAKEFLAGS) \
&& $(MAKE) $(AM_MAKEFLAGS) dvi \
&& $(MAKE) $(AM_MAKEFLAGS) check \
&& $(MAKE) $(AM_MAKEFLAGS) install \
&& $(MAKE) $(AM_MAKEFLAGS) installcheck \
&& $(MAKE) $(AM_MAKEFLAGS) uninstall \
&& $(MAKE) $(AM_MAKEFLAGS) distuninstallcheck_dir="$$dc_install_base" \
distuninstallcheck \
&& chmod -R a-w "$$dc_install_base" \
&& ({ \
(cd ../.. && umask 077 && mkdir "$$dc_destdir") \
&& $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" install \
&& $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" uninstall \
&& $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" \
distuninstallcheck_dir="$$dc_destdir" distuninstallcheck; \
} || { rm -rf "$$dc_destdir"; exit 1; }) \
&& rm -rf "$$dc_destdir" \
&& $(MAKE) $(AM_MAKEFLAGS) dist \
&& rm -rf $(DIST_ARCHIVES) \
&& $(MAKE) $(AM_MAKEFLAGS) distcleancheck
$(am__remove_distdir)
@(echo "$(distdir) archives ready for distribution: "; \
list='$(DIST_ARCHIVES)'; for i in $$list; do echo $$i; done) | \
sed -e '1{h;s/./=/g;p;x;}' -e '$${p;x;}'
distuninstallcheck:
@cd $(distuninstallcheck_dir) \
&& test `$(distuninstallcheck_listfiles) | wc -l` -le 1 \
|| { echo "ERROR: files left after uninstall:" ; \
if test -n "$(DESTDIR)"; then \
echo " (check DESTDIR support)"; \
fi ; \
$(distuninstallcheck_listfiles) ; \
exit 1; } >&2
distcleancheck: distclean
@if test '$(srcdir)' = . ; then \
echo "ERROR: distcleancheck can only run from a VPATH build" ; \
exit 1 ; \
fi
@test `$(distcleancheck_listfiles) | wc -l` -eq 0 \
|| { echo "ERROR: files left in build directory after distclean:" ; \
$(distcleancheck_listfiles) ; \
exit 1; } >&2
check-am: all-am
check: check-recursive
all-am: Makefile config.h
installdirs: installdirs-recursive
installdirs-am:
install: install-recursive
install-exec: install-exec-recursive
install-data: install-data-recursive
uninstall: uninstall-recursive
install-am: all-am
@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
installcheck: installcheck-recursive
install-strip:
$(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
`test -z '$(STRIP)' || \
echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
mostlyclean-generic:
clean-generic:
distclean-generic:
-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
maintainer-clean-generic:
@echo "This command is intended for maintainers to use"
@echo "it deletes files that may require special tools to rebuild."
clean: clean-recursive
clean-am: clean-generic clean-libtool mostlyclean-am
distclean: distclean-recursive
-rm -f $(am__CONFIG_DISTCLEAN_FILES)
-rm -f Makefile
distclean-am: clean-am distclean-generic distclean-hdr \
distclean-libtool distclean-tags
dvi: dvi-recursive
dvi-am:
html: html-recursive
info: info-recursive
info-am:
install-data-am:
install-exec-am:
install-info: install-info-recursive
install-man:
installcheck-am:
maintainer-clean: maintainer-clean-recursive
-rm -f $(am__CONFIG_DISTCLEAN_FILES)
-rm -rf $(top_srcdir)/autom4te.cache
-rm -f Makefile
maintainer-clean-am: distclean-am maintainer-clean-generic
mostlyclean: mostlyclean-recursive
mostlyclean-am: mostlyclean-generic mostlyclean-libtool
pdf: pdf-recursive
pdf-am:
ps: ps-recursive
ps-am:
uninstall-am: uninstall-info-am
uninstall-info: uninstall-info-recursive
.PHONY: $(RECURSIVE_TARGETS) CTAGS GTAGS all all-am am--refresh check \
check-am clean clean-generic clean-libtool clean-recursive \
ctags ctags-recursive dist dist-all dist-bzip2 dist-gzip \
dist-shar dist-tarZ dist-zip distcheck distclean \
distclean-generic distclean-hdr distclean-libtool \
distclean-recursive distclean-tags distcleancheck distdir \
distuninstallcheck dvi dvi-am html html-am info info-am \
install install-am install-data install-data-am install-exec \
install-exec-am install-info install-info-am install-man \
install-strip installcheck installcheck-am installdirs \
installdirs-am maintainer-clean maintainer-clean-generic \
maintainer-clean-recursive mostlyclean mostlyclean-generic \
mostlyclean-libtool mostlyclean-recursive pdf pdf-am ps ps-am \
tags tags-recursive uninstall uninstall-am uninstall-info-am
# Tell versions [3.59,3.63) of GNU make to not export all variables.
# Otherwise a system limit (for SysV at least) may be exceeded.
.NOEXPORT:

1
NEWS
View File

@ -1 +0,0 @@
no news.

21
README
View File

@ -1,21 +0,0 @@
linux HLSWMASTER
================
install:
$ ./configure
$ make all
$ make install
hlswmaster.conf anpassen (evtl. plugin pfade)
$ src/hlswmaster -c hlswmaster.conf
Es gibt auch einen kleinen Konsolen Client:
$ tools/masterquery --help
plugin interface:
=================
siehe plugins/skel.c

33
TODO
View File

@ -1,33 +0,0 @@
- evtl. noch natives ut2k3/ut2k4 protocol einbauen
laut hlsw wiki/changelog geht gamespy "nicht immer"
- signalhandler fuer config reread
- signalhandler listen-flush + neuscannen
- auf mehreren/allen interfaces gleichzeitig scannen
geht das ueberhaupt? ohne root rechte?
- threads ueberwachen
- threadpool fuer client-thread?
- statistiken? webserver? gamespy-export?
- Makefile: stripping binarys?
und natuerlich:
- weitere spiele finden:
Halflife
Quake 1
Command & Conquer Renegade
Medal of Honor: Allied Assault
Rune
Never Winter Nights
Medal of Honor: Allied Assault Spearhead
Operation Flashpoint
Operation Flashpoint Resistance
Devastation
Elite Force 2
Medal of Honor: Allied Assault Breakthrough
Tribes 2
Savage: The Battle for Newerth
Pain Killer
Halflife 2
Tribes Vengeance
- vorhandene parser debuggen & verbessern

7133
aclocal.m4 vendored

File diff suppressed because it is too large Load Diff

View File

@ -1,8 +0,0 @@
#!/bin/sh
set -e
aclocal
autoheader
automake --add-missing --copy
autoconf

1477
config.guess vendored

File diff suppressed because it is too large Load Diff

View File

@ -1,61 +0,0 @@
/* config.h.in. Generated from configure.in by autoheader. */
/* Define to 1 if you have the <dlfcn.h> header file. */
#undef HAVE_DLFCN_H
/* Define to 1 if you have the <inttypes.h> header file. */
#undef HAVE_INTTYPES_H
/* Define to 1 if you have the <memory.h> header file. */
#undef HAVE_MEMORY_H
/* Define to 1 if you have the <pthread.h> header file. */
#undef HAVE_PTHREAD_H
/* Define to 1 if you have the <stdint.h> header file. */
#undef HAVE_STDINT_H
/* Define to 1 if you have the <stdlib.h> header file. */
#undef HAVE_STDLIB_H
/* Define to 1 if you have the <strings.h> header file. */
#undef HAVE_STRINGS_H
/* Define to 1 if you have the <string.h> header file. */
#undef HAVE_STRING_H
/* Define to 1 if you have the <sys/ioctl.h> header file. */
#undef HAVE_SYS_IOCTL_H
/* Define to 1 if you have the <sys/stat.h> header file. */
#undef HAVE_SYS_STAT_H
/* Define to 1 if you have the <sys/types.h> header file. */
#undef HAVE_SYS_TYPES_H
/* Define to 1 if you have the <unistd.h> header file. */
#undef HAVE_UNISTD_H
/* Name of package */
#undef PACKAGE
/* Define to the address where bug reports for this package should be sent. */
#undef PACKAGE_BUGREPORT
/* Define to the full name of this package. */
#undef PACKAGE_NAME
/* Define to the full name and version of this package. */
#undef PACKAGE_STRING
/* Define to the one symbol short name of this package. */
#undef PACKAGE_TARNAME
/* Define to the version of this package. */
#undef PACKAGE_VERSION
/* Define to 1 if you have the ANSI C header files. */
#undef STDC_HEADERS
/* Version number of package */
#undef VERSION

1566
config.sub vendored

File diff suppressed because it is too large Load Diff

230
configfile.c Normal file
View File

@ -0,0 +1,230 @@
/***************************************************************************
* Copyright (C) 06/2006 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include "configfile.h"
#include "list.h"
#include "logging.h"
#define BUFSIZE 1024
struct conf_section {
struct list_head list;
struct list_head tupel_list;
char *name;
};
struct conf_tupel {
struct list_head list;
char *option;
char *parameter;
};
static LIST_HEAD(config_list);
static struct conf_section * config_add_section(const char *name)
{
struct conf_section *section;
section = malloc(sizeof(struct conf_section) + strlen(name));
if (section == NULL)
return NULL;
INIT_LIST_HEAD(&section->list);
INIT_LIST_HEAD(&section->tupel_list);
section->name = strdup(name);
if (section->name == NULL) {
free(section);
return NULL;
}
list_add_tail(&section->list, &config_list);
return section;
}
static int config_add_tupel(struct conf_section *section, const char *option, const char *parameter)
{
struct conf_tupel *tupel = malloc(sizeof(struct conf_tupel));
if (tupel == NULL)
return -1;
INIT_LIST_HEAD(&tupel->list);
tupel->option = strdup(option);
tupel->parameter = strdup(parameter);
if (tupel->option == NULL || tupel->parameter == NULL) {
free(tupel);
return -1;
}
list_add_tail(&tupel->list, &section->tupel_list);
return 0;
}
int config_parse(const char *config)
{
FILE *fz = fopen(config, "r");
if (fz == NULL) {
log_print(LOG_ERROR, "config_parse(): %s", config);
return -1;
}
char *line = malloc(BUFSIZE);
if (line == NULL) {
log_print(LOG_ERROR, "config_parse(): out of memory");
fclose(fz);
return -1;
}
int linenum = 0;
struct conf_section *section = NULL;
while (fgets(line, BUFSIZE, fz) != NULL) {
linenum++;
if (line[0] == '#' || line[0] <= ' ') {
continue;
} else if (line[0] == '[') {
char *tok = strtok(line +1, " ]\n");
if (tok == NULL || (section = config_add_section(tok)) == NULL) {
log_print(LOG_WARN, "config_parse(): invalid section in row %d", linenum);
free(line);
fclose(fz);
return -1;
}
continue;
} else if (section == NULL) {
log_print(LOG_WARN, "config_parse(): missing section in row %d", linenum);
free(line);
fclose(fz);
return -1;
}
char *tok = strtok(line, " \n");
if (tok != NULL) {
char *tok2;
while ((tok2 = strtok(NULL, " \n"))) {
if (config_add_tupel(section, tok, tok2) != 0)
log_print(LOG_WARN, "config_parse(): invalid row %d", linenum);
}
}
}
fclose(fz);
free(line);
return 0;
}
static struct conf_section * config_get_section(const char *name)
{
struct conf_section *section;
list_for_each_entry(section, &config_list, list) {
if (!strcmp(section->name, name))
return section;
}
return NULL;
}
char * config_get_string(const char *section_str, const char *option, char *def)
{
struct conf_section *section = config_get_section(section_str);
if (section != NULL) {
struct conf_tupel *tupel;
list_for_each_entry(tupel, &section->tupel_list, list) {
if (!strcmp(tupel->option, option))
return tupel->parameter;
}
}
if (def != NULL)
log_print(LOG_WARN, "config [%s:%s] not found, using default: '%s'",
section_str, option, def);
return def;
}
int config_get_int(const char *section, const char *option, int def)
{
char *ret = config_get_string(section, option, NULL);
if (ret == NULL) {
log_print(LOG_WARN, "config [%s:%s] not found, using default: '%d'",
section, option, def);
return def;
}
return atoi(ret);
}
int config_get_strings(const char *section_str, const char *option,
int (*callback)(const char *value, void *privdata),
void *privdata)
{
struct conf_section *section = config_get_section(section_str);
if (section == NULL)
return -1;
int cnt = 0;
struct conf_tupel *tupel;
list_for_each_entry(tupel, &section->tupel_list, list) {
if (!strcmp(tupel->option, option))
if (callback(tupel->parameter, privdata) == 0)
cnt++;
}
return cnt;
}
// TODO: wrong place!
int parse_saddr(const char *addr, struct sockaddr_in *sa)
{
char *addr_cpy = strdup(addr);
if (addr_cpy == NULL) {
log_print(LOG_WARN, "parse_saddr(): out of memory");
return -1;
}
char *tmp;
char *ip = strtok_r(addr_cpy, ":", &tmp);
if (ip == NULL) {
free(addr_cpy);
return -1;
}
char *port = strtok_r(NULL, ":", &tmp);
if (port == NULL) {
free(addr_cpy);
return -1;
}
sa->sin_family = AF_INET;
sa->sin_port = htons(atoi(port));
int ret = inet_aton(ip, &sa->sin_addr);
free(addr_cpy);
return (ret != 0) ? 0 : -1;
}

22470
configure vendored

File diff suppressed because it is too large Load Diff

View File

@ -1,36 +0,0 @@
dnl projekname, version, bugsto
AC_INIT(hlswmaster, 0.52, [Olaf Rempel <razzor@kopf-tisch.de>])
dnl same for automake
AM_INIT_AUTOMAKE(hlswmaster, 0.52)
dnl do not rebuild configure
AM_MAINTAINER_MODE
dnl request autoconf 2.57
AC_PREREQ(2.57)
dnl libtool stuff
AC_DISABLE_STATIC
AC_LIBTOOL_DLOPEN
AC_PROG_LIBTOOL
dnl store config here
AC_CONFIG_HEADER(config.h)
dnl check compiler
AC_PROG_CC
AC_LANG_C
dnl check headers
AC_HEADER_STDC
AC_CHECK_HEADERS(sys/ioctl.h, , AC_MSG_ERROR(sys/ioctl.h is missing) )
AC_CHECK_HEADERS(dlfcn.h, , AC_MSG_ERROR(dlfcn.h is missing) )
AC_CHECK_HEADERS(pthread.h, , AC_MSG_ERROR(pthread.h is missing) )
dnl check install-sh, make env
AC_PROG_INSTALL
AC_PROG_MAKE_SET
dnl generate Makefile
AC_OUTPUT(Makefile src/Makefile plugins/Makefile tools/Makefile)

310
event.c Normal file
View File

@ -0,0 +1,310 @@
/***************************************************************************
* Copyright (C) 10/2006 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <sys/time.h>
#include <sys/types.h>
#include "list.h"
#include "logging.h"
#include "event.h"
static LIST_HEAD(readfd_list);
static LIST_HEAD(writefd_list);
static LIST_HEAD(exceptfd_list);
static LIST_HEAD(timeout_list);
struct fd_entry {
struct list_head list;
int fd;
int type;
int (*callback)(int fd, void *privdata);
void *privdata;
};
struct timeout_entry {
struct list_head list;
struct timeval timeout;
struct timeval nextrun;
int (*callback)(void *privdata);
void *privdata;
};
int event_add_fd(int fd, int type, int (*callback)(int fd, void *privdata), void *privdata)
{
if (fd < 0 || fd > FD_SETSIZE)
return -1;
struct fd_entry *entry;
entry = malloc(sizeof(struct fd_entry));
if (entry == NULL) {
log_print(LOG_ERROR, "event_add_fd(): out of memory");
return -1;
}
entry->fd = fd;
entry->type = type;
entry->callback = callback;
entry->privdata = privdata;
switch (type) {
case FD_READ:
list_add_tail(&entry->list, &readfd_list);
break;
case FD_WRITE:
list_add_tail(&entry->list, &writefd_list);
break;
case FD_EXCEPT:
list_add_tail(&entry->list, &exceptfd_list);
break;
default:
log_print(LOG_ERROR, "add_fd(): unknown type");
free(entry);
return -1;
}
return 0;
}
int event_remove_fd(int fd)
{
struct fd_entry *entry, *tmp;
list_for_each_entry_safe(entry, tmp, &readfd_list, list) {
if (entry->fd == fd) {
list_del(&entry->list);
free(entry);
return 0;
}
}
list_for_each_entry_safe(entry, tmp, &writefd_list, list) {
if (entry->fd == fd) {
list_del(&entry->list);
free(entry);
return 0;
}
}
list_for_each_entry_safe(entry, tmp, &exceptfd_list, list) {
if (entry->fd == fd) {
list_del(&entry->list);
free(entry);
return 0;
}
}
return -1;
}
static void calc_nextrun(struct timeval *timeout, struct timeval *nextrun)
{
struct timeval now;
gettimeofday(&now, NULL);
nextrun->tv_usec = now.tv_usec + timeout->tv_usec;
nextrun->tv_sec = now.tv_sec + timeout->tv_sec;
if (nextrun->tv_usec >= 1000000) {
nextrun->tv_usec -= 1000000;
nextrun->tv_sec++;
}
}
static void calc_timeout(struct timeval *timeout, struct timeval *nextrun)
{
struct timeval now;
gettimeofday(&now, NULL);
timeout->tv_usec = nextrun->tv_usec - now.tv_usec;
timeout->tv_sec = nextrun->tv_sec - now.tv_sec;
if (timeout->tv_usec < 0) {
timeout->tv_usec += 1000000;
timeout->tv_sec--;
}
}
static void schedule_nextrun(struct timeout_entry *entry)
{
struct timeout_entry *search;
list_for_each_entry(search, &timeout_list, list) {
if (search->nextrun.tv_sec > entry->nextrun.tv_sec) {
list_add_tail(&entry->list, &search->list);
return;
} else if (search->nextrun.tv_sec == entry->nextrun.tv_sec &&
search->nextrun.tv_usec > entry->nextrun.tv_usec) {
list_add_tail(&entry->list, &search->list);
return;
}
}
list_add_tail(&entry->list, &timeout_list);
}
int event_add_timeout(struct timeval *timeout, int (*callback)(void *privdata), void *privdata)
{
struct timeout_entry *entry;
entry = malloc(sizeof(struct timeout_entry));
if (entry == NULL) {
log_print(LOG_ERROR, "event_add_timeout(): out of memory");
return -1;
}
memcpy(&entry->timeout, timeout, sizeof(entry->timeout));
entry->callback = callback;
entry->privdata = privdata;
calc_nextrun(&entry->timeout, &entry->nextrun);
schedule_nextrun(entry);
return 0;
}
void event_loop(void)
{
while (1) {
fd_set readfds, *readfds_p = NULL;
fd_set writefds, *writefds_p = NULL;
fd_set exceptfds, *exceptfds_p =NULL;
struct timeval timeout, *timeout_p = NULL;
if (!list_empty(&readfd_list)) {
struct fd_entry *entry;
FD_ZERO(&readfds);
list_for_each_entry(entry, &readfd_list, list)
FD_SET(entry->fd, &readfds);
readfds_p = &readfds;
}
if (!list_empty(&writefd_list)) {
struct fd_entry *entry;
FD_ZERO(&writefds);
list_for_each_entry(entry, &writefd_list, list)
FD_SET(entry->fd, &writefds);
writefds_p = &writefds;
}
if (!list_empty(&exceptfd_list)) {
struct fd_entry *entry;
FD_ZERO(&exceptfds);
list_for_each_entry(entry, &exceptfd_list, list)
FD_SET(entry->fd, &exceptfds);
exceptfds_p = &exceptfds;
}
if (!list_empty(&timeout_list)) {
struct timeout_entry *entry, *tmp;
list_for_each_entry_safe(entry, tmp, &timeout_list, list) {
calc_timeout(&timeout, &entry->nextrun);
if (timeout.tv_sec >= 0 && timeout.tv_usec > 0) {
timeout_p = &timeout;
break;
}
// delayed timeout, exec NOW!
list_del(&entry->list);
int ret = entry->callback(entry->privdata);
if (ret == 0) {
calc_nextrun(&entry->timeout, &entry->nextrun);
schedule_nextrun(entry);
} else {
free(entry);
}
}
}
int i = select(FD_SETSIZE, readfds_p, writefds_p, exceptfds_p, timeout_p);
if (i < 0) {
/* On error, -1 is returned, and errno is set
* appropriately; the sets and timeout become
* undefined, so do not rely on their contents
* after an error.
*/
continue;
} else if (i == 0 && !list_empty(&timeout_list)) {
struct timeout_entry *entry;
entry = list_entry(timeout_list.next, typeof(*entry), list);
list_del(&entry->list);
int ret = entry->callback(entry->privdata);
if (ret == 0) {
calc_nextrun(&entry->timeout, &entry->nextrun);
schedule_nextrun(entry);
} else {
free(entry);
}
}
if (readfds_p) {
struct fd_entry *entry, *tmp;
list_for_each_entry_safe(entry, tmp, &readfd_list, list) {
if (!FD_ISSET(entry->fd, &readfds))
continue;
if (entry->callback(entry->fd, entry->privdata) != 0) {
list_del(&entry->list);
free(entry);
}
}
}
if (writefds_p) {
struct fd_entry *entry, *tmp;
list_for_each_entry_safe(entry, tmp, &writefd_list, list) {
if (FD_ISSET(entry->fd, &writefds))
continue;
if (entry->callback(entry->fd, entry->privdata) != 0) {
list_del(&entry->list);
free(entry);
}
}
}
if (exceptfds_p) {
struct fd_entry *entry, *tmp;
list_for_each_entry_safe(entry, tmp, &exceptfd_list, list) {
if (FD_ISSET(entry->fd, &exceptfds))
continue;
if (entry->callback(entry->fd, entry->privdata) != 0) {
list_del(&entry->list);
free(entry);
}
}
}
}
}

85
gamelist.c Normal file
View File

@ -0,0 +1,85 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include "gamelist.h"
#include "logging.h"
#define BUCKET_NUM 127
static struct list_head *bucket;
static unsigned int hash_entry(struct game_entry *entry)
{
unsigned int hash = 0x12345678;
hash = ((hash << 5) ^ (hash >> 27)) ^ ((entry->ip >> 0) & 0xFF);
hash = ((hash << 5) ^ (hash >> 27)) ^ ((entry->ip >> 8) & 0xFF);
hash = ((hash << 5) ^ (hash >> 27)) ^ ((entry->ip >> 16) & 0xFF);
hash = ((hash << 5) ^ (hash >> 27)) ^ ((entry->ip >> 24) & 0xFF);
hash = ((hash << 5) ^ (hash >> 27)) ^ ((entry->port1 >> 0) & 0xFF);
hash = ((hash << 5) ^ (hash >> 27)) ^ ((entry->port1 >> 8) & 0xFF);
return hash % BUCKET_NUM;
}
static int compare_entry(struct game_entry *a, struct game_entry *b)
{
return (a->gameid == b->gameid && a->ip == b->ip &&
a->port1 == b->port1 && a->port2 == b->port2);
}
int gamelist_add(struct game_entry *entry)
{
unsigned int hash = hash_entry(entry);
struct game_entry *search;
list_for_each_entry(search, &bucket[hash], list) {
if (compare_entry(search, entry)) {
search->modtime = time(NULL);
return 0;
}
}
entry->modtime = time(NULL);
list_add_tail(&entry->list, &bucket[hash]);
return 0;
}
int gamelist_gc_and_dump(int (*callback)(struct game_entry *entry), int timeout)
{
long now = time(NULL);
int i;
for (i = 0; i < BUCKET_NUM; i++) {
struct game_entry *entry, *tmp;
list_for_each_entry_safe(entry, tmp, &bucket[i], list) {
if (entry->modtime + timeout >= now) {
callback(entry);
} else {
list_del(&entry->list);
free(entry);
}
}
}
return 0;
}
int gamelist_init()
{
bucket = malloc(sizeof(struct list_head) * BUCKET_NUM);
if (bucket == NULL) {
log_print(LOG_ERROR, "scan_init(): out of memory");
return -1;
}
int i;
for (i = 0; i < BUCKET_NUM; i++)
INIT_LIST_HEAD(&bucket[i]);
return 0;
}

View File

@ -21,13 +21,21 @@
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <pthread.h>
#include <getopt.h>
#include <sys/stat.h>
#include <pwd.h>
#include "hlswmaster.h"
#include "configfile.h"
#include "event.h"
#include "logging.h"
#include "gamelist.h"
#include "scanner.h"
#include "server.h"
#include "plugin.h"
#define DEFAULT_CONFIG "hlswmaster.conf"
#define DEFAULT_LOGFILE "hlswmaster.log"
static struct option opts[] = {
{"config", 1, 0, 'c'},
@ -37,11 +45,11 @@ static struct option opts[] = {
{0, 0, 0, 0}
};
int main(int argc, char *argv[]) {
pthread_t thread1, thread2, thread3;
int main(int argc, char *argv[])
{
int arg = 0, code = 0, debug = 0;
char *config = NULL, *user = NULL, *logfile;
char *config = DEFAULT_CONFIG, *user = NULL, *logfile;
while (code != -1) {
code = getopt_long(argc, argv, "c:u:dh", opts, &arg);
@ -82,48 +90,50 @@ int main(int argc, char *argv[]) {
if (user) {
struct passwd *pwl;
if (!(pwl = getpwnam(user))) {
log_print("unknown user: %s", user);
log_print(LOG_ERROR, "unknown user: %s", user);
exit(-1);
}
if (setgid(pwl->pw_gid) || setuid(pwl->pw_uid)) {
log_print("setgid/setuid");
log_print(LOG_ERROR, "setgid/setuid");
exit(-1);
}
}
/* parse config file */
if (!config_parse(config))
if (config_parse(config) == -1)
exit(-1);
/* check logfile */
logfile = config_get_string("global", "logfile", NULL);
logfile = config_get_string("global", "logfile", DEFAULT_LOGFILE);
if (logfile && !debug) {
/* start logging */
if (!log_init(logfile))
exit(-1);
/* zum daemon mutieren */
daemon(-1, 0);
}
log_print("hlswmaster started (user: %s, pid: %d)", getpwuid(getuid())->pw_name, getpid());
/* init scan engine */
if (!scan_init())
log_print(LOG_INFO, "hlswmaster started (user: %s, pid: %d)", getpwuid(getuid())->pw_name, getpid());
/* init plugins */
if (plugin_init() == -1)
exit(-1);
/* load plugins */
plugin_load_all();
/* init gamelist */
if (gamelist_init() == -1)
exit(-1);
/* startup threads */
pthread_create(&thread1, NULL, (void *)&scan_control, NULL);
pthread_create(&thread2, NULL, (void *)&scan_receive, NULL);
pthread_create(&thread3, NULL, (void *)&client_handler, NULL);
/* init server */
if (server_init() == -1)
exit(-1);
/* wait untill d00msday */
while (1)
sleep(3600);
/* init scanner */
if (scanner_init() == -1)
exit(-1);
event_loop();
return 0;
}

View File

@ -1,35 +1,42 @@
[global]
# broadcast scan source IP & PORT (udp)
#scan_ip 0.0.0.0
#scan_port 7130
## broadcast scan source IP & PORT (udp)
scanner_src 0.0.0.0:7130
# broadcast scan every X seconds
#scan_interval 30
## broadcast scan every X seconds
scan_interval 60
# serverlist rebuild every X seconds
#serverlist_interval 5
## serverlist rebuild every X seconds
serverlist_refresh 5
# server timeout after X seconds
#serverlist_timeout 30
## server timeout after X seconds
serverlist_timeout 180
# plugin data timeout every X seconds
#plugin_timeout 30
## master answers with this source IP
master_src 0.0.0.0:7140
# master answers with this source IP
#master_ip 0.0.0.0
plugin_dir plugins
plugin d3engine.so
plugin gamespy1.so
plugin gamespy2.so
plugin halflife.so
plugin hlswproxy.so
plugin q3engine.so
plugin quake2.so
plugin ut2k4.so
# load these plugins
plugin plugins/.libs/hlswproxy.so
plugin plugins/.libs/q3engine.so
plugin plugins/.libs/quake2.so
plugin plugins/.libs/gamespy1.so
plugin plugins/.libs/gamespy2.so
plugin plugins/.libs/doom3.so
# logging
## logging
logfile hlswmaster.log
[hlswproxy]
scan_ip 10.10.0.1
scan_ip 10.10.0.2
[gamespy1]
## internal fragment-list timeout
gc_timeout 90
[hlswproxy]
## ask these hlswmasters
#scan 10.10.0.1:7140
#scan 10.10.0.2:7140
[halflife]
## allow these nets
valid_net 10.10.0.0/16
valid_net 172.16.0.0/16

View File

@ -1,24 +1,18 @@
#ifndef _CONFIG_H
#define _CONFIG_H
#ifndef _CONFIG_H_
#define _CONFIG_H_
#include "list.h"
#include <netinet/in.h>
struct conf_section {
struct list_head list;
char name[32];
struct list_head tupel;
};
int config_parse(const char *config);
struct conf_tupel {
struct list_head list;
char *option;
char *parameter;
};
char * config_get_string(const char *section_str, const char *option, char *def);
int config_parse(char *config);
struct conf_section * config_get_section(char *name);
char * config_get_parameter(struct conf_section *section, char *option);
char * config_get_string(char *section, char *option, char *def);
int config_get_int(char *section, char *option, int def);
int config_get_int(const char *section, const char *option, int def);
#endif /* _CONFIG_H */
int config_get_strings(const char *section_str, const char *option,
int (*callback)(const char *value, void *privdata),
void *privdata);
int parse_saddr(const char *addr, struct sockaddr_in *sa);
#endif /* _CONFIG_H_ */

26
include/event.h Normal file
View File

@ -0,0 +1,26 @@
#ifndef _EVENT_H_
#define _EVENT_H_
#include <sys/time.h>
#define FD_READ 0x01
#define FD_WRITE 0x02
#define FD_EXCEPT 0x04
#define event_add_readfd(fd, callback, privdata) \
event_add_fd(fd, FD_READ, callback, privdata)
#define event_add_writefd(fd, callback, privdata) \
event_add_fd(fd, FD_WRITE, callback, privdata)
#define event_add_exceptfd(fd, callback, privdata) \
event_add_fd(fd, FD_EXCEPT, callback, privdata)
int event_add_fd(int fd, int type, int (*callback)(int fd, void *privdata), void *privdata);
int event_add_timeout(struct timeval *timeout, int (*callback)(void *privdata), void *privdata);
int event_remove_fd(int fd);
void event_loop(void);
#endif /* _EVENT_H_ */

25
include/gamelist.h Normal file
View File

@ -0,0 +1,25 @@
#ifndef _GAMELIST_H_
#define _GAMELIST_H_
#include <inttypes.h>
#include "list.h"
struct game_entry {
struct list_head list;
unsigned long modtime;
/* begin HLSW_ENTRY */
uint16_t gameid;
uint32_t ip;
uint16_t port1;
uint16_t port2;
/* end HLSW_ENTRY */
} __attribute__ ((packed));
int gamelist_init();
int gamelist_add(struct game_entry *entry);
int gamelist_gc_and_dump(int (*callback)(struct game_entry *entry), int timeout);
#endif /* _GAMELIST_H_ */

View File

@ -1,40 +0,0 @@
#ifndef _HLSWMASTER_H
#define _HLSWMASTER_H
#include "list.h"
#include "netpkt.h"
struct game_server {
struct list_head list;
unsigned long modtime;
u_int16_t gameid;
u_int32_t ip;
u_int16_t port1;
u_int16_t port2;
} __attribute__ ((packed));
/* logging.c */
int log_init(char *logfile);
void log_print(const char *fmt, ... );
/* plugin.c */
int plugin_load(char *name);
int plugin_load_all();
int plugin_unload_all();
int plugins_scan();
int plugins_parse(struct net_pkt *pkt);
int plugins_gc(unsigned long timeout);
/* scanner.c */
int scan_init();
void scan_control();
void scan_receive();
/* client.c */
int client_pkt_add(struct game_server *server);
int client_pkt_commit();
void client_handler();
#endif /* _HLSWMASTER_H */

View File

@ -1,15 +1,15 @@
#ifndef _LIST_H
#define _LIST_H
#ifndef _LIST_H_
#define _LIST_H_
/*
** stolen from linux kernel (2.6.11)
** linux/include/linux/stddef.h (offsetoff)
** linux/include/linux/kernel.h (container_of)
** linux/include/linux/list.h (*list*)
** linux/include/linux/netfilter_ipv4/listhelp.h (LIST_FIND)
**
** modified by Olaf Rempel
*/
* stolen from linux kernel 2.6.11 (http://kernel.org/)
* linux/include/linux/stddef.h (offsetoff)
* linux/include/linux/kernel.h (container_of)
* linux/include/linux/list.h (*list*)
* linux/include/linux/netfilter_ipv4/listhelp.h (LIST_FIND)
*
* modified by Olaf Rempel <razzor@kopf-tisch.de>
*/
#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)
#define container_of(ptr, type, member) ({ \
@ -45,7 +45,7 @@ static inline void __list_add(struct list_head *new,
prev->next = new;
}
/**
/*
* list_add - add a new entry
* @new: new entry to be added
* @head: list head to add it after
@ -58,7 +58,7 @@ static inline void list_add(struct list_head *new, struct list_head *head)
__list_add(new, head, head->next);
}
/**
/*
* list_add_tail - add a new entry
* @new: new entry to be added
* @head: list head to add it before
@ -71,7 +71,7 @@ static inline void list_add_tail(struct list_head *new, struct list_head *head)
__list_add(new, head->prev, head);
}
/**
/*
* Delete a list entry by making the prev/next entries
* point to each other.
*
@ -84,7 +84,7 @@ static inline void __list_del(struct list_head * prev, struct list_head * next)
prev->next = next;
}
/**
/*
* list_del - deletes entry from list.
* @entry: the element to delete from the list.
* Note: list_empty on entry does not return true after this, the entry is
@ -97,9 +97,9 @@ static inline void list_del(struct list_head *entry)
entry->prev = NULL;
}
/**
/*
* list_del_init - deletes entry from list and reinitialize it.
* @entry: the element to delete from the list.
* entry: the element to delete from the list.
*/
static inline void list_del_init(struct list_head *entry)
{
@ -107,7 +107,7 @@ static inline void list_del_init(struct list_head *entry)
INIT_LIST_HEAD(entry);
}
/**
/*
* list_move - delete from one list and add as another's head
* @list: the entry to move
* @head: the head that will precede our entry
@ -118,7 +118,7 @@ static inline void list_move(struct list_head *list, struct list_head *head)
list_add(list, head);
}
/**
/*
* list_move_tail - delete from one list and add as another's tail
* @list: the entry to move
* @head: the head that will follow our entry
@ -130,7 +130,7 @@ static inline void list_move_tail(struct list_head *list,
list_add_tail(list, head);
}
/**
/*
* list_empty - tests whether a list is empty
* @head: the list to test.
*/
@ -153,7 +153,7 @@ static inline void __list_splice(struct list_head *list,
at->prev = last;
}
/**
/*
* list_splice - join two lists
* @list: the new list to add.
* @head: the place to add it in the first list.
@ -164,7 +164,7 @@ static inline void list_splice(struct list_head *list, struct list_head *head)
__list_splice(list, head);
}
/**
/*
* list_splice_init - join two lists and reinitialise the emptied list.
* @list: the new list to add.
* @head: the place to add it in the first list.
@ -180,7 +180,7 @@ static inline void list_splice_init(struct list_head *list,
}
}
/**
/*
* list_entry - get the struct for this entry
* @ptr: the &struct list_head pointer.
* @type: the type of the struct this is embedded in.
@ -189,7 +189,7 @@ static inline void list_splice_init(struct list_head *list,
#define list_entry(ptr, type, member) \
container_of(ptr, type, member)
/**
/*
* list_for_each - iterate over a list
* @pos: the &struct list_head to use as a loop counter.
* @head: the head for your list.
@ -197,7 +197,7 @@ static inline void list_splice_init(struct list_head *list,
#define list_for_each(pos, head) \
for (pos = (head)->next; pos != (head); pos = pos->next)
/**
/*
* list_for_each_prev - iterate over a list backwards
* @pos: the &struct list_head to use as a loop counter.
* @head: the head for your list.
@ -205,7 +205,7 @@ static inline void list_splice_init(struct list_head *list,
#define list_for_each_prev(pos, head) \
for (pos = (head)->prev; pos != (head); pos = pos->prev)
/**
/*
* list_for_each_safe - iterate over a list safe against removal of list entry
* @pos: the &struct list_head to use as a loop counter.
* @n: another &struct list_head to use as temporary storage
@ -215,7 +215,7 @@ static inline void list_splice_init(struct list_head *list,
for (pos = (head)->next, n = pos->next; pos != (head); \
pos = n, n = pos->next)
/**
/*
* list_for_each_entry - iterate over list of given type
* @pos: the type * to use as a loop counter.
* @head: the head for your list.
@ -226,7 +226,7 @@ static inline void list_splice_init(struct list_head *list,
&pos->member != (head); \
pos = list_entry(pos->member.next, typeof(*pos), member))
/**
/*
* list_for_each_entry_reverse - iterate backwards over list of given type.
* @pos: the type * to use as a loop counter.
* @head: the head for your list.
@ -237,7 +237,7 @@ static inline void list_splice_init(struct list_head *list,
&pos->member != (head); \
pos = list_entry(pos->member.prev, typeof(*pos), member))
/**
/*
* list_for_each_entry_safe - iterate over list of given type safe against removal of list entry
* @pos: the type * to use as a loop counter.
* @n: another type * to use as temporary storage
@ -265,4 +265,4 @@ static inline void list_splice_init(struct list_head *list,
(type)__j; \
})
#endif /* _LIST_H */
#endif /* _LIST_H_ */

16
include/logging.h Normal file
View File

@ -0,0 +1,16 @@
#ifndef _LOGGING_H_
#define _LOGGING_H_
#define LOG_DEBUG 5
#define LOG_INFO 4
#define LOG_NOTICE 3
#define LOG_WARN 2
#define LOG_ERROR 1
#define LOG_CRIT 0
#define LOG_EVERYTIME 0
int log_init(char *logfile);
void log_print(int prio, const char *fmt, ... );
#endif /* _LOGGING_H_ */

View File

@ -5,10 +5,24 @@
#include <netinet/in.h>
#include <netinet/ip.h>
#include "list.h"
struct net_pkt {
struct list_head list;
struct sockaddr_in addr;
unsigned int size;
unsigned char buf[0];
};
int pkt_memcmp(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size);
int pkt_memmem(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size);
struct net_pkt * pkt_merge(struct net_pkt *pkt1, struct net_pkt *pkt2);
char * pkt_ntoa(struct net_pkt *pkt);
unsigned short pkt_getport(struct net_pkt *pkt);
int pkt_sameaddr(struct net_pkt *pkt1, struct net_pkt *pkt2);
int pkt_parse_int(struct net_pkt *pkt, unsigned int offset, int *val);
int pkt_parse_ip(struct net_pkt *pkt, int offset, struct in_addr *ip);
char * pkt_print(struct net_pkt *pkt);
#endif /* _NETPKT_H */

View File

@ -5,17 +5,27 @@
#include "configfile.h"
#include "list.h"
// paket nicht akzeptiert, free() muss noch aufgerufen werden
#define PARSE_REJECT 0
// paket akzeptiert, free() muss noch aufgerufen werden
#define PARSE_ACCEPT 1
// paket akzeptiert, free() wurde schon, oder darf noch aufgerufen werden
#define PARSE_ACCEPT_FREED 2
struct hlswmaster_plugin {
struct list_head list;
char name[32];
void *dlref;
int (*init)(struct conf_section *config);
int (*init)(void);
int (*fini)(void);
int (*scan)(void);
int (*parse)(struct net_pkt *pkt);
int (*gc)(int timeout);
};
int plugin_init();
int plugins_scan();
int plugins_parse(struct net_pkt *pkt);
#endif /* _PLUGIN_H */

View File

@ -1,29 +1,15 @@
#ifndef _PLUGIN_HELPER_H
#define _PLUGIN_HELPER_H
#include "netpkt.h"
#include "list.h"
#include "plugin.h"
extern int server_add(u_int16_t gameid, u_int32_t ip, u_int16_t port1, u_int16_t port2);
struct scan_ports {
unsigned short portlo;
unsigned short porthi;
unsigned short gameid;
};
extern int pkt_send(struct in_addr *dstip, unsigned int dstport, char *buf, unsigned int size);
extern int pkt_send_portarr(struct in_addr *dstip, struct scan_ports *portarr, char *buf, unsigned int size);
extern int pkt_check_portarr(struct net_pkt *pkt, struct scan_ports *portarr);
extern int pkt_memcmp(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size);
extern void * pkt_memmem(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size);
extern int server_add_pkt(unsigned int gameid, struct net_pkt *pkt);
extern char * pkt_ntoa(struct net_pkt *pkt);
extern unsigned short pkt_getport(struct net_pkt *pkt);
extern int pkt_atoi(struct net_pkt *pkt, void *p);
int server_add(uint16_t gameid, uint32_t ip, uint16_t port1, uint16_t port2);
int server_add_pkt(unsigned int gameid, struct net_pkt *pkt);
int pkt_send_portarr(struct in_addr *dstip, struct scan_ports *portarr, char *buf, unsigned int size);
int pkt_check_portarr(struct net_pkt *pkt, struct scan_ports *portarr);
#endif /* _PLUGIN_HELPER_H */

7
include/scanner.h Normal file
View File

@ -0,0 +1,7 @@
#ifndef _SCANNER_H_
#define _SCANNER_H_
int pkt_send(struct in_addr *dstip, unsigned int dstport, char *buf, unsigned int size);
int scanner_init();
#endif /* _SCANNER_H_ */

6
include/server.h Normal file
View File

@ -0,0 +1,6 @@
#ifndef _SERVER_H_
#define _SERVER_H_
int server_init();
#endif /* _SERVER_H_ */

View File

@ -1,323 +0,0 @@
#!/bin/sh
# install - install a program, script, or datafile
scriptversion=2004-12-17.09
# This originates from X11R5 (mit/util/scripts/install.sh), which was
# later released in X11R6 (xc/config/util/install.sh) with the
# following copyright and license.
#
# Copyright (C) 1994 X Consortium
#
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to
# deal in the Software without restriction, including without limitation the
# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
# sell copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC-
# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#
# Except as contained in this notice, the name of the X Consortium shall not
# be used in advertising or otherwise to promote the sale, use or other deal-
# ings in this Software without prior written authorization from the X Consor-
# tium.
#
#
# FSF changes to this file are in the public domain.
#
# Calling this script install-sh is preferred over install.sh, to prevent
# `make' implicit rules from creating a file called install from it
# when there is no Makefile.
#
# This script is compatible with the BSD install script, but was written
# from scratch. It can only install one file at a time, a restriction
# shared with many OS's install programs.
# set DOITPROG to echo to test this script
# Don't use :- since 4.3BSD and earlier shells don't like it.
doit="${DOITPROG-}"
# put in absolute paths if you don't have them in your path; or use env. vars.
mvprog="${MVPROG-mv}"
cpprog="${CPPROG-cp}"
chmodprog="${CHMODPROG-chmod}"
chownprog="${CHOWNPROG-chown}"
chgrpprog="${CHGRPPROG-chgrp}"
stripprog="${STRIPPROG-strip}"
rmprog="${RMPROG-rm}"
mkdirprog="${MKDIRPROG-mkdir}"
chmodcmd="$chmodprog 0755"
chowncmd=
chgrpcmd=
stripcmd=
rmcmd="$rmprog -f"
mvcmd="$mvprog"
src=
dst=
dir_arg=
dstarg=
no_target_directory=
usage="Usage: $0 [OPTION]... [-T] SRCFILE DSTFILE
or: $0 [OPTION]... SRCFILES... DIRECTORY
or: $0 [OPTION]... -t DIRECTORY SRCFILES...
or: $0 [OPTION]... -d DIRECTORIES...
In the 1st form, copy SRCFILE to DSTFILE.
In the 2nd and 3rd, copy all SRCFILES to DIRECTORY.
In the 4th, create DIRECTORIES.
Options:
-c (ignored)
-d create directories instead of installing files.
-g GROUP $chgrpprog installed files to GROUP.
-m MODE $chmodprog installed files to MODE.
-o USER $chownprog installed files to USER.
-s $stripprog installed files.
-t DIRECTORY install into DIRECTORY.
-T report an error if DSTFILE is a directory.
--help display this help and exit.
--version display version info and exit.
Environment variables override the default commands:
CHGRPPROG CHMODPROG CHOWNPROG CPPROG MKDIRPROG MVPROG RMPROG STRIPPROG
"
while test -n "$1"; do
case $1 in
-c) shift
continue;;
-d) dir_arg=true
shift
continue;;
-g) chgrpcmd="$chgrpprog $2"
shift
shift
continue;;
--help) echo "$usage"; exit 0;;
-m) chmodcmd="$chmodprog $2"
shift
shift
continue;;
-o) chowncmd="$chownprog $2"
shift
shift
continue;;
-s) stripcmd=$stripprog
shift
continue;;
-t) dstarg=$2
shift
shift
continue;;
-T) no_target_directory=true
shift
continue;;
--version) echo "$0 $scriptversion"; exit 0;;
*) # When -d is used, all remaining arguments are directories to create.
# When -t is used, the destination is already specified.
test -n "$dir_arg$dstarg" && break
# Otherwise, the last argument is the destination. Remove it from $@.
for arg
do
if test -n "$dstarg"; then
# $@ is not empty: it contains at least $arg.
set fnord "$@" "$dstarg"
shift # fnord
fi
shift # arg
dstarg=$arg
done
break;;
esac
done
if test -z "$1"; then
if test -z "$dir_arg"; then
echo "$0: no input file specified." >&2
exit 1
fi
# It's OK to call `install-sh -d' without argument.
# This can happen when creating conditional directories.
exit 0
fi
for src
do
# Protect names starting with `-'.
case $src in
-*) src=./$src ;;
esac
if test -n "$dir_arg"; then
dst=$src
src=
if test -d "$dst"; then
mkdircmd=:
chmodcmd=
else
mkdircmd=$mkdirprog
fi
else
# Waiting for this to be detected by the "$cpprog $src $dsttmp" command
# might cause directories to be created, which would be especially bad
# if $src (and thus $dsttmp) contains '*'.
if test ! -f "$src" && test ! -d "$src"; then
echo "$0: $src does not exist." >&2
exit 1
fi
if test -z "$dstarg"; then
echo "$0: no destination specified." >&2
exit 1
fi
dst=$dstarg
# Protect names starting with `-'.
case $dst in
-*) dst=./$dst ;;
esac
# If destination is a directory, append the input filename; won't work
# if double slashes aren't ignored.
if test -d "$dst"; then
if test -n "$no_target_directory"; then
echo "$0: $dstarg: Is a directory" >&2
exit 1
fi
dst=$dst/`basename "$src"`
fi
fi
# This sed command emulates the dirname command.
dstdir=`echo "$dst" | sed -e 's,/*$,,;s,[^/]*$,,;s,/*$,,;s,^$,.,'`
# Make sure that the destination directory exists.
# Skip lots of stat calls in the usual case.
if test ! -d "$dstdir"; then
defaultIFS='
'
IFS="${IFS-$defaultIFS}"
oIFS=$IFS
# Some sh's can't handle IFS=/ for some reason.
IFS='%'
set x `echo "$dstdir" | sed -e 's@/@%@g' -e 's@^%@/@'`
shift
IFS=$oIFS
pathcomp=
while test $# -ne 0 ; do
pathcomp=$pathcomp$1
shift
if test ! -d "$pathcomp"; then
$mkdirprog "$pathcomp"
# mkdir can fail with a `File exist' error in case several
# install-sh are creating the directory concurrently. This
# is OK.
test -d "$pathcomp" || exit
fi
pathcomp=$pathcomp/
done
fi
if test -n "$dir_arg"; then
$doit $mkdircmd "$dst" \
&& { test -z "$chowncmd" || $doit $chowncmd "$dst"; } \
&& { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } \
&& { test -z "$stripcmd" || $doit $stripcmd "$dst"; } \
&& { test -z "$chmodcmd" || $doit $chmodcmd "$dst"; }
else
dstfile=`basename "$dst"`
# Make a couple of temp file names in the proper directory.
dsttmp=$dstdir/_inst.$$_
rmtmp=$dstdir/_rm.$$_
# Trap to clean up those temp files at exit.
trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0
trap '(exit $?); exit' 1 2 13 15
# Copy the file name to the temp name.
$doit $cpprog "$src" "$dsttmp" &&
# and set any options; do chmod last to preserve setuid bits.
#
# If any of these fail, we abort the whole thing. If we want to
# ignore errors from any of these, just make sure not to ignore
# errors from the above "$doit $cpprog $src $dsttmp" command.
#
{ test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } \
&& { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } \
&& { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } \
&& { test -z "$chmodcmd" || $doit $chmodcmd "$dsttmp"; } &&
# Now rename the file to the real destination.
{ $doit $mvcmd -f "$dsttmp" "$dstdir/$dstfile" 2>/dev/null \
|| {
# The rename failed, perhaps because mv can't rename something else
# to itself, or perhaps because mv is so ancient that it does not
# support -f.
# Now remove or move aside any old file at destination location.
# We try this two ways since rm can't unlink itself on some
# systems and the destination file might be busy for other
# reasons. In this case, the final cleanup might fail but the new
# file should still install successfully.
{
if test -f "$dstdir/$dstfile"; then
$doit $rmcmd -f "$dstdir/$dstfile" 2>/dev/null \
|| $doit $mvcmd -f "$dstdir/$dstfile" "$rmtmp" 2>/dev/null \
|| {
echo "$0: cannot unlink or rename $dstdir/$dstfile" >&2
(exit 1); exit 1
}
else
:
fi
} &&
# Now rename the file to the real destination.
$doit $mvcmd "$dsttmp" "$dstdir/$dstfile"
}
}
fi || { (exit 1); exit 1; }
done
# The final little trick to "correctly" pass the exit status to the exit trap.
{
(exit 0); exit 0
}
# Local variables:
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-end: "$"
# End:

View File

@ -1,5 +1,5 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* Copyright (C) 06/2006 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
@ -24,69 +24,80 @@
#include <errno.h>
#include <string.h>
#include "configfile.h"
#include "logging.h"
#define BUFSIZE 8192
static FILE *log_fd = NULL;
static char *buffer = NULL;
/**
* log_print()
* schreibt eine Zeile ins Logfile oder auf stderr
* wenn errno gesetzt ist, wird der error-string mit ausgegeben
*
* @param variable parameterlist
*/
void log_print(const char *fmt, ...) {
void log_print(int prio, const char *fmt, ...)
{
va_list az;
char buffer[256];
int len;
va_start(az, fmt);
vsprintf(buffer, fmt, az);
va_end(az);
if (log_fd) {
time_t tzgr;
char tbuf[64];
time(&tzgr);
strftime(tbuf, 64, "%b %d %H:%M:%S :", localtime(&tzgr));
if (errno) {
fprintf(log_fd, "%s %s: %s\n", tbuf, buffer, strerror(errno));
} else {
fprintf(log_fd, "%s %s\n", tbuf, buffer);
}
} else {
if (errno) {
fprintf(stderr, "%s: %s\n", buffer, strerror(errno));
} else {
fprintf(stderr, "%s\n", buffer);
if (buffer == NULL) {
buffer = malloc(BUFSIZE);
if (buffer == NULL) {
fprintf(stderr, "log_print: out of memory\nBailing out!\n");
exit(-1);
}
}
va_start(az, fmt);
len = vsnprintf(buffer, BUFSIZE, fmt, az);
va_end(az);
if (len < 0 || len >= BUFSIZE) {
log_print(LOG_ERROR, "log_print: arguments too long");
errno = 0;
return;
}
if (errno) {
strncpy(buffer + len, ": ", BUFSIZE - len);
len += 2;
strncpy(buffer + len, strerror(errno), BUFSIZE - len);
}
if (log_fd) {
char tbuf[64];
time_t tzgr;
time(&tzgr);
strftime(tbuf, sizeof(tbuf), "%b %d %H:%M:%S :", localtime(&tzgr));
fprintf(log_fd, "%s %s\n", tbuf, buffer);
fflush(log_fd);
} else {
fprintf(stderr, "%s\n", buffer);
}
errno = 0;
fflush(log_fd);
}
/**
* log_close()
* schliesst das logfile
*/
static void log_close() {
static void log_close(void)
{
if (buffer)
free(buffer);
fclose(log_fd);
}
/**
* log_init()
* oeffnet das logfile
* wenn der prozess sich beendet, wird das logfile auch wieder geschlossen
*/
int log_init(char *logfile) {
if ((log_fd = fopen(logfile, "a" )) == NULL) {
log_print("log_open('%s'): %s", logfile);
int log_init(char *logfile)
{
log_fd = fopen(logfile, "a");
if (log_fd == NULL) {
log_print(LOG_ERROR, "log_open('%s'): %s", logfile);
return 0;
}
if (atexit(log_close) != 0) {
log_print("log_open(): atexit()");
log_print(LOG_ERROR, "log_open(): atexit()");
return 0;
}
log_print("==========================");
log_print(LOG_EVERYTIME, "==========================");
return 1;
}

6496
ltmain.sh

File diff suppressed because it is too large Load Diff

View File

@ -10,23 +10,25 @@
#include <arpa/inet.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <inttypes.h>
struct _entry {
u_int16_t gameid;
u_int32_t ip;
u_int16_t port1;
u_int16_t port2;
uint16_t gameid;
uint32_t ip;
uint16_t port1;
uint16_t port2;
} __attribute__ ((packed));
static char hlswheader[] = "\xFF\xFF\xFF\xFFHLSWLANSEARCH";
#define id2name_count (sizeof(id2name) / sizeof(char *) -1)
static char *id2name[] = {
"Unknown", // 0
"Unknown", // 0
"Halflife",
"Quake 1",
"Quake 2",
"Q3Comp",
"Unreal Tournament",
"Unreal Tournament", // 5
"Quake 3 Arena",
"Elite Force",
"Return to Castle Wolfenstein",
@ -36,7 +38,7 @@ static char *id2name[] = {
"Jedi Knight 2",
"Soldier of Fortune",
"Unreal Tournament 2003",
"America's Army: Operations",
"America's Army: Operations", // 15
"Battlefield 1942",
"Alien vs. Predator 2",
"Rune",
@ -46,29 +48,39 @@ static char *id2name[] = {
"Operation Flashpoint",
"Operation Flashpoint Resistance",
"Devastation",
"Wolfenstein - Enemy Territory",
"Wolfenstein - Enemy Territory", //25
"Elite Force 2",
"Jedi Knight 3",
"Medal of Honor: Allied Assault Breakthrough",
"Tribes 2",
"Halo", // 30
"Call of Duty",
"Call of Duty",
"Savage: The Battle for Newerth",
"Unreal Tournament 2004",
"HLSteam",
"Battlefield Vietnam",
"Battlefield Vietnam", // 35
"GS2Prot",
"Pain Killer",
"Doom 3",
"OGPProt",
"Halflife 2", // 40
"Tribes Vengeance",
"Call of Duty: United Offensive"
"Call of Duty: United Offensive",
"Starwars: Battlefront (?)",
"SWAT 4",
"Battlefield 2", // 45
"unknown",
"Quake 4",
"Call of Duty 2",
"unknown",
"FEAR", // 50
"Warsow(?)"
};
static int sock, verbose = 0;
static void parse_pkt(struct sockaddr_in *src, void *pkt, unsigned int size) {
static void parse_pkt(struct sockaddr_in *src, void *pkt, unsigned int size)
{
struct _entry *server;
struct in_addr tmp;
@ -77,40 +89,43 @@ static void parse_pkt(struct sockaddr_in *src, void *pkt, unsigned int size) {
inet_ntoa(src->sin_addr), ntohs(src->sin_port), size);
} else {
printf("received hlsw packet from: %15s:%-5d size=%d\n count=%d",
inet_ntoa(src->sin_addr), ntohs(src->sin_port), size,
printf("received hlsw packet from: %15s:%-5d size=%d count=%d\n",
inet_ntoa(src->sin_addr), ntohs(src->sin_port), size,
((size > sizeof(hlswheader)) ? (size - sizeof(hlswheader)) / sizeof(struct _entry) : 0));
if (verbose) {
server = pkt + sizeof(hlswheader);
while ((void *)server < pkt + size) {
tmp.s_addr = server->ip;
printf(" ip=%15s port1=%5d port2=%5d gameid=%2d (%s)\n",
inet_ntoa(tmp), server->port1, server->port2,
server->gameid, id2name[server->gameid]);
server->gameid, server->gameid <= id2name_count ? id2name[server->gameid] : "unknown");
server++;
}
}
}
}
static int scan_init() {
int i = 1;
if ((sock = socket(PF_INET, SOCK_DGRAM, 0)) < 0) {
static int scan_init()
{
sock = socket(PF_INET, SOCK_DGRAM, 0);
if (sock < 0) {
perror("socket()");
return -1;
}
unsigned int i = 1;
if (setsockopt(sock, SOL_SOCKET, SO_BROADCAST, &i, sizeof(i))) {
perror("setsockopt()");
return -1;
}
return 0;
}
static int scan_transmit(struct sockaddr_in *dst) {
static int scan_transmit(struct sockaddr_in *dst)
{
if (sendto(sock, hlswheader, sizeof(hlswheader), 0, (struct sockaddr *)dst, sizeof(struct sockaddr_in)) < 0) {
perror("sendto()");
return -1;
@ -119,7 +134,8 @@ static int scan_transmit(struct sockaddr_in *dst) {
return 0;
}
static int scan_receive() {
static int scan_receive()
{
struct sockaddr_in src;
struct timeval tv;
fd_set fdsel;
@ -128,10 +144,10 @@ static int scan_receive() {
FD_ZERO(&fdsel);
FD_SET(sock, &fdsel);
tv.tv_sec = 1;
tv.tv_usec = 0;
/* timeout */
while (tv.tv_sec > 0 || tv.tv_usec > 0) {
@ -145,7 +161,7 @@ static int scan_receive() {
perror("ioctl()");
return -1;
}
if (recvsize > 0) {
if (!(pkt = malloc(recvsize))) {
perror("malloc()");
@ -171,7 +187,8 @@ static struct option opts[] = {
{0, 0, 0, 0}
};
int main(int argc, char *argv[]) {
int main(int argc, char *argv[])
{
struct sockaddr_in dst;
int arg = 0, code = 0;
int freq = -1;
@ -190,7 +207,7 @@ int main(int argc, char *argv[]) {
exit(-1);
}
break;
case 'i': /* intervall */
freq = atoi(optarg);
if (freq < 1) {
@ -202,7 +219,7 @@ int main(int argc, char *argv[]) {
case 'v': /* verbose */
verbose = 1;
break;
case 'h': /* help */
printf("Usage: masterquery [options]\n"
"Options: \n"

353
missing
View File

@ -1,353 +0,0 @@
#! /bin/sh
# Common stub for a few missing GNU programs while installing.
scriptversion=2004-09-07.08
# Copyright (C) 1996, 1997, 1999, 2000, 2002, 2003, 2004
# Free Software Foundation, Inc.
# Originally by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2, or (at your option)
# any later version.
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
# 02111-1307, USA.
# As a special exception to the GNU General Public License, if you
# distribute this file as part of a program that contains a
# configuration script generated by Autoconf, you may include it under
# the same distribution terms that you use for the rest of that program.
if test $# -eq 0; then
echo 1>&2 "Try \`$0 --help' for more information"
exit 1
fi
run=:
# In the cases where this matters, `missing' is being run in the
# srcdir already.
if test -f configure.ac; then
configure_ac=configure.ac
else
configure_ac=configure.in
fi
msg="missing on your system"
case "$1" in
--run)
# Try to run requested program, and just exit if it succeeds.
run=
shift
"$@" && exit 0
# Exit code 63 means version mismatch. This often happens
# when the user try to use an ancient version of a tool on
# a file that requires a minimum version. In this case we
# we should proceed has if the program had been absent, or
# if --run hadn't been passed.
if test $? = 63; then
run=:
msg="probably too old"
fi
;;
-h|--h|--he|--hel|--help)
echo "\
$0 [OPTION]... PROGRAM [ARGUMENT]...
Handle \`PROGRAM [ARGUMENT]...' for when PROGRAM is missing, or return an
error status if there is no known handling for PROGRAM.
Options:
-h, --help display this help and exit
-v, --version output version information and exit
--run try to run the given command, and emulate it if it fails
Supported PROGRAM values:
aclocal touch file \`aclocal.m4'
autoconf touch file \`configure'
autoheader touch file \`config.h.in'
automake touch all \`Makefile.in' files
bison create \`y.tab.[ch]', if possible, from existing .[ch]
flex create \`lex.yy.c', if possible, from existing .c
help2man touch the output file
lex create \`lex.yy.c', if possible, from existing .c
makeinfo touch the output file
tar try tar, gnutar, gtar, then tar without non-portable flags
yacc create \`y.tab.[ch]', if possible, from existing .[ch]
Send bug reports to <bug-automake@gnu.org>."
exit 0
;;
-v|--v|--ve|--ver|--vers|--versi|--versio|--version)
echo "missing $scriptversion (GNU Automake)"
exit 0
;;
-*)
echo 1>&2 "$0: Unknown \`$1' option"
echo 1>&2 "Try \`$0 --help' for more information"
exit 1
;;
esac
# Now exit if we have it, but it failed. Also exit now if we
# don't have it and --version was passed (most likely to detect
# the program).
case "$1" in
lex|yacc)
# Not GNU programs, they don't have --version.
;;
tar)
if test -n "$run"; then
echo 1>&2 "ERROR: \`tar' requires --run"
exit 1
elif test "x$2" = "x--version" || test "x$2" = "x--help"; then
exit 1
fi
;;
*)
if test -z "$run" && ($1 --version) > /dev/null 2>&1; then
# We have it, but it failed.
exit 1
elif test "x$2" = "x--version" || test "x$2" = "x--help"; then
# Could not run --version or --help. This is probably someone
# running `$TOOL --version' or `$TOOL --help' to check whether
# $TOOL exists and not knowing $TOOL uses missing.
exit 1
fi
;;
esac
# If it does not exist, or fails to run (possibly an outdated version),
# try to emulate it.
case "$1" in
aclocal*)
echo 1>&2 "\
WARNING: \`$1' is $msg. You should only need it if
you modified \`acinclude.m4' or \`${configure_ac}'. You might want
to install the \`Automake' and \`Perl' packages. Grab them from
any GNU archive site."
touch aclocal.m4
;;
autoconf)
echo 1>&2 "\
WARNING: \`$1' is $msg. You should only need it if
you modified \`${configure_ac}'. You might want to install the
\`Autoconf' and \`GNU m4' packages. Grab them from any GNU
archive site."
touch configure
;;
autoheader)
echo 1>&2 "\
WARNING: \`$1' is $msg. You should only need it if
you modified \`acconfig.h' or \`${configure_ac}'. You might want
to install the \`Autoconf' and \`GNU m4' packages. Grab them
from any GNU archive site."
files=`sed -n 's/^[ ]*A[CM]_CONFIG_HEADER(\([^)]*\)).*/\1/p' ${configure_ac}`
test -z "$files" && files="config.h"
touch_files=
for f in $files; do
case "$f" in
*:*) touch_files="$touch_files "`echo "$f" |
sed -e 's/^[^:]*://' -e 's/:.*//'`;;
*) touch_files="$touch_files $f.in";;
esac
done
touch $touch_files
;;
automake*)
echo 1>&2 "\
WARNING: \`$1' is $msg. You should only need it if
you modified \`Makefile.am', \`acinclude.m4' or \`${configure_ac}'.
You might want to install the \`Automake' and \`Perl' packages.
Grab them from any GNU archive site."
find . -type f -name Makefile.am -print |
sed 's/\.am$/.in/' |
while read f; do touch "$f"; done
;;
autom4te)
echo 1>&2 "\
WARNING: \`$1' is needed, but is $msg.
You might have modified some files without having the
proper tools for further handling them.
You can get \`$1' as part of \`Autoconf' from any GNU
archive site."
file=`echo "$*" | sed -n 's/.*--output[ =]*\([^ ]*\).*/\1/p'`
test -z "$file" && file=`echo "$*" | sed -n 's/.*-o[ ]*\([^ ]*\).*/\1/p'`
if test -f "$file"; then
touch $file
else
test -z "$file" || exec >$file
echo "#! /bin/sh"
echo "# Created by GNU Automake missing as a replacement of"
echo "# $ $@"
echo "exit 0"
chmod +x $file
exit 1
fi
;;
bison|yacc)
echo 1>&2 "\
WARNING: \`$1' $msg. You should only need it if
you modified a \`.y' file. You may need the \`Bison' package
in order for those modifications to take effect. You can get
\`Bison' from any GNU archive site."
rm -f y.tab.c y.tab.h
if [ $# -ne 1 ]; then
eval LASTARG="\${$#}"
case "$LASTARG" in
*.y)
SRCFILE=`echo "$LASTARG" | sed 's/y$/c/'`
if [ -f "$SRCFILE" ]; then
cp "$SRCFILE" y.tab.c
fi
SRCFILE=`echo "$LASTARG" | sed 's/y$/h/'`
if [ -f "$SRCFILE" ]; then
cp "$SRCFILE" y.tab.h
fi
;;
esac
fi
if [ ! -f y.tab.h ]; then
echo >y.tab.h
fi
if [ ! -f y.tab.c ]; then
echo 'main() { return 0; }' >y.tab.c
fi
;;
lex|flex)
echo 1>&2 "\
WARNING: \`$1' is $msg. You should only need it if
you modified a \`.l' file. You may need the \`Flex' package
in order for those modifications to take effect. You can get
\`Flex' from any GNU archive site."
rm -f lex.yy.c
if [ $# -ne 1 ]; then
eval LASTARG="\${$#}"
case "$LASTARG" in
*.l)
SRCFILE=`echo "$LASTARG" | sed 's/l$/c/'`
if [ -f "$SRCFILE" ]; then
cp "$SRCFILE" lex.yy.c
fi
;;
esac
fi
if [ ! -f lex.yy.c ]; then
echo 'main() { return 0; }' >lex.yy.c
fi
;;
help2man)
echo 1>&2 "\
WARNING: \`$1' is $msg. You should only need it if
you modified a dependency of a manual page. You may need the
\`Help2man' package in order for those modifications to take
effect. You can get \`Help2man' from any GNU archive site."
file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'`
if test -z "$file"; then
file=`echo "$*" | sed -n 's/.*--output=\([^ ]*\).*/\1/p'`
fi
if [ -f "$file" ]; then
touch $file
else
test -z "$file" || exec >$file
echo ".ab help2man is required to generate this page"
exit 1
fi
;;
makeinfo)
echo 1>&2 "\
WARNING: \`$1' is $msg. You should only need it if
you modified a \`.texi' or \`.texinfo' file, or any other file
indirectly affecting the aspect of the manual. The spurious
call might also be the consequence of using a buggy \`make' (AIX,
DU, IRIX). You might want to install the \`Texinfo' package or
the \`GNU make' package. Grab either from any GNU archive site."
file=`echo "$*" | sed -n 's/.*-o \([^ ]*\).*/\1/p'`
if test -z "$file"; then
file=`echo "$*" | sed 's/.* \([^ ]*\) *$/\1/'`
file=`sed -n '/^@setfilename/ { s/.* \([^ ]*\) *$/\1/; p; q; }' $file`
fi
touch $file
;;
tar)
shift
# We have already tried tar in the generic part.
# Look for gnutar/gtar before invocation to avoid ugly error
# messages.
if (gnutar --version > /dev/null 2>&1); then
gnutar "$@" && exit 0
fi
if (gtar --version > /dev/null 2>&1); then
gtar "$@" && exit 0
fi
firstarg="$1"
if shift; then
case "$firstarg" in
*o*)
firstarg=`echo "$firstarg" | sed s/o//`
tar "$firstarg" "$@" && exit 0
;;
esac
case "$firstarg" in
*h*)
firstarg=`echo "$firstarg" | sed s/h//`
tar "$firstarg" "$@" && exit 0
;;
esac
fi
echo 1>&2 "\
WARNING: I can't seem to be able to run \`tar' with the given arguments.
You may want to install GNU tar or Free paxutils, or check the
command line arguments."
exit 1
;;
*)
echo 1>&2 "\
WARNING: \`$1' is needed, and is $msg.
You might have modified some files without having the
proper tools for further handling them. Check the \`README' file,
it often tells you about the needed prerequisites for installing
this package. You may also peek at any GNU archive site, in case
some other package would contain this missing \`$1' program."
exit 1
;;
esac
exit 0
# Local variables:
# eval: (add-hook 'write-file-hooks 'time-stamp)
# time-stamp-start: "scriptversion="
# time-stamp-format: "%:y-%02m-%02d.%02H"
# time-stamp-end: "$"
# End:

143
netpkt.c Normal file
View File

@ -0,0 +1,143 @@
#include <stdio.h>
#define __USE_GNU
#include <string.h>
#include <ctype.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include "netpkt.h"
int pkt_memcmp(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size)
{
if (offset >= pkt->size)
return 1;
/* nicht ueber das paket hinaus vergleichen */
if (offset + size >= pkt->size)
size = pkt->size - offset;
return memcmp(pkt->buf + offset, search, size);
}
int pkt_memmem(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size)
{
void *found;
if (offset >= pkt->size)
return -1;
found = memmem(pkt->buf + offset, pkt->size, search, size);
return (found == NULL) ? -1 : (found - (void *)pkt->buf);
}
struct net_pkt * pkt_merge(struct net_pkt *pkt1, struct net_pkt *pkt2)
{
struct net_pkt *ret;
ret = malloc(sizeof(struct net_pkt) + pkt1->size + pkt2->size);
memcpy(&ret->addr, &pkt1->addr, sizeof(ret->addr));
ret->size = pkt1->size + pkt2->size;
memcpy(ret->buf, pkt1->buf, pkt1->size);
memcpy(ret->buf + pkt1->size, pkt2->buf, pkt2->size);
return ret;
}
char * pkt_ntoa(struct net_pkt *pkt)
{
return inet_ntoa(pkt->addr.sin_addr);
}
unsigned short pkt_getport(struct net_pkt *pkt)
{
return ntohs(pkt->addr.sin_port);
}
int pkt_sameaddr(struct net_pkt *pkt1, struct net_pkt *pkt2)
{
return (pkt1->addr.sin_addr.s_addr == pkt2->addr.sin_addr.s_addr) &&
(pkt1->addr.sin_port == pkt2->addr.sin_port);
}
int pkt_parse_int(struct net_pkt *pkt, unsigned int offset, int *val)
{
unsigned char *max = pkt->buf + pkt->size;
unsigned char *c = pkt->buf + offset;
/* untere grenze abtesten */
if (pkt->buf > c || c > max)
return -1;
*val = 0;
/* ziffern einlesen */
while (isdigit(*c) && c < max)
*val = (*val * 10) + (*c++ - 0x30);
return (c - (pkt->buf + offset));
}
int pkt_parse_ip(struct net_pkt *pkt, int offset, struct in_addr *ip)
{
int i, tmp, count, pos = offset;
ip->s_addr = 0;
for (i = 0; i < 4; i++) {
count = pkt_parse_int(pkt, pos, &tmp);
pos += count;
if (count == 0 || tmp < 0 || tmp > 255)
return 0;
ip->s_addr = ip->s_addr>>8 | tmp<<24;
if (i != 3 && pkt->buf[pos++] != '.')
return 0;
}
return pos - offset;
}
char * pkt_print(struct net_pkt *pkt)
{
int pos = 0, i = 0, j;
char *buf = malloc(pkt->size * 4 + 64);
while (pos < pkt->size) {
i += sprintf(buf + i, "%04X: ", pos);
for (j = 0; j < 16; j++) {
if (pos + j < pkt->size)
i += sprintf(buf + i, "%02X", pkt->buf[pos + j]);
else
i += sprintf(buf + i, " ");
if (j % 2)
buf[i++] = ' ';
}
for (j = 0; j < 16; j++) {
if (pos + j < pkt->size) {
unsigned char val = pkt->buf[pos + j];
if (val >= 0x20 && val < 0x80)
buf[i++] = val;
else
buf[i++] = '.';
} else {
buf[i++] = ' ';
}
}
pos += 16;
buf[i++] = '\r';
buf[i++] = '\n';
}
buf[i] = 0;
return buf;
}

113
plugin.c Normal file
View File

@ -0,0 +1,113 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <dlfcn.h>
#include "plugin.h"
#include "configfile.h"
#include "logging.h"
#include "netpkt.h"
#include "list.h"
#include "event.h"
#define BUFSIZE 512
static LIST_HEAD(plugin_list);
static int plugin_load(const char *filename, void *privdata)
{
char *plugin_dir = (char *)privdata;
char *fullname = malloc(BUFSIZE);
if (fullname == NULL) {
log_print(LOG_ERROR, "plugin_load: out of memory");
return -1;
}
int len = snprintf(fullname, BUFSIZE, "%s/%s", plugin_dir, filename);
if (len < 0 || len >= BUFSIZE) {
log_print(LOG_ERROR, "plugin_load: file name too long: %s/%s", plugin_dir, filename);
free(fullname);
return -1;
}
dlerror();
void *dlref = dlopen(fullname, RTLD_NOW);
if (dlref == NULL) {
log_print(LOG_WARN, "plugin_load: %s", dlerror());
free(fullname);
return -1;
}
struct hlswmaster_plugin *plugin = dlsym(dlref, "plugin");
if (plugin == NULL) {
log_print(LOG_WARN, "plugin_load: invalid plugin '%s'", fullname);
dlclose(dlref);
free(fullname);
return -1;
}
log_print(LOG_INFO, "loading plugin '%s'", plugin->name);
if (plugin->init == NULL || (plugin->init() == 0)) {
list_add_tail(&plugin->list, &plugin_list);
free(fullname);
return 0;
}
log_print(LOG_WARN, "plugin_load: failed to load '%s'", plugin->name);
dlclose(dlref);
free(fullname);
return -1;
}
int plugins_scan(void)
{
struct hlswmaster_plugin *plugin;
list_for_each_entry(plugin, &plugin_list, list)
if (plugin->scan && !plugin->scan())
log_print(LOG_WARN, "plugin %s: scan error", plugin->name);
return 0;
}
int plugins_parse(struct net_pkt *pkt)
{
int retval;
struct hlswmaster_plugin *plugin;
list_for_each_entry(plugin, &plugin_list, list)
if (plugin->parse && (retval = plugin->parse(pkt)))
return retval;
return PARSE_REJECT;
}
int plugin_init(void)
{
char *dir = config_get_string("global", "plugin_dir", ".");
int cnt = config_get_strings("global", "plugin", plugin_load, (void *)dir);
log_print(LOG_INFO, "%d plugins loaded", cnt);
return 0;
}

78
plugin_helper.c Normal file
View File

@ -0,0 +1,78 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include "gamelist.h"
#include "logging.h"
#include "netpkt.h"
#include "plugin_helper.h"
#include "scanner.h"
int server_add(uint16_t gameid, uint32_t ip, uint16_t port1, uint16_t port2)
{
struct game_entry *entry = malloc(sizeof(struct game_entry));
if (entry == NULL) {
log_print(LOG_WARN, "server_add(): out of memory");
return -1;
}
entry->gameid = gameid;
entry->ip = ip;
entry->port1 = port1;
entry->port2 = port2;
return gamelist_add(entry);
}
int server_add_pkt(unsigned int gameid, struct net_pkt *pkt)
{
return server_add(gameid, pkt->addr.sin_addr.s_addr, ntohs(pkt->addr.sin_port), 0);
}
int pkt_send_portarr(struct in_addr *dstip, struct scan_ports *portarr, char *buf, unsigned int size)
{
unsigned short port;
int ret = 0;
while (portarr && portarr->portlo) {
for (port = portarr->portlo; port <= portarr->porthi; port++)
if (pkt_send(dstip, port, buf, size) < 0)
ret = -1;
portarr++;
}
return ret;
}
int pkt_check_portarr(struct net_pkt *pkt, struct scan_ports *portarr)
{
unsigned short port;
while (portarr && portarr->portlo) {
for (port = portarr->portlo; port <= portarr->porthi; port++)
if (port == ntohs(pkt->addr.sin_port))
return portarr->gameid;
portarr++;
}
return 0;
}

3
plugins/.gitignore vendored Normal file
View File

@ -0,0 +1,3 @@
*.o
*.so
*.d

22
plugins/Makefile Normal file
View File

@ -0,0 +1,22 @@
PLUGINS := $(wildcard *.c)
CFLAGS := -O2 -pipe -Wall -I../include
all: $(PLUGINS:.c=.so)
%.o: %.c
$(CC) $(CFLAGS) -c $< -o $@
%.so: %_sh.o
$(LD) -shared -o $@ $<
%_sh.o: %.c
$(CC) $(CFLAGS) -fPIC -c $< -o $@
%.d: %.c
$(CC) $(CFLAGS) -MM -c $< -o $@
clean:
rm -f *.so *.d *.o
DEPS := $(wildcard *.c)
-include $(DEPS:.c=.d)

View File

@ -1,25 +0,0 @@
AUTOMAKE_OPTIONS = foreign no-dependencies
EXTRA_DIST = skel.c
INCLUDES = -I../include
pkgdata_LTLIBRARIES = doom3.la gamespy1.la gamespy2.la hlswproxy.la q3engine.la quake2.la
doom3_la_SOURCES = doom3.c
doom3_la_LDFLAGS = -module -avoid-version
gamespy1_la_SOURCES = gamespy1.c
gamespy1_la_LDFLAGS = -module -avoid-version
gamespy2_la_SOURCES = gamespy2.c
gamespy2_la_LDFLAGS = -module -avoid-version
hlswproxy_la_SOURCES = hlswproxy.c
hlswproxy_la_LDFLAGS = -module -avoid-version
q3engine_la_SOURCES = q3engine.c
q3engine_la_LDFLAGS = -module -avoid-version
quake2_la_SOURCES = quake2.c
quake2_la_LDFLAGS = -module -avoid-version

View File

@ -1,480 +0,0 @@
# Makefile.in generated by automake 1.9.4 from Makefile.am.
# @configure_input@
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
# 2003, 2004 Free Software Foundation, Inc.
# This Makefile.in is free software; the Free Software Foundation
# gives unlimited permission to copy and/or distribute it,
# with or without modifications, as long as this notice is preserved.
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
# PARTICULAR PURPOSE.
@SET_MAKE@
SOURCES = $(doom3_la_SOURCES) $(gamespy1_la_SOURCES) $(gamespy2_la_SOURCES) $(hlswproxy_la_SOURCES) $(q3engine_la_SOURCES) $(quake2_la_SOURCES)
srcdir = @srcdir@
top_srcdir = @top_srcdir@
VPATH = @srcdir@
pkgdatadir = $(datadir)/@PACKAGE@
pkglibdir = $(libdir)/@PACKAGE@
pkgincludedir = $(includedir)/@PACKAGE@
top_builddir = ..
am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
INSTALL = @INSTALL@
install_sh_DATA = $(install_sh) -c -m 644
install_sh_PROGRAM = $(install_sh) -c
install_sh_SCRIPT = $(install_sh) -c
INSTALL_HEADER = $(INSTALL_DATA)
transform = $(program_transform_name)
NORMAL_INSTALL = :
PRE_INSTALL = :
POST_INSTALL = :
NORMAL_UNINSTALL = :
PRE_UNINSTALL = :
POST_UNINSTALL = :
build_triplet = @build@
host_triplet = @host@
subdir = plugins
DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
am__aclocal_m4_deps = $(top_srcdir)/configure.in
am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
$(ACLOCAL_M4)
mkinstalldirs = $(install_sh) -d
CONFIG_HEADER = $(top_builddir)/config.h
CONFIG_CLEAN_FILES =
am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`;
am__vpath_adj = case $$p in \
$(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \
*) f=$$p;; \
esac;
am__strip_dir = `echo $$p | sed -e 's|^.*/||'`;
am__installdirs = "$(DESTDIR)$(pkgdatadir)"
pkgdataLTLIBRARIES_INSTALL = $(INSTALL)
LTLIBRARIES = $(pkgdata_LTLIBRARIES)
doom3_la_LIBADD =
am_doom3_la_OBJECTS = doom3.lo
doom3_la_OBJECTS = $(am_doom3_la_OBJECTS)
gamespy1_la_LIBADD =
am_gamespy1_la_OBJECTS = gamespy1.lo
gamespy1_la_OBJECTS = $(am_gamespy1_la_OBJECTS)
gamespy2_la_LIBADD =
am_gamespy2_la_OBJECTS = gamespy2.lo
gamespy2_la_OBJECTS = $(am_gamespy2_la_OBJECTS)
hlswproxy_la_LIBADD =
am_hlswproxy_la_OBJECTS = hlswproxy.lo
hlswproxy_la_OBJECTS = $(am_hlswproxy_la_OBJECTS)
q3engine_la_LIBADD =
am_q3engine_la_OBJECTS = q3engine.lo
q3engine_la_OBJECTS = $(am_q3engine_la_OBJECTS)
quake2_la_LIBADD =
am_quake2_la_OBJECTS = quake2.lo
quake2_la_OBJECTS = $(am_quake2_la_OBJECTS)
DEFAULT_INCLUDES = -I. -I$(srcdir) -I$(top_builddir)
depcomp =
am__depfiles_maybe =
COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
$(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
LTCOMPILE = $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) \
$(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \
$(AM_CFLAGS) $(CFLAGS)
CCLD = $(CC)
LINK = $(LIBTOOL) --tag=CC --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \
$(AM_LDFLAGS) $(LDFLAGS) -o $@
SOURCES = $(doom3_la_SOURCES) $(gamespy1_la_SOURCES) \
$(gamespy2_la_SOURCES) $(hlswproxy_la_SOURCES) \
$(q3engine_la_SOURCES) $(quake2_la_SOURCES)
DIST_SOURCES = $(doom3_la_SOURCES) $(gamespy1_la_SOURCES) \
$(gamespy2_la_SOURCES) $(hlswproxy_la_SOURCES) \
$(q3engine_la_SOURCES) $(quake2_la_SOURCES)
ETAGS = etags
CTAGS = ctags
DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
ACLOCAL = @ACLOCAL@
AMDEP_FALSE = @AMDEP_FALSE@
AMDEP_TRUE = @AMDEP_TRUE@
AMTAR = @AMTAR@
AR = @AR@
AUTOCONF = @AUTOCONF@
AUTOHEADER = @AUTOHEADER@
AUTOMAKE = @AUTOMAKE@
AWK = @AWK@
CC = @CC@
CCDEPMODE = @CCDEPMODE@
CFLAGS = @CFLAGS@
CPP = @CPP@
CPPFLAGS = @CPPFLAGS@
CXX = @CXX@
CXXCPP = @CXXCPP@
CXXDEPMODE = @CXXDEPMODE@
CXXFLAGS = @CXXFLAGS@
CYGPATH_W = @CYGPATH_W@
DEFS = @DEFS@
DEPDIR = @DEPDIR@
ECHO = @ECHO@
ECHO_C = @ECHO_C@
ECHO_N = @ECHO_N@
ECHO_T = @ECHO_T@
EGREP = @EGREP@
EXEEXT = @EXEEXT@
F77 = @F77@
FFLAGS = @FFLAGS@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_SCRIPT = @INSTALL_SCRIPT@
INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
LDFLAGS = @LDFLAGS@
LIBOBJS = @LIBOBJS@
LIBS = @LIBS@
LIBTOOL = @LIBTOOL@
LN_S = @LN_S@
LTLIBOBJS = @LTLIBOBJS@
MAINT = @MAINT@
MAINTAINER_MODE_FALSE = @MAINTAINER_MODE_FALSE@
MAINTAINER_MODE_TRUE = @MAINTAINER_MODE_TRUE@
MAKEINFO = @MAKEINFO@
OBJEXT = @OBJEXT@
PACKAGE = @PACKAGE@
PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
PACKAGE_NAME = @PACKAGE_NAME@
PACKAGE_STRING = @PACKAGE_STRING@
PACKAGE_TARNAME = @PACKAGE_TARNAME@
PACKAGE_VERSION = @PACKAGE_VERSION@
PATH_SEPARATOR = @PATH_SEPARATOR@
RANLIB = @RANLIB@
SET_MAKE = @SET_MAKE@
SHELL = @SHELL@
STRIP = @STRIP@
VERSION = @VERSION@
ac_ct_AR = @ac_ct_AR@
ac_ct_CC = @ac_ct_CC@
ac_ct_CXX = @ac_ct_CXX@
ac_ct_F77 = @ac_ct_F77@
ac_ct_RANLIB = @ac_ct_RANLIB@
ac_ct_STRIP = @ac_ct_STRIP@
am__fastdepCC_FALSE = @am__fastdepCC_FALSE@
am__fastdepCC_TRUE = @am__fastdepCC_TRUE@
am__fastdepCXX_FALSE = @am__fastdepCXX_FALSE@
am__fastdepCXX_TRUE = @am__fastdepCXX_TRUE@
am__include = @am__include@
am__leading_dot = @am__leading_dot@
am__quote = @am__quote@
am__tar = @am__tar@
am__untar = @am__untar@
bindir = @bindir@
build = @build@
build_alias = @build_alias@
build_cpu = @build_cpu@
build_os = @build_os@
build_vendor = @build_vendor@
datadir = @datadir@
exec_prefix = @exec_prefix@
host = @host@
host_alias = @host_alias@
host_cpu = @host_cpu@
host_os = @host_os@
host_vendor = @host_vendor@
includedir = @includedir@
infodir = @infodir@
install_sh = @install_sh@
libdir = @libdir@
libexecdir = @libexecdir@
localstatedir = @localstatedir@
mandir = @mandir@
mkdir_p = @mkdir_p@
oldincludedir = @oldincludedir@
prefix = @prefix@
program_transform_name = @program_transform_name@
sbindir = @sbindir@
sharedstatedir = @sharedstatedir@
sysconfdir = @sysconfdir@
target_alias = @target_alias@
AUTOMAKE_OPTIONS = foreign no-dependencies
EXTRA_DIST = skel.c
INCLUDES = -I../include
pkgdata_LTLIBRARIES = doom3.la gamespy1.la gamespy2.la hlswproxy.la q3engine.la quake2.la
doom3_la_SOURCES = doom3.c
doom3_la_LDFLAGS = -module -avoid-version
gamespy1_la_SOURCES = gamespy1.c
gamespy1_la_LDFLAGS = -module -avoid-version
gamespy2_la_SOURCES = gamespy2.c
gamespy2_la_LDFLAGS = -module -avoid-version
hlswproxy_la_SOURCES = hlswproxy.c
hlswproxy_la_LDFLAGS = -module -avoid-version
q3engine_la_SOURCES = q3engine.c
q3engine_la_LDFLAGS = -module -avoid-version
quake2_la_SOURCES = quake2.c
quake2_la_LDFLAGS = -module -avoid-version
all: all-am
.SUFFIXES:
.SUFFIXES: .c .lo .o .obj
$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps)
@for dep in $?; do \
case '$(am__configure_deps)' in \
*$$dep*) \
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
&& exit 0; \
exit 1;; \
esac; \
done; \
echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign plugins/Makefile'; \
cd $(top_srcdir) && \
$(AUTOMAKE) --foreign plugins/Makefile
.PRECIOUS: Makefile
Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
@case '$?' in \
*config.status*) \
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
*) \
echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
esac;
$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
install-pkgdataLTLIBRARIES: $(pkgdata_LTLIBRARIES)
@$(NORMAL_INSTALL)
test -z "$(pkgdatadir)" || $(mkdir_p) "$(DESTDIR)$(pkgdatadir)"
@list='$(pkgdata_LTLIBRARIES)'; for p in $$list; do \
if test -f $$p; then \
f=$(am__strip_dir) \
echo " $(LIBTOOL) --mode=install $(pkgdataLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) '$$p' '$(DESTDIR)$(pkgdatadir)/$$f'"; \
$(LIBTOOL) --mode=install $(pkgdataLTLIBRARIES_INSTALL) $(INSTALL_STRIP_FLAG) "$$p" "$(DESTDIR)$(pkgdatadir)/$$f"; \
else :; fi; \
done
uninstall-pkgdataLTLIBRARIES:
@$(NORMAL_UNINSTALL)
@set -x; list='$(pkgdata_LTLIBRARIES)'; for p in $$list; do \
p=$(am__strip_dir) \
echo " $(LIBTOOL) --mode=uninstall rm -f '$(DESTDIR)$(pkgdatadir)/$$p'"; \
$(LIBTOOL) --mode=uninstall rm -f "$(DESTDIR)$(pkgdatadir)/$$p"; \
done
clean-pkgdataLTLIBRARIES:
-test -z "$(pkgdata_LTLIBRARIES)" || rm -f $(pkgdata_LTLIBRARIES)
@list='$(pkgdata_LTLIBRARIES)'; for p in $$list; do \
dir="`echo $$p | sed -e 's|/[^/]*$$||'`"; \
test "$$dir" != "$$p" || dir=.; \
echo "rm -f \"$${dir}/so_locations\""; \
rm -f "$${dir}/so_locations"; \
done
doom3.la: $(doom3_la_OBJECTS) $(doom3_la_DEPENDENCIES)
$(LINK) -rpath $(pkgdatadir) $(doom3_la_LDFLAGS) $(doom3_la_OBJECTS) $(doom3_la_LIBADD) $(LIBS)
gamespy1.la: $(gamespy1_la_OBJECTS) $(gamespy1_la_DEPENDENCIES)
$(LINK) -rpath $(pkgdatadir) $(gamespy1_la_LDFLAGS) $(gamespy1_la_OBJECTS) $(gamespy1_la_LIBADD) $(LIBS)
gamespy2.la: $(gamespy2_la_OBJECTS) $(gamespy2_la_DEPENDENCIES)
$(LINK) -rpath $(pkgdatadir) $(gamespy2_la_LDFLAGS) $(gamespy2_la_OBJECTS) $(gamespy2_la_LIBADD) $(LIBS)
hlswproxy.la: $(hlswproxy_la_OBJECTS) $(hlswproxy_la_DEPENDENCIES)
$(LINK) -rpath $(pkgdatadir) $(hlswproxy_la_LDFLAGS) $(hlswproxy_la_OBJECTS) $(hlswproxy_la_LIBADD) $(LIBS)
q3engine.la: $(q3engine_la_OBJECTS) $(q3engine_la_DEPENDENCIES)
$(LINK) -rpath $(pkgdatadir) $(q3engine_la_LDFLAGS) $(q3engine_la_OBJECTS) $(q3engine_la_LIBADD) $(LIBS)
quake2.la: $(quake2_la_OBJECTS) $(quake2_la_DEPENDENCIES)
$(LINK) -rpath $(pkgdatadir) $(quake2_la_LDFLAGS) $(quake2_la_OBJECTS) $(quake2_la_LIBADD) $(LIBS)
mostlyclean-compile:
-rm -f *.$(OBJEXT)
distclean-compile:
-rm -f *.tab.c
.c.o:
$(COMPILE) -c $<
.c.obj:
$(COMPILE) -c `$(CYGPATH_W) '$<'`
.c.lo:
$(LTCOMPILE) -c -o $@ $<
mostlyclean-libtool:
-rm -f *.lo
clean-libtool:
-rm -rf .libs _libs
distclean-libtool:
-rm -f libtool
uninstall-info-am:
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
mkid -fID $$unique
tags: TAGS
TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
test -n "$$unique" || unique=$$empty_fix; \
$(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
$$tags $$unique; \
fi
ctags: CTAGS
CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
test -z "$(CTAGS_ARGS)$$tags$$unique" \
|| $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
$$tags $$unique
GTAGS:
here=`$(am__cd) $(top_builddir) && pwd` \
&& cd $(top_srcdir) \
&& gtags -i $(GTAGS_ARGS) $$here
distclean-tags:
-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
distdir: $(DISTFILES)
@srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; \
topsrcdirstrip=`echo "$(top_srcdir)" | sed 's|.|.|g'`; \
list='$(DISTFILES)'; for file in $$list; do \
case $$file in \
$(srcdir)/*) file=`echo "$$file" | sed "s|^$$srcdirstrip/||"`;; \
$(top_srcdir)/*) file=`echo "$$file" | sed "s|^$$topsrcdirstrip/|$(top_builddir)/|"`;; \
esac; \
if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
dir=`echo "$$file" | sed -e 's,/[^/]*$$,,'`; \
if test "$$dir" != "$$file" && test "$$dir" != "."; then \
dir="/$$dir"; \
$(mkdir_p) "$(distdir)$$dir"; \
else \
dir=''; \
fi; \
if test -d $$d/$$file; then \
if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
fi; \
cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
else \
test -f $(distdir)/$$file \
|| cp -p $$d/$$file $(distdir)/$$file \
|| exit 1; \
fi; \
done
check-am: all-am
check: check-am
all-am: Makefile $(LTLIBRARIES)
installdirs:
for dir in "$(DESTDIR)$(pkgdatadir)"; do \
test -z "$$dir" || $(mkdir_p) "$$dir"; \
done
install: install-am
install-exec: install-exec-am
install-data: install-data-am
uninstall: uninstall-am
install-am: all-am
@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
installcheck: installcheck-am
install-strip:
$(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
`test -z '$(STRIP)' || \
echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
mostlyclean-generic:
clean-generic:
distclean-generic:
-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
maintainer-clean-generic:
@echo "This command is intended for maintainers to use"
@echo "it deletes files that may require special tools to rebuild."
clean: clean-am
clean-am: clean-generic clean-libtool clean-pkgdataLTLIBRARIES \
mostlyclean-am
distclean: distclean-am
-rm -f Makefile
distclean-am: clean-am distclean-compile distclean-generic \
distclean-libtool distclean-tags
dvi: dvi-am
dvi-am:
html: html-am
info: info-am
info-am:
install-data-am: install-pkgdataLTLIBRARIES
install-exec-am:
install-info: install-info-am
install-man:
installcheck-am:
maintainer-clean: maintainer-clean-am
-rm -f Makefile
maintainer-clean-am: distclean-am maintainer-clean-generic
mostlyclean: mostlyclean-am
mostlyclean-am: mostlyclean-compile mostlyclean-generic \
mostlyclean-libtool
pdf: pdf-am
pdf-am:
ps: ps-am
ps-am:
uninstall-am: uninstall-info-am uninstall-pkgdataLTLIBRARIES
.PHONY: CTAGS GTAGS all all-am check check-am clean clean-generic \
clean-libtool clean-pkgdataLTLIBRARIES ctags distclean \
distclean-compile distclean-generic distclean-libtool \
distclean-tags distdir dvi dvi-am html html-am info info-am \
install install-am install-data install-data-am install-exec \
install-exec-am install-info install-info-am install-man \
install-pkgdataLTLIBRARIES install-strip installcheck \
installcheck-am installdirs maintainer-clean \
maintainer-clean-generic mostlyclean mostlyclean-compile \
mostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \
tags uninstall uninstall-am uninstall-info-am \
uninstall-pkgdataLTLIBRARIES
# Tell versions [3.59,3.63) of GNU make to not export all variables.
# Otherwise a system limit (for SysV at least) may be exceeded.
.NOEXPORT:

View File

@ -1,5 +1,5 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* Copyright (C) 12/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
@ -18,36 +18,41 @@
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <string.h>
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
static struct scan_ports port_arr[] = {
{ 27666, 27673, 38 }, /* Doom 3 */
{ 28004, 28008, 47 }, /* Quake 4 */
{ 0,0,0 }
};
static char scanmsg[] = "\xff\xffgetInfo";
static char replymsg[] = "\xff\xffinfoResponse";
static int scan(void) {
static int scan(void)
{
pkt_send_portarr(NULL, port_arr, scanmsg, strlen(scanmsg));
return 1;
}
static int parse(struct net_pkt *pkt) {
static int parse(struct net_pkt *pkt)
{
int gameid;
if (!(gameid = pkt_check_portarr(pkt, port_arr)))
return 0;
return PARSE_REJECT;
if (pkt_memcmp(pkt, 0, replymsg, strlen(replymsg)))
return 0;
return PARSE_REJECT;
server_add_pkt(gameid, pkt);
return 1;
return PARSE_ACCEPT;
}
struct hlswmaster_plugin plugin = {
.name = "doom3",
.name = "d3engine",
.scan = &scan,
.parse = &parse,
};

View File

@ -17,101 +17,285 @@
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include "logging.h"
#include "event.h"
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
static struct scan_ports port_arr[] = {
{ 7777, 7788, 5 }, /* ut(5), ut2k3(14), ut2k4(33) */
{ 7777, 7788, 5 }, /* ut(5), ut2k3(14), rune(18), ut2k4(33), aao(15) */
{ 22000, 22010, 16 }, /* bf1942(16) */
{ 23000, 23010, 35 }, /* bfv(35) */
{ 26001, 26011, 19 }, /* igi2(19) */
{ 27888, 27888, 17 }, /* avp2(17) (nur der standart-port..) */
{ 0, 0, 0 }
{ 44400, 44400, 51 },
{ 0, 0, 0 }
};
static char scanmsg[] = "\\status\\";
static char ut_reply[] = "\\gamename\\ut\\";
static char ut2k3_reply[] = "\\gamename\\ut2\\";
static char ut2k4_reply[] = "\\gamename\\ut2004\\";
static char bf1942_reply[] = "\\gamename\\bfield1942\\";
static char bfv_reply[] = "\\game_id\\bfvietnam\\";
static char avp2_reply[] = "\\gamename\\avp2\\";
static char igi2_reply[] = "\\gamename\\projectigi2r\\";
static char hostport_search[] = "\\hostport\\";
struct gs1_part {
struct list_head list;
unsigned long timeout;
unsigned int queryid;
unsigned int subid;
struct net_pkt *pkt;
};
static int scan(void) {
static LIST_HEAD(gs1_partlist);
static char scanmsg[] = "\\status\\";
static char search_queryid[] = "\\queryid\\";
static char search_final[] = "\\final\\";
static char search_hostport[] = "\\hostport\\";
static char search_gamename[] = "\\gamename\\";
static char search_gameid[] = "\\game_id\\";
static char reply_ut[] = "ut\\";
static char reply_ut2k3[] = "ut2\\";
static char reply_ut2k4[] = "ut2004\\";
static char reply_bf1942[] = "bfield1942\\";
static char reply_bfv1[] = "bfvietnam\\";
static char reply_bfv2[] = "BFVIETNAM\\";
static char reply_poe[] = "poe\\";
static char reply_opk[] = "opk\\";
static char reply_avp2[] = "avp2\\";
static char reply_igi2[] = "projectigi2r\\";
static char reply_aao[] = "armygame\\";
static char reply_rune[] = "rune\\";
static char reply_postal2[] ="postal2\\";
static int scan(void)
{
pkt_send_portarr(NULL, port_arr, scanmsg, strlen(scanmsg));
return 1;
}
static int parse(struct net_pkt *pkt) {
int gameid, port;
void *p;
static struct net_pkt * gs1_pkt_merge(struct net_pkt *pkt, unsigned int queryid, unsigned int subid)
{
struct net_pkt *retpkt = NULL;
struct gs1_part *part, *tmp;
unsigned int i = 1, found = 0, notfound = 0;
if (!(gameid = pkt_check_portarr(pkt, port_arr)))
return 0;
// wenn paket non-final ist, in liste speichern
// NULL zurueckgeben
if (pkt_memmem(pkt, 0, search_final, strlen(search_final)) == -1) {
part = malloc(sizeof(struct gs1_part));
part->timeout = time(NULL);
part->queryid = queryid;
part->subid = subid;
part->pkt = pkt;
// in liste packen
list_add_tail(&part->list, &gs1_partlist);
return NULL;
}
// wenn paket final ist, dann mit evtl. non-final paketen mergen
// komplettes Paket zurueckgeben
while (i < subid && notfound <= subid) {
found = 0;
list_for_each_entry_safe(part, tmp, &gs1_partlist, list) {
if (pkt_sameaddr(part->pkt, pkt) && (part->queryid == queryid) && part->subid == i) {
if (retpkt != NULL) {
struct net_pkt *retpkt2 = retpkt;
retpkt = pkt_merge(retpkt, part->pkt);
free(retpkt2);
free(part->pkt);
} else {
retpkt = part->pkt;
}
list_del(&part->list);
free(part);
found = 1;
i++;
}
}
if (found == 0)
notfound++;
}
/* merge error, eat last paket, cleanup */
if (i != subid || notfound > subid) {
log_print(LOG_INFO, "gs1: merging error!");
free(pkt);
return NULL;
}
return (retpkt != NULL) ? pkt_merge(retpkt, pkt) : pkt;
}
static int parse_real(struct net_pkt *pkt, int gameid)
{
int port, offset, pos1, pos2;
pos1 = pkt_memmem(pkt, 0, search_gamename, strlen(search_gamename));
pos1 += strlen(search_gamename);
pos2 = pkt_memmem(pkt, 0, search_gameid, strlen(search_gameid));
pos2 += strlen(search_gameid);
switch (gameid) {
case 5:/* unreal tournament 2k3 */
if (pkt_memmem(pkt, 0, ut_reply, strlen(ut_reply)))
case 5:/* unreal tournament */
if (!pkt_memcmp(pkt, pos1, reply_ut, strlen(reply_ut)))
gameid = 5;
/* unreal tournament 2k3 */
else if (pkt_memmem(pkt, 0, ut2k3_reply, strlen(ut2k3_reply)))
else if (!pkt_memcmp(pkt, pos1, reply_ut2k3, strlen(reply_ut2k4)))
gameid = 14;
/* unreal tournament 2k4 */
else if (pkt_memmem(pkt, 0, ut2k4_reply, strlen(ut2k4_reply)))
else if (!pkt_memcmp(pkt, pos1, reply_ut2k4, strlen(reply_ut2k4)))
gameid = 33;
/* americas army operations */
else if (!pkt_memcmp(pkt, pos1, reply_aao, strlen(reply_aao)))
gameid = 15;
/* postal2 */
else if (!pkt_memcmp(pkt, pos1, reply_postal2, strlen(reply_postal2)))
gameid = 9;
else
return 0;
return PARSE_REJECT;
break;
case 16:/* battlefield 1942 */
if (!pkt_memmem(pkt, 0, bf1942_reply, strlen(bf1942_reply)))
return 0;
case 35:/* battlefield vietnam */
if (!pkt_memcmp(pkt, pos1, reply_bf1942, strlen(reply_bf1942)))
gameid = 16;
else if (!pkt_memcmp(pkt, pos2, reply_bfv1, strlen(reply_bfv1)))
gameid = 35;
else if (!pkt_memcmp(pkt, pos2, reply_bfv2, strlen(reply_bfv2)))
gameid = 35;
else if (!pkt_memcmp(pkt, pos2, reply_poe, strlen(reply_poe)))
gameid = 35;
else if (!pkt_memcmp(pkt, pos2, reply_opk, strlen(reply_opk)))
gameid = 35;
else
return PARSE_REJECT;
break;
case 17:/* alien vs. predator 2 */
if (!pkt_memmem(pkt, 0, avp2_reply, strlen(avp2_reply)))
return 0;
if (!pkt_memcmp(pkt, pos1, reply_avp2, strlen(reply_avp2)))
gameid = 17;
else
return PARSE_REJECT;
break;
case 18:/* rune */
if (!pkt_memcmp(pkt, pos1, reply_rune, strlen(reply_rune)))
gameid = 18;
else
return PARSE_REJECT;
break;
case 19:/* project igi2 covert strike */
if (!pkt_memmem(pkt, 0, igi2_reply, strlen(igi2_reply)))
return 0;
if (!pkt_memcmp(pkt, pos1, reply_igi2, strlen(reply_igi2)))
gameid = 19;
else
return PARSE_REJECT;
break;
case 35:/* battlefield vietnam */
if (!pkt_memmem(pkt, 0, bfv_reply, strlen(bfv_reply)))
return 0;
break;
default:
return 0;
return PARSE_REJECT;
}
/* hostport angabe suchen */
p = pkt_memmem(pkt, 0, hostport_search, strlen(hostport_search));
if (p) {
port = pkt_atoi(pkt, p + strlen(hostport_search));
}
offset = pkt_memmem(pkt, 0, search_hostport, strlen(search_hostport));
if (offset != -1)
pkt_parse_int(pkt, offset + strlen(search_hostport), &port);
/* wenn ein hostport angegeben wurde, und das nicht der src port ist
** beide ports in die serverliste uebernehmen
*/
if (p && port != ntohs(pkt->addr.sin_port)) {
/*
* wenn ein hostport angegeben wurde, und das nicht der src port ist
* beide ports in die serverliste uebernehmen
*/
if ((offset != -1) && (port != ntohs(pkt->addr.sin_port))) {
server_add(gameid, pkt->addr.sin_addr.s_addr, port, ntohs(pkt->addr.sin_port));
} else {
server_add_pkt(gameid, pkt);
}
return 1;
return PARSE_ACCEPT;
}
static int parse(struct net_pkt *pkt)
{
struct net_pkt *pkt2;
int gameid, pos, offset, queryid, subid, retval;
if (!(gameid = pkt_check_portarr(pkt, port_arr)))
return PARSE_REJECT;
/* eat ut connection attemps */
if (gameid == 5 && pkt->size <= 6)
return PARSE_ACCEPT;
if ((offset = pkt_memmem(pkt, 0, search_queryid, strlen(search_queryid))) == -1)
return PARSE_REJECT;
pos = offset + strlen(search_queryid);
if ((offset = pkt_parse_int(pkt, pos, &queryid)) == 0)
return PARSE_REJECT;
pos += offset +1;
if ((offset = pkt_parse_int(pkt, pos, &subid)) == 0)
return PARSE_REJECT;
/* multipaket antworten zusammenfassen
* wenn paket non-final, dann einfach annehmen
*/
if ((pkt2 = gs1_pkt_merge(pkt, queryid, subid)) == NULL)
return PARSE_ACCEPT_FREED;
retval = parse_real(pkt2, gameid);
/* free merged packet */
if (pkt != pkt2)
free(pkt2);
return retval;
}
static int gc(void *privdata) {
unsigned int timeout = (int)privdata;
unsigned long now = time(NULL);
struct gs1_part *part, *tmp;
list_for_each_entry_safe(part, tmp, &gs1_partlist, list) {
if (part->timeout + timeout < now) {
log_print(LOG_INFO, "gs1: removing dead fragment");
list_del(&part->list);
free(part->pkt);
free(part);
}
}
return 0;
}
static int init(void)
{
int timeout = config_get_int("gamespy1", "gc_timeout", 90);
struct timeval tv;
tv.tv_sec = timeout;
tv.tv_usec = 0;
event_add_timeout(&tv, gc, (void *)timeout);
return 0;
}
struct hlswmaster_plugin plugin = {
.name = "gamespy1",
.scan = &scan,
.parse = &parse,
.init = &init,
};

View File

@ -18,32 +18,86 @@
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <string.h>
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
static struct scan_ports port_arr[] = {
{ 2302, 2302, 30 }, /* halo(30) */
{ 0,0,0 }
{ 2302, 2302, 30 }, /* halo(30) */
{ 3455, 3455, 37 }, /* painkiller(34) */
{ 10481, 10482, 44 }, /* swat4 (44) */
{ 29900, 29910, 45 }, /* battlefield2 (45) */
{ 0, 0, 0 }
};
static char scanmsg[] = { 0xFE, 0xFD, 0x00, 0xDE, 0xAD, 0xBE, 0xEF, 0x00, 0x00, 0x00 };
static char scanmsg[] = { 0xFE, 0xFD, 0x00, 0xDE, 0xAD, 0xBE, 0xEF, 0xFF, 0x00, 0x00 };
static char replymsg[] = { 0x00, 0xDE, 0xAD, 0xBE, 0xEF };
static int scan(void) {
static char search_hostport[] = "hostport";
static char search_gamename[] = "gamename";
static char reply_bf2[] = "battlefield2";
static int scan(void)
{
pkt_send_portarr(NULL, port_arr, scanmsg, sizeof(scanmsg));
return 1;
}
static int parse(struct net_pkt *pkt) {
int gameid;
static int parse(struct net_pkt *pkt)
{
int gameid, pos1, pos3, port;
if (!(gameid = pkt_check_portarr(pkt, port_arr)))
return 0;
if (pkt_memcmp(pkt, 0, replymsg, sizeof(replymsg)))
return 0;
return PARSE_REJECT;
server_add_pkt(gameid, pkt);
return 1;
if (pkt_memcmp(pkt, 0, replymsg, sizeof(replymsg)))
return PARSE_REJECT;
pos1 = pkt_memmem(pkt, 0, search_gamename, strlen(search_gamename));
pos1 += strlen(search_gamename) +1;
/* hostport angabe suchen */
pos3 = pkt_memmem(pkt, 0, search_hostport, strlen(search_hostport));
if (pos3 != -1)
pkt_parse_int(pkt, pos3 + strlen(search_hostport) +1, &port);
switch (gameid) {
case 30:/* halo */
case 37:/* painkiller */
break;
case 44:/* swat4 */
if (pos3 != -1)
gameid = 44;
else
return PARSE_REJECT;
break;
case 45:/* battlefield 2 */
// todo: pos3 check noetig?
if (!pkt_memcmp(pkt, pos1, reply_bf2, strlen(reply_bf2)) && pos3 != -1)
gameid = 45;
else
return PARSE_REJECT;
break;
default:
return PARSE_REJECT;
break;
}
/*
* wenn ein hostport angegeben wurde, und das nicht der src port ist
* beide ports in die serverliste uebernehmen
*/
if ((pos3 != -1) && (port != ntohs(pkt->addr.sin_port))) {
server_add(gameid, pkt->addr.sin_addr.s_addr, port, ntohs(pkt->addr.sin_port));
} else {
server_add_pkt(gameid, pkt);
}
return PARSE_ACCEPT;
}
struct hlswmaster_plugin plugin = {

179
plugins/halflife.c Normal file
View File

@ -0,0 +1,179 @@
/***************************************************************************
* Copyright (C) 04/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdlib.h>
#include <string.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
#include "logging.h"
struct validnet_entry {
struct list_head list;
struct in_addr ip;
struct in_addr netmask;
};
static LIST_HEAD(validnet_list);
static struct scan_ports port_arr[] = {
{ 27015, 27024, 1 }, /* cs/hl */
{ 0, 0, 0 }
};
static char scanmsg1[] = "\xff\xff\xff\xff" "details";
static char scanmsg2[] = "\xff\xff\xff\xff\x54";
static char scanmsg3[] = "\xff\xff\xff\xff" "TSource Engine Query";
static int scan(void)
{
pkt_send_portarr(NULL, port_arr, scanmsg1, strlen(scanmsg1));
pkt_send_portarr(NULL, port_arr, scanmsg2, strlen(scanmsg2));
pkt_send_portarr(NULL, port_arr, scanmsg3, strlen(scanmsg3));
return 1;
}
static int parse(struct net_pkt *pkt)
{
struct in_addr tmp;
int port, count, pos;
if (!pkt_check_portarr(pkt, port_arr))
return PARSE_REJECT;
// check 0xFF 0xFF 0xFF 0xFF
if (pkt_memcmp(pkt, 0, scanmsg1, 4))
return PARSE_REJECT;
/* check for short answer without ip/port */
if (pkt->size >= 5 && pkt->buf[4] == 'm' && pkt->buf[5] == 0x00) {
server_add_pkt(1, pkt);
return PARSE_ACCEPT;
}
/* second query?! */
if (pkt->size >= 5 && pkt->buf[4] == 'I' && pkt->buf[5] == 0x07) {
server_add_pkt(40, pkt);
return PARSE_ACCEPT;
}
/* parse server IP */
pos = 5;
if ((count = pkt_parse_ip(pkt, pos, &tmp)) == 0)
return PARSE_REJECT;
/* parse server port */
pos += count +1;
if ((count = pkt_parse_int(pkt, pos, &port)) == 0)
return PARSE_REJECT;
/* check server IP */
struct validnet_entry *entry;
list_for_each_entry(entry, &validnet_list, list) {
if (((entry->ip.s_addr ^ tmp.s_addr) & entry->netmask.s_addr) == 0) {
server_add(1, tmp.s_addr, port, 0);
return PARSE_ACCEPT;
}
}
server_add(1, pkt->addr.sin_addr.s_addr, port, 0);
return PARSE_ACCEPT;
}
// TODO: wrong place
int parse_ipmask(const char *value, struct in_addr *ip, struct in_addr *netmask)
{
char *buf = strdup(value);
if (buf == NULL)
return -1;
int retval = -1;
char *p = strchr(buf, '/');
/* valid_net x.x.x.x */
if (p == NULL) {
/* single ip */
if (inet_pton(AF_INET, buf, ip) > 0) {
netmask->s_addr = 0xFFFFFFFF;
retval = 0;
}
/* valid_net x.x.x.x/x.x.x.x or x.x.x.x/xx */
} else {
*p = 0x00;
/* ip */
if (inet_pton(AF_INET, buf, &ip) > 0) {
/* x.x.x.x/x.x.x.x */
if (inet_pton(AF_INET, p+1, netmask) > 0) {
retval = 0;
/* x.x.x.x/xx */
} else {
int mask = atoi(p+1);
if (mask >= 0 && mask <= 32) {
netmask->s_addr = htonl(0xFFFFFFFF << (32 - mask));
retval = 0;
}
}
}
*p = '/';
}
free(buf);
return retval;
}
static int init_callback(const char *value, void *privdata)
{
struct validnet_entry *entry = malloc(sizeof(struct validnet_entry));
if (entry == NULL) {
log_print(LOG_ERROR, "halflife_init(): out of memory");
return -1;
}
if (parse_ipmask(value, &entry->ip, &entry->netmask) != 0) {
log_print(LOG_WARN, " invalid dst: %s", value);
free(entry);
return -1;
}
list_add(&entry->list, &validnet_list);
return 0;
}
static int init(void)
{
config_get_strings("halflife", "valid_net", init_callback, NULL);
return 0;
}
struct hlswmaster_plugin plugin = {
.name = "halflife",
.scan = &scan,
.parse = &parse,
.init = &init,
};

View File

@ -17,77 +17,89 @@
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <netinet/in.h>
#include <inttypes.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
#include "logging.h"
#include "scanner.h"
struct _entry {
u_int16_t gameid;
u_int32_t ip;
u_int16_t port1;
u_int16_t port2;
struct game_entry {
uint16_t gameid;
uint32_t ip;
uint16_t port1;
uint16_t port2;
} __attribute__ ((packed));
static struct in_addr *ip_arr = NULL;
static int ip_arr_size = 0;
struct master_entry {
struct list_head list;
struct sockaddr_in addr;
};
static LIST_HEAD(master_list);
static char scanmsg[] = "\xff\xff\xff\xffHLSWLANSEARCH";
static int scan(void) {
int i;
for (i = 0; i < ip_arr_size; i++)
pkt_send(&ip_arr[i], 7140, scanmsg, sizeof(scanmsg));
static int scan(void)
{
struct master_entry *entry;
list_for_each_entry(entry, &master_list, list)
pkt_send(&entry->addr.sin_addr, ntohs(entry->addr.sin_port), scanmsg, sizeof(scanmsg));
return 1;
}
static int parse(struct net_pkt *pkt) {
struct _entry *server;
static int parse(struct net_pkt *pkt)
{
// TODO: check against master_list
if (pkt_getport(pkt) != 7140)
return 0;
return PARSE_REJECT;
server = (void *)pkt->buf + sizeof(scanmsg);
struct game_entry *game = (void *)pkt->buf + sizeof(scanmsg);
while ((void *)server < ((void *)pkt->buf + pkt->size)) {
server_add(server->gameid, server->ip, server->port1, server->port2);
server++;
while ((void *)game < ((void *)pkt->buf + pkt->size)) {
server_add(game->gameid, game->ip, game->port1, game->port2);
game++;
}
return 1;
return PARSE_ACCEPT;
}
static int init(struct conf_section *section) {
struct conf_tupel *tupel;
int i = 0;
list_for_each_entry(tupel, &section->tupel, list)
if (!strcmp(tupel->option, "scan_ip"))
i++;
if (i == 0 || !(ip_arr = malloc(sizeof(struct in_addr) * i)))
return 0;
i = 0;
list_for_each_entry(tupel, &section->tupel, list) {
if (!strcmp(tupel->option, "scan_ip")) {
if (inet_pton(AF_INET, tupel->parameter, &ip_arr[i]) <= 0) {
log_print(" invalid ip: %s", tupel->parameter);
} else {
log_print(" adding %s", tupel->parameter);
i++;
}
}
static int init_callback(const char *value, void *privdata)
{
struct master_entry *entry = malloc(sizeof(struct master_entry));
if (entry == NULL) {
log_print(LOG_ERROR, "hlswproxy_init(): out of memory");
return -1;
}
ip_arr_size = i;
log_print(" added %d master server(s)", i);
return 1;
if (parse_saddr(value, &entry->addr) != 0) {
log_print(LOG_WARN, " invalid dst: %s", value);
free(entry);
return -1;
}
log_print(LOG_INFO, " adding remote master %s:%d",
inet_ntoa(entry->addr.sin_addr), ntohs(entry->addr.sin_port));
list_add(&entry->list, &master_list);
return 0;
}
static int fini() {
if (ip_arr_size > 0 && ip_arr)
free(ip_arr);
static int init(void)
{
if (config_get_strings("hlswproxy", "scan", init_callback, NULL) <= 0)
return -1;
return 0;
}
struct hlswmaster_plugin plugin = {
@ -95,5 +107,4 @@ struct hlswmaster_plugin plugin = {
.scan = &scan,
.parse = &parse,
.init = &init,
.fini = &fini,
};

View File

@ -18,86 +18,89 @@
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <string.h>
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
static struct scan_ports port_arr[] = {
{ 27960, 27969, 6 }, /* q3(6), ef(7), et25), rtcw(8) */
{ 28070, 28070, 12 }, /* jk2(12) TODO: UNTESTED */
{ 28960, 28963, 31 }, /* cod(31), cod:uo(42) */
{ 29070, 29070, 27 }, /* jk3(27) TODO: UNTESTED */
{ 28070, 28070, 12 }, /* jk2(12) */
{ 28960, 28963, 31 }, /* cod(31), cod:uo(42), cod2(48) */
{ 29070, 29070, 27 }, /* jk3(27) */
{ 0,0,0 }
};
static char scanmsg[] = "\xff\xff\xff\xffgetStatus";
static char replymsg[] = "\xff\xff\xff\xffstatusResponse";
static char search_version[] = "\\version\\";
static char search_gamename[] = "\\gamename\\";
static char reply_q3[] = "Q3 ";
static char reply_ef[] = "ST:V HM ";
static char reply_rtcw[] = "Wolf ";
static char reply_et[] = "ET";
static char reply_jk2[] = "JK2MP";
static char reply_jk3[] = "JAmp";
static char reply_cod[] = "Call of Duty\\";
static char reply_coduo[] = "CoD:United Offensive\\";
static char reply_cod2[] = "Call of Duty 2\\";
static char q3_reply[] = "\\version\\Q3 ";
static char ef_reply[] = "\\version\\ST:V HM ";
static char rtcw_reply[] = "\\version\\Wolf ";
static char et_reply[] = "\\version\\ET ";
static char jk2_reply[] = "\\version\\JK2MP ";
static char jk3_reply[] = "\\version\\JAmp ";
static char cod_reply[] = "\\gamename\\Call of Duty\\";
static char coduo_reply[] = "\\gamename\\CoD:United Offensive\\";
static int scan(void) {
static int scan(void)
{
pkt_send_portarr(NULL, port_arr, scanmsg, strlen(scanmsg));
return 1;
}
static int parse(struct net_pkt *pkt) {
int gameid;
static int parse(struct net_pkt *pkt)
{
int gameid = 0, pos1, pos2;
if (!pkt_check_portarr(pkt, port_arr))
return PARSE_REJECT;
if (!(gameid = pkt_check_portarr(pkt, port_arr)))
return 0;
if (pkt_memcmp(pkt, 0, replymsg, strlen(replymsg)))
return 0;
return PARSE_REJECT;
switch (gameid) {
case 6: /* q3, ef, et, rtcw */
if (pkt_memmem(pkt, 0, q3_reply, strlen(q3_reply))) {
pos1 = pkt_memmem(pkt, 0, search_version, strlen(search_version));
pos2 = pkt_memmem(pkt, 0, search_gamename, strlen(search_gamename));
if (pos1 != -1) {
pos1 += strlen(search_version);
if (!pkt_memcmp(pkt, pos1, reply_q3, strlen(reply_q3)))
gameid = 6;
} else if (pkt_memmem(pkt, 0, ef_reply, strlen(ef_reply))) {
else if (!pkt_memcmp(pkt, pos1, reply_ef, strlen(reply_ef)))
gameid = 7;
} else if (pkt_memmem(pkt, 0, rtcw_reply, strlen(rtcw_reply))) {
else if (!pkt_memcmp(pkt, pos1, reply_rtcw, strlen(reply_rtcw)))
gameid = 8;
} else if (pkt_memmem(pkt, 0, et_reply, strlen(et_reply))) {
else if (!pkt_memcmp(pkt, pos1, reply_et, strlen(reply_et)))
gameid = 25;
} else {
return 0;
}
break;
case 12: /* jedi knight 2 */
if (!pkt_memmem(pkt, 0, jk2_reply, strlen(jk2_reply)))
return 0;
break;
case 27: /* jedi knight 3 */
if (!pkt_memmem(pkt, 0, jk3_reply, strlen(jk3_reply)))
return 0;
break;
case 31: /* cod, cod:uo */
if (pkt_memmem(pkt, 0, cod_reply, strlen(cod_reply))) {
gameid = 31;
else if (!pkt_memcmp(pkt, pos1, reply_jk2, strlen(reply_jk2)))
gameid = 12;
} else if (pkt_memmem(pkt, 0, coduo_reply, strlen(coduo_reply))) {
gameid = 42;
} else {
return 0;
}
break;
else if (!pkt_memcmp(pkt, pos1, reply_jk3, strlen(reply_jk3)))
gameid = 27;
}
if (gameid == 0 && pos2 != -1) {
pos2 += strlen(search_gamename);
if (!pkt_memcmp(pkt, pos2, reply_cod, strlen(reply_cod)))
gameid = 31;
else if (!pkt_memcmp(pkt, pos2, reply_coduo, strlen(reply_coduo)))
gameid = 42;
else if (!pkt_memcmp(pkt, pos2, reply_cod2, strlen(reply_cod2)))
gameid = 48;
}
if (gameid == 0)
return PARSE_REJECT;
server_add_pkt(gameid, pkt);
return 1;
return PARSE_ACCEPT;
}
struct hlswmaster_plugin plugin = {

View File

@ -18,24 +18,30 @@
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <string.h>
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
#include "scanner.h"
static char scanmsg[] = "\xff\xff\xff\xffinfo 34";
static char scanmsg[] = "\xff\xff\xff\xffinfo 34"; /* q2(3) */
static char replymsg[] = "\xff\xff\xff\xffinfo";
static int scan(void) {
static int scan(void)
{
pkt_send(NULL, 27910, scanmsg, strlen(scanmsg));
return 1;
}
static int parse(struct net_pkt *pkt) {
static int parse(struct net_pkt *pkt)
{
if (pkt_getport(pkt) != 27910)
return 0;
if (pkt_memcmp(pkt, 0, scanmsg, strlen(scanmsg)))
return 0;
return PARSE_REJECT;
if (pkt_memcmp(pkt, 0, replymsg, strlen(replymsg)))
return PARSE_REJECT;
server_add_pkt(3, pkt);
return 1;
return PARSE_ACCEPT;
}
struct hlswmaster_plugin plugin = {

View File

@ -1,159 +0,0 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <string.h>
#include "plugin_helper.h"
/**
* scan()
* wird periodisch aufgerufen um server querys loszuschicken.
*
* @return int false bei fehler
*/
static int scan(void) {
char myscan[] = "hallo"
/* sendet an 255.255.255.255:8888 'hallo' */
pkt_send(NULL, 8888, myscan, strlen(myscan));
/* sendet an 255.255.255.255:8888 'hallo\x00' */
pkt_send(NULL, 8888, myscan, sizeof(myscan));
/* sendet an 192.168.1.100:8888 'hallo' */
struct in_addr tmp;
inet_aton("192.168.1.100", &tmp)
pkt_send(&tmp, 8888, myscan, strlen(myscan));
/* an portrange(s) senden */
struct scan_ports port_arr[] = {
{ 27960, 27963, 0 }, /* von 27960-27963 scannen */
{ 28960, 28963, 0 }, /* und von 28960-28963 */
{ 0,0,0 }
};
pkt_send_portarr(NULL, &port_arr, myscan, strlen(myscan));
return 1;
}
/**
* parse()
* wird beim Empfang von Paketen aufgerufen um die Antworten zu parsen.
* Wenn das Paket fuer diesen Plugin einen Sinn ergibt,
* wird true zurueckgegeben.
*
* @param struct net_pkt *pkt - Pointer auf das empfangene Paket
* @return int true wenn das Plugin das Paket parsen konnte
*/
static int parse(struct net_pkt *pkt) {
/* checken ob das paket vom richtigen port kommt: */
if (pkt_getport(pkt) != 27910)
return 0;
/* bei einem port_arr checken ob es von einem der angefragten ports kommt */
int gameid;
if (!(gameid = pkt_check_portarr(pkt, port_arr)))
return 0;
/* gameid enthaelt nun den dritten wert einer passenden port_arr zeile */
/* paketinhalt checken (packet = "good morning dave\x00") */
char mycmp1[] = "good";
if (pkt_memcmp(pkt, 0, mycmp1, strlen(mycmp1)))
return 0;
/* paketinhalt mit offset */
char mycmp2[] = "morning";
if (pkt_memcmp(pkt, 5, mycmp2, strlen(mycmp2)))
return 0;
/* suchen ob paketinhalt vorhanden ist (packet = "blablablablabla\hostport\7777\blablabla") */
char mymem[] = "\\hostport\\";
void *p
p = pkt_memmem(pkt, 0, mymem, strlen(mymem));
if (!p)
return 0;
/* ints aus paket parsen: */
p += strlen(mymem);
port2 = pkt_atoi(pkt, p);
/* src ip des pakets */
printf("server found: %s\n", pkt_ntoa(pkt));
/* server zu interner liste hinzufuegen: (port1 = port, port2 = 0)*/
server_add_pkt(gameid, pkt);
/* server mit zwei ports zur liste hinzufuegen: */
server_add(gameid, pkt->addr.sin_addr.s_addr, port1, port2);
}
/**
* init()
* wird direkt nach dem Ladem des Plugins aufgerufen um evtl.
* Speicher, Files/Sockets zu initialisieren
* Als Parameter wird der Pointer auf eine Liste von Optionen
* im Configfile uebergeben, die in der Configsection des Plugins
* stehen ([Section] == Pluginname)
*
* @param struct conf_section *section
* @return false bei fehler
*/
static int init(struct conf_section *section) {
/* config optionen holen (myfile in section [myplugin] */
char *myfile = config_get_parameter(section, "myfile");
mybigmem = malloc(1024 * 1024);
}
/**
* init()
* wird direkt vor dem Entfernen des Plugins aufgerufen um
* Speicher, Files/Sockets zu schliessen
*
* @return false bei fehler
*/
static int fini() {
free(mybigmem);
}
/**
* gc()
* wird periodisch aufgerufen um Plugin interne Daten aufzufrischen
* als Parameter wird der plugin_timeout Wert uebergeben
*
* @param int timeout
* @return false bei fehler
*/
static int gc(int timeout) {
}
/**
* plugin
* Struktur mit Pointern auf die Funktionen.
* MUSS "plugin" heissen, damit es von dlsym() gefunden wird!
* der .name sollte dem Dateinamen entsprechen um Verwechslungen zu vermeiden
*/
struct hlswmaster_plugin plugin = {
.name = "myplugin",
.init = &init,
.fini = &fini,
.scan = &scan,
.parse = &parse,
.gc = &gc,
};

53
plugins/ut2k4.c Normal file
View File

@ -0,0 +1,53 @@
/***************************************************************************
* Copyright (C) 09/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <string.h>
#include "netpkt.h"
#include "scanner.h"
#include "plugin.h"
#include "plugin_helper.h"
static char scanmsg1[] = "\x80\x00\x00\x00\x00";
static int scan(void)
{
pkt_send(NULL, 10777, scanmsg1, 5);
return 1;
}
static int parse(struct net_pkt *pkt)
{
unsigned short *port;
if (pkt_memcmp(pkt, 0, scanmsg1, 5))
return PARSE_REJECT;
if (pkt->size < 12)
return PARSE_REJECT;
port = (unsigned short *)&(pkt->buf[10]);
server_add(33, pkt->addr.sin_addr.s_addr, *port, ntohs(pkt->addr.sin_port));
return PARSE_ACCEPT;
}
struct hlswmaster_plugin plugin = {
.name = "ut2k4",
.scan = &scan,
.parse = &parse,
};

177
scanner.c Normal file
View File

@ -0,0 +1,177 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include <sys/ioctl.h>
#include "event.h"
#include "netpkt.h"
#include "configfile.h"
#include "plugin.h"
#include "scanner.h"
#include "logging.h"
#include "gamelist.h"
static LIST_HEAD(tx_queue);
static int scan_sock;
int pkt_send(struct in_addr *dstip, unsigned int dstport, char *buf, unsigned int size)
{
struct net_pkt *pkt = malloc(sizeof(struct net_pkt) + size);
if (pkt == NULL) {
log_print(LOG_WARN, "pkt_send(): out of memory");
return -1;
}
pkt->addr.sin_family = AF_INET;
pkt->addr.sin_port = htons(dstport);
pkt->addr.sin_addr.s_addr = (dstip ? dstip->s_addr : 0xFFFFFFFF);
memcpy(pkt->buf, buf, size);
pkt->size = size;
list_add_tail(&pkt->list, &tx_queue);
return 0;
}
static int scanner_transmit(void *privdata)
{
if (list_empty(&tx_queue))
return -1;
struct net_pkt *pkt;
pkt = list_entry(tx_queue.next, struct net_pkt, list);
list_del(&pkt->list);
int ret = sendto(scan_sock, pkt->buf, pkt->size, 0, (struct sockaddr *)&pkt->addr, sizeof(pkt->addr));
if (ret <= 0)
log_print(LOG_WARN, "scanner_transmit(): sendto()");
return 0;
}
static int scanner_scan(void *privdata)
{
plugins_scan();
struct timeval tv;
tv.tv_sec = 0;
tv.tv_usec = 10000;
event_add_timeout(&tv, scanner_transmit, NULL);
return 0;
}
static int scanner_receive(int fd, void *privdata)
{
int recvsize;
if (ioctl(fd, FIONREAD, &recvsize) == -1) {
log_print(LOG_WARN, "scanner_receive(): ioctl(FIONREAD)");
return 0;
}
struct net_pkt *pkt = malloc(sizeof(struct net_pkt) + recvsize);
if (pkt == NULL) {
log_print(LOG_WARN, "scanner_receive(): out of memory");
return 0;
}
unsigned int i = sizeof(struct sockaddr_in);
pkt->size = recvfrom(fd, pkt->buf, recvsize, 0, (struct sockaddr *)&pkt->addr, &i);
if (pkt->size < 0) {
log_print(LOG_WARN, "scanner_receive(): recvfrom()");
free(pkt);
return 0;
}
switch (plugins_parse(pkt)) {
case PARSE_REJECT: {
char *pkt_str = pkt_print(pkt);
log_print(LOG_INFO, "scanner_receive(): unknown packet: %s:%d size:%d\n%s",
inet_ntoa(pkt->addr.sin_addr),
ntohs(pkt->addr.sin_port),
pkt->size, pkt_str);
free(pkt_str);
}
case PARSE_ACCEPT:
free(pkt);
case PARSE_ACCEPT_FREED:
break;
}
return 0;
}
int scanner_init()
{
scan_sock = socket(PF_INET, SOCK_DGRAM, 0);
if (scan_sock < 0) {
log_print(LOG_ERROR, "scan_init(): socket()");
return -1;
}
struct sockaddr_in src;
char *addr = config_get_string("global", "scanner_src", "0.0.0.0:7130");
if (parse_saddr(addr, &src) != 0) {
log_print(LOG_ERROR, "server_init(): invalid scanner_src '%s'", addr);
return -1;
}
if (bind(scan_sock, (struct sockaddr *)&src, sizeof(src)) < 0) {
log_print(LOG_ERROR, "scan_init(): bind()");
return -1;
}
int j = 1;
if (setsockopt(scan_sock, SOL_SOCKET, SO_BROADCAST, &j, sizeof(j))) {
log_print(LOG_ERROR, "scan_init(): setsockopt(SO_BROADCAST)");
return -1;
}
int rxsize = 1<<20;
if (setsockopt(scan_sock, SOL_SOCKET, SO_RCVBUF, &rxsize, sizeof(rxsize))) {
log_print(LOG_ERROR, "scan_init(): setsockopt(SO_RCVBUF)");
return -1;
}
event_add_readfd(scan_sock, scanner_receive, NULL);
log_print(LOG_INFO, "scan socket initialized (%s:%d)", inet_ntoa(src.sin_addr), ntohs(src.sin_port));
struct timeval tv;
tv.tv_sec = config_get_int("global", "scan_interval", 60);
tv.tv_usec = 0;
event_add_timeout(&tv, scanner_scan, NULL);
scanner_scan(NULL);
return 0;
}

138
server.c Normal file
View File

@ -0,0 +1,138 @@
/***************************************************************************
* Copyright (C) 11/2006 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include "configfile.h"
#include "list.h"
#include "event.h"
#include "scanner.h"
#include "logging.h"
#include "netpkt.h"
#include "gamelist.h"
#define HLSW_HEADER "\xFF\xFF\xFF\xFFHLSWLANSEARCH"
#define HLSW_HEADER_LEN 0x11
#define HLSW_ENTRY_LEN 10
#define MAX_PKT_LEN (HLSW_HEADER_LEN + HLSW_ENTRY_LEN * 140)
static LIST_HEAD(master_pkt_list);
static int serverlist_add_game(struct game_entry *entry)
{
int found = 0;
struct net_pkt *pkt;
list_for_each_entry(pkt, &master_pkt_list, list) {
if (pkt->size <= (MAX_PKT_LEN - HLSW_ENTRY_LEN)) {
found = 1;
break;
}
}
if (!found) {
pkt = malloc(sizeof(struct net_pkt) + MAX_PKT_LEN);
if (pkt == NULL) {
log_print(LOG_WARN, "serverlist_add_game(): out of memory");
return -1;
}
memcpy(pkt->buf, HLSW_HEADER, HLSW_HEADER_LEN);
pkt->size = HLSW_HEADER_LEN;
list_add(&pkt->list, &master_pkt_list);
}
memcpy((void *)&pkt->buf + pkt->size, &entry->gameid, HLSW_ENTRY_LEN);
pkt->size += HLSW_ENTRY_LEN;
return 0;
}
static int serverlist_refresh(void *privdata)
{
int timeout = (int)privdata;
struct net_pkt *pkt, *tmp;
list_for_each_entry_safe(pkt, tmp, &master_pkt_list, list) {
list_del(&pkt->list);
free(pkt);
}
gamelist_gc_and_dump(serverlist_add_game, timeout);
return 0;
}
static int server_handler(int fd, void *privdata)
{
struct sockaddr_in client;
unsigned char buf[32];
unsigned int i = sizeof(client);
int ret = recvfrom(fd, buf, sizeof(buf), 0, (struct sockaddr *)&client, &i);
if (ret <= 0) {
log_print(LOG_WARN, "server_handler(): recvfrom()");
return 0;
}
if (memcmp(buf, HLSW_HEADER, HLSW_HEADER_LEN))
return 0;
struct net_pkt *pkt;
list_for_each_entry(pkt, &master_pkt_list, list)
sendto(fd, pkt->buf, pkt->size, 0, (struct sockaddr *)&client, sizeof(client));
return 0;
}
int server_init()
{
int sock = socket(PF_INET, SOCK_DGRAM, 0);
if (sock < 0) {
log_print(LOG_ERROR, "server_init(): socket()");
return -1;
}
struct sockaddr_in src;
char *addr = config_get_string("global", "master_src", "0.0.0.0:7140");
if (parse_saddr(addr, &src) != 0) {
log_print(LOG_ERROR, "server_init(): invalid master_src '%s'", addr);
return -1;
}
if (bind(sock, (struct sockaddr *)&src, sizeof(src)) < 0) {
log_print(LOG_ERROR, "server_init(): bind()");
return -1;
}
event_add_readfd(sock, server_handler, NULL);
struct timeval tv;
tv.tv_sec = config_get_int("global", "serverlist_refresh", 5);
tv.tv_usec = 0;
int timeout = config_get_int("global", "serverlist_timeout", 180);
event_add_timeout(&tv, serverlist_refresh, (void *)timeout);
return 0;
}

View File

@ -1,10 +0,0 @@
AUTOMAKE_OPTIONS = foreign no-dependencies
INCLUDES = -I../include
bin_PROGRAMS = hlswmaster
hlswmaster_SOURCES = client.c config.c logging.c main.c plugin.c plugin_helper.c scanner.c \
../include/configfile.h ../include/hlswmaster.h ../include/list.h \
../include/netpkt.h ../include/plugin.h ../include/plugin_helper.h
hlswmaster_LDADD = -ldl -lpthread
hlswmaster_LDFLAGS = -rdynamic

View File

@ -1,440 +0,0 @@
# Makefile.in generated by automake 1.9.4 from Makefile.am.
# @configure_input@
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
# 2003, 2004 Free Software Foundation, Inc.
# This Makefile.in is free software; the Free Software Foundation
# gives unlimited permission to copy and/or distribute it,
# with or without modifications, as long as this notice is preserved.
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
# PARTICULAR PURPOSE.
@SET_MAKE@
SOURCES = $(hlswmaster_SOURCES)
srcdir = @srcdir@
top_srcdir = @top_srcdir@
VPATH = @srcdir@
pkgdatadir = $(datadir)/@PACKAGE@
pkglibdir = $(libdir)/@PACKAGE@
pkgincludedir = $(includedir)/@PACKAGE@
top_builddir = ..
am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
INSTALL = @INSTALL@
install_sh_DATA = $(install_sh) -c -m 644
install_sh_PROGRAM = $(install_sh) -c
install_sh_SCRIPT = $(install_sh) -c
INSTALL_HEADER = $(INSTALL_DATA)
transform = $(program_transform_name)
NORMAL_INSTALL = :
PRE_INSTALL = :
POST_INSTALL = :
NORMAL_UNINSTALL = :
PRE_UNINSTALL = :
POST_UNINSTALL = :
build_triplet = @build@
host_triplet = @host@
bin_PROGRAMS = hlswmaster$(EXEEXT)
subdir = src
DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
am__aclocal_m4_deps = $(top_srcdir)/configure.in
am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
$(ACLOCAL_M4)
mkinstalldirs = $(install_sh) -d
CONFIG_HEADER = $(top_builddir)/config.h
CONFIG_CLEAN_FILES =
am__installdirs = "$(DESTDIR)$(bindir)"
binPROGRAMS_INSTALL = $(INSTALL_PROGRAM)
PROGRAMS = $(bin_PROGRAMS)
am_hlswmaster_OBJECTS = client.$(OBJEXT) config.$(OBJEXT) \
logging.$(OBJEXT) main.$(OBJEXT) plugin.$(OBJEXT) \
plugin_helper.$(OBJEXT) scanner.$(OBJEXT)
hlswmaster_OBJECTS = $(am_hlswmaster_OBJECTS)
hlswmaster_DEPENDENCIES =
DEFAULT_INCLUDES = -I. -I$(srcdir) -I$(top_builddir)
depcomp =
am__depfiles_maybe =
COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
$(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
LTCOMPILE = $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) \
$(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \
$(AM_CFLAGS) $(CFLAGS)
CCLD = $(CC)
LINK = $(LIBTOOL) --tag=CC --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \
$(AM_LDFLAGS) $(LDFLAGS) -o $@
SOURCES = $(hlswmaster_SOURCES)
DIST_SOURCES = $(hlswmaster_SOURCES)
ETAGS = etags
CTAGS = ctags
DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
ACLOCAL = @ACLOCAL@
AMDEP_FALSE = @AMDEP_FALSE@
AMDEP_TRUE = @AMDEP_TRUE@
AMTAR = @AMTAR@
AR = @AR@
AUTOCONF = @AUTOCONF@
AUTOHEADER = @AUTOHEADER@
AUTOMAKE = @AUTOMAKE@
AWK = @AWK@
CC = @CC@
CCDEPMODE = @CCDEPMODE@
CFLAGS = @CFLAGS@
CPP = @CPP@
CPPFLAGS = @CPPFLAGS@
CXX = @CXX@
CXXCPP = @CXXCPP@
CXXDEPMODE = @CXXDEPMODE@
CXXFLAGS = @CXXFLAGS@
CYGPATH_W = @CYGPATH_W@
DEFS = @DEFS@
DEPDIR = @DEPDIR@
ECHO = @ECHO@
ECHO_C = @ECHO_C@
ECHO_N = @ECHO_N@
ECHO_T = @ECHO_T@
EGREP = @EGREP@
EXEEXT = @EXEEXT@
F77 = @F77@
FFLAGS = @FFLAGS@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_SCRIPT = @INSTALL_SCRIPT@
INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
LDFLAGS = @LDFLAGS@
LIBOBJS = @LIBOBJS@
LIBS = @LIBS@
LIBTOOL = @LIBTOOL@
LN_S = @LN_S@
LTLIBOBJS = @LTLIBOBJS@
MAINT = @MAINT@
MAINTAINER_MODE_FALSE = @MAINTAINER_MODE_FALSE@
MAINTAINER_MODE_TRUE = @MAINTAINER_MODE_TRUE@
MAKEINFO = @MAKEINFO@
OBJEXT = @OBJEXT@
PACKAGE = @PACKAGE@
PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
PACKAGE_NAME = @PACKAGE_NAME@
PACKAGE_STRING = @PACKAGE_STRING@
PACKAGE_TARNAME = @PACKAGE_TARNAME@
PACKAGE_VERSION = @PACKAGE_VERSION@
PATH_SEPARATOR = @PATH_SEPARATOR@
RANLIB = @RANLIB@
SET_MAKE = @SET_MAKE@
SHELL = @SHELL@
STRIP = @STRIP@
VERSION = @VERSION@
ac_ct_AR = @ac_ct_AR@
ac_ct_CC = @ac_ct_CC@
ac_ct_CXX = @ac_ct_CXX@
ac_ct_F77 = @ac_ct_F77@
ac_ct_RANLIB = @ac_ct_RANLIB@
ac_ct_STRIP = @ac_ct_STRIP@
am__fastdepCC_FALSE = @am__fastdepCC_FALSE@
am__fastdepCC_TRUE = @am__fastdepCC_TRUE@
am__fastdepCXX_FALSE = @am__fastdepCXX_FALSE@
am__fastdepCXX_TRUE = @am__fastdepCXX_TRUE@
am__include = @am__include@
am__leading_dot = @am__leading_dot@
am__quote = @am__quote@
am__tar = @am__tar@
am__untar = @am__untar@
bindir = @bindir@
build = @build@
build_alias = @build_alias@
build_cpu = @build_cpu@
build_os = @build_os@
build_vendor = @build_vendor@
datadir = @datadir@
exec_prefix = @exec_prefix@
host = @host@
host_alias = @host_alias@
host_cpu = @host_cpu@
host_os = @host_os@
host_vendor = @host_vendor@
includedir = @includedir@
infodir = @infodir@
install_sh = @install_sh@
libdir = @libdir@
libexecdir = @libexecdir@
localstatedir = @localstatedir@
mandir = @mandir@
mkdir_p = @mkdir_p@
oldincludedir = @oldincludedir@
prefix = @prefix@
program_transform_name = @program_transform_name@
sbindir = @sbindir@
sharedstatedir = @sharedstatedir@
sysconfdir = @sysconfdir@
target_alias = @target_alias@
AUTOMAKE_OPTIONS = foreign no-dependencies
INCLUDES = -I../include
hlswmaster_SOURCES = client.c config.c logging.c main.c plugin.c plugin_helper.c scanner.c \
../include/configfile.h ../include/hlswmaster.h ../include/list.h \
../include/netpkt.h ../include/plugin.h ../include/plugin_helper.h
hlswmaster_LDADD = -ldl -lpthread
hlswmaster_LDFLAGS = -rdynamic
all: all-am
.SUFFIXES:
.SUFFIXES: .c .lo .o .obj
$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps)
@for dep in $?; do \
case '$(am__configure_deps)' in \
*$$dep*) \
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
&& exit 0; \
exit 1;; \
esac; \
done; \
echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign src/Makefile'; \
cd $(top_srcdir) && \
$(AUTOMAKE) --foreign src/Makefile
.PRECIOUS: Makefile
Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
@case '$?' in \
*config.status*) \
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
*) \
echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
esac;
$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
install-binPROGRAMS: $(bin_PROGRAMS)
@$(NORMAL_INSTALL)
test -z "$(bindir)" || $(mkdir_p) "$(DESTDIR)$(bindir)"
@list='$(bin_PROGRAMS)'; for p in $$list; do \
p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \
if test -f $$p \
|| test -f $$p1 \
; then \
f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \
echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) --mode=install $(binPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(bindir)/$$f'"; \
$(INSTALL_PROGRAM_ENV) $(LIBTOOL) --mode=install $(binPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(bindir)/$$f" || exit 1; \
else :; fi; \
done
uninstall-binPROGRAMS:
@$(NORMAL_UNINSTALL)
@list='$(bin_PROGRAMS)'; for p in $$list; do \
f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \
echo " rm -f '$(DESTDIR)$(bindir)/$$f'"; \
rm -f "$(DESTDIR)$(bindir)/$$f"; \
done
clean-binPROGRAMS:
@list='$(bin_PROGRAMS)'; for p in $$list; do \
f=`echo $$p|sed 's/$(EXEEXT)$$//'`; \
echo " rm -f $$p $$f"; \
rm -f $$p $$f ; \
done
hlswmaster$(EXEEXT): $(hlswmaster_OBJECTS) $(hlswmaster_DEPENDENCIES)
@rm -f hlswmaster$(EXEEXT)
$(LINK) $(hlswmaster_LDFLAGS) $(hlswmaster_OBJECTS) $(hlswmaster_LDADD) $(LIBS)
mostlyclean-compile:
-rm -f *.$(OBJEXT)
distclean-compile:
-rm -f *.tab.c
.c.o:
$(COMPILE) -c $<
.c.obj:
$(COMPILE) -c `$(CYGPATH_W) '$<'`
.c.lo:
$(LTCOMPILE) -c -o $@ $<
mostlyclean-libtool:
-rm -f *.lo
clean-libtool:
-rm -rf .libs _libs
distclean-libtool:
-rm -f libtool
uninstall-info-am:
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
mkid -fID $$unique
tags: TAGS
TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
test -n "$$unique" || unique=$$empty_fix; \
$(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
$$tags $$unique; \
fi
ctags: CTAGS
CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
test -z "$(CTAGS_ARGS)$$tags$$unique" \
|| $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
$$tags $$unique
GTAGS:
here=`$(am__cd) $(top_builddir) && pwd` \
&& cd $(top_srcdir) \
&& gtags -i $(GTAGS_ARGS) $$here
distclean-tags:
-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
distdir: $(DISTFILES)
@srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; \
topsrcdirstrip=`echo "$(top_srcdir)" | sed 's|.|.|g'`; \
list='$(DISTFILES)'; for file in $$list; do \
case $$file in \
$(srcdir)/*) file=`echo "$$file" | sed "s|^$$srcdirstrip/||"`;; \
$(top_srcdir)/*) file=`echo "$$file" | sed "s|^$$topsrcdirstrip/|$(top_builddir)/|"`;; \
esac; \
if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
dir=`echo "$$file" | sed -e 's,/[^/]*$$,,'`; \
if test "$$dir" != "$$file" && test "$$dir" != "."; then \
dir="/$$dir"; \
$(mkdir_p) "$(distdir)$$dir"; \
else \
dir=''; \
fi; \
if test -d $$d/$$file; then \
if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
fi; \
cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
else \
test -f $(distdir)/$$file \
|| cp -p $$d/$$file $(distdir)/$$file \
|| exit 1; \
fi; \
done
check-am: all-am
check: check-am
all-am: Makefile $(PROGRAMS)
installdirs:
for dir in "$(DESTDIR)$(bindir)"; do \
test -z "$$dir" || $(mkdir_p) "$$dir"; \
done
install: install-am
install-exec: install-exec-am
install-data: install-data-am
uninstall: uninstall-am
install-am: all-am
@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
installcheck: installcheck-am
install-strip:
$(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
`test -z '$(STRIP)' || \
echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
mostlyclean-generic:
clean-generic:
distclean-generic:
-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
maintainer-clean-generic:
@echo "This command is intended for maintainers to use"
@echo "it deletes files that may require special tools to rebuild."
clean: clean-am
clean-am: clean-binPROGRAMS clean-generic clean-libtool mostlyclean-am
distclean: distclean-am
-rm -f Makefile
distclean-am: clean-am distclean-compile distclean-generic \
distclean-libtool distclean-tags
dvi: dvi-am
dvi-am:
html: html-am
info: info-am
info-am:
install-data-am:
install-exec-am: install-binPROGRAMS
install-info: install-info-am
install-man:
installcheck-am:
maintainer-clean: maintainer-clean-am
-rm -f Makefile
maintainer-clean-am: distclean-am maintainer-clean-generic
mostlyclean: mostlyclean-am
mostlyclean-am: mostlyclean-compile mostlyclean-generic \
mostlyclean-libtool
pdf: pdf-am
pdf-am:
ps: ps-am
ps-am:
uninstall-am: uninstall-binPROGRAMS uninstall-info-am
.PHONY: CTAGS GTAGS all all-am check check-am clean clean-binPROGRAMS \
clean-generic clean-libtool ctags distclean distclean-compile \
distclean-generic distclean-libtool distclean-tags distdir dvi \
dvi-am html html-am info info-am install install-am \
install-binPROGRAMS install-data install-data-am install-exec \
install-exec-am install-info install-info-am install-man \
install-strip installcheck installcheck-am installdirs \
maintainer-clean maintainer-clean-generic mostlyclean \
mostlyclean-compile mostlyclean-generic mostlyclean-libtool \
pdf pdf-am ps ps-am tags uninstall uninstall-am \
uninstall-binPROGRAMS uninstall-info-am
# Tell versions [3.59,3.63) of GNU make to not export all variables.
# Otherwise a system limit (for SysV at least) may be exceeded.
.NOEXPORT:

View File

@ -1,188 +0,0 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include <pthread.h>
#include "hlswmaster.h"
#include "configfile.h"
#include "list.h"
#define HLSW_HEADER "\xFF\xFF\xFF\xFFHLSWLANSEARCH\x00"
#define HLSW_HEADER_LEN 0x12
#define HLSW_ENTRY_LEN 10
#define MAX_PKT_LEN (HLSW_HEADER_LEN + HLSW_ENTRY_LEN * 140)
struct client_pkt {
struct list_head list;
unsigned int size;
unsigned char buf[0];
};
/* real und prepare list. enthalten die client-antworten */
static LIST_HEAD(client_pkt_list);
static LIST_HEAD(client_pkt_prepare);
/* sichert die real list ab */
static pthread_mutex_t pkt_list_lock = PTHREAD_MUTEX_INITIALIZER;
/**
* pkt_not_full()
* LIST_FIND helper
*
* @param struct client_pkt *a
* @param void *b
* @return true wenn das paket noch nicht voll ist
*/
static inline int cpkt_not_full(const struct client_pkt *a, void *b) {
return (a->size <= (MAX_PKT_LEN - HLSW_ENTRY_LEN));
}
/**
* client_pkt_add_real()
* erzeugt eine neues client_pkt und fuegt es einer liste hinzu
* gibt einen pointer auf das neue client_pkt zurueck
*
* @param struct list_head *list
* @return struct client_pkt * or NULL on error
*/
static struct client_pkt * client_pkt_add_real(struct list_head *list) {
struct client_pkt *pkt;
pkt = malloc(sizeof(struct client_pkt) + MAX_PKT_LEN);
if (pkt) {
INIT_LIST_HEAD(&pkt->list);
/* kopier den hlsw header in das client paket */
memcpy(pkt->buf, HLSW_HEADER, HLSW_HEADER_LEN);
pkt->size = HLSW_HEADER_LEN;
list_add_tail(&pkt->list, list);
}
return pkt;
}
/**
* client_pkt_add()
* fuegt dem freien client_pkt der prepare-liste ein Spiel hinzu
* wenn kein platz vorhanden ist, wird ein neues paket erzeugt
*
* @param struct game_server *server
* @return false bei fehler (malloc)
*/
int client_pkt_add(struct game_server *server) {
struct client_pkt *cpkt;
cpkt = LIST_FIND(&client_pkt_prepare, cpkt_not_full, struct client_pkt *, NULL);
if (!cpkt && !(cpkt = client_pkt_add_real(&client_pkt_prepare)))
return 0;
/* kopiert den server eintrag in das client paket */
memcpy((void *)&cpkt->buf + cpkt->size, &server->gameid, HLSW_ENTRY_LEN);
cpkt->size += HLSW_ENTRY_LEN;
return 1;
}
/**
* client_pkt_commit()
* die prepare liste wird die echte liste und
* alle pakete der alten echten liste werden entfernt
*
* @return true
*/
int client_pkt_commit() {
struct list_head old_list, *pkt, *tmp;
/* wenn die liste leer ist, nur HLSW-header verschicken */
if (list_empty(&client_pkt_prepare))
client_pkt_add_real(&client_pkt_prepare);
pthread_mutex_lock(&pkt_list_lock);
/* old_list wird head der real list */
list_add(&old_list, &client_pkt_list);
list_del(&client_pkt_list);
/* client_pkt_list wird head der prepare list */
list_add(&client_pkt_list, &client_pkt_prepare);
list_del_init(&client_pkt_prepare);
pthread_mutex_unlock(&pkt_list_lock);
/* alle alten pakete entfernen */
list_for_each_safe(pkt, tmp, &old_list) {
list_del(pkt);
free(pkt);
}
return 1;
}
/**
* client_handler()
* empfaengt und beantwortet die HLSW Anfragen
*/
void client_handler(void) {
struct client_pkt *pkt;
struct sockaddr_in dst;
int sock, i;
unsigned char buf[32], *ip;
if ((sock = socket(PF_INET, SOCK_DGRAM, 0)) < 0) {
log_print("client_handler(): socket()");
return;
}
ip = config_get_string("global", "master_ip", "0.0.0.0");
log_print("thread_start: client_handler (%s:7140)", ip);
dst.sin_family = AF_INET;
dst.sin_port = htons(7140);
inet_aton(ip, &dst.sin_addr);
if (bind(sock, (struct sockaddr *)&dst, sizeof(dst)) < 0) {
log_print("client_handler(): bind()");
return;
}
while (1) {
/* auf clientanfrage warten */
i = sizeof(struct sockaddr_in);
recvfrom(sock, buf, sizeof(buf), 0, (struct sockaddr *)&dst, &i);
/* testen ob es sich um ein HLSW anforderung handelt */
if (memcmp(buf, HLSW_HEADER, HLSW_HEADER_LEN))
continue;
pthread_mutex_lock(&pkt_list_lock);
/* pakete aus der real list senden */
list_for_each_entry(pkt, &client_pkt_list, list)
sendto(sock, pkt->buf, pkt->size, 0, (struct sockaddr *)&dst, sizeof(dst));
pthread_mutex_unlock(&pkt_list_lock);
}
}

View File

@ -1,247 +0,0 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include "hlswmaster.h"
#include "configfile.h"
#include "list.h"
//#define DEBUG 1
/* liste config optionen */
static LIST_HEAD(config_list);
/**
* config_add_section()
* fuegt der config liste ein section hinzu
* @param char *name
* @return struct conf_section *
*/
static struct conf_section * config_add_section(char *name) {
struct conf_section *section;
if (!name)
return NULL;
section = malloc(sizeof(struct conf_section));
if (section) {
INIT_LIST_HEAD(&section->list);
INIT_LIST_HEAD(&section->tupel);
strncpy(section->name, name, sizeof(section->name));
list_add_tail(&section->list, &config_list);
}
return section;
}
/**
* config_add_tupel()
* fuegt einer config section ein werte tupel hinzu
* @param struct conf_section *
* @param char *option
* @param char *parameter
* @return false bei fehler
*/
static int config_add_tupel(struct conf_section *section, char *option, char *parameter) {
struct conf_tupel *tupel;
if (!section || !option || !parameter)
return 0;
if (!(tupel = malloc(sizeof(struct conf_tupel))))
return 0;
INIT_LIST_HEAD(&tupel->list);
tupel->option = strdup(option);
tupel->parameter = strdup(parameter);
list_add_tail(&tupel->list, &section->tupel);
return 1;
}
/**
* config_free()
* entfernt die config_liste aus dem Speicher
*/
static void config_free() {
struct conf_section *section, *section_tmp;
struct conf_tupel *tupel, *tupel_tmp;
list_for_each_entry_safe(section, section_tmp, &config_list, list) {
list_for_each_entry_safe(tupel, tupel_tmp, &section->tupel, list) {
list_del(&tupel->list);
free(tupel->option);
free(tupel->parameter);
free(tupel);
}
list_del(&section->list);
free(section);
}
}
/**
* config_parse()
* parsed die configfile
*
* @param char *config
* @return false bei fehler
*/
int config_parse(char *config) {
struct conf_section *section = NULL;
FILE *fz;
int i = 0, ret = 1;
char *row, *tok, *tok2;
if (!config)
return 0;
if (!(row = malloc(1024)))
return 0;
if (!(fz = fopen(config, "r"))) {
log_print("config_parse(): %s", config);
return 0;
}
while (fgets(row, 1024, fz)) {
i++;
if (row[0] == '#' || row[0] <= ' ') {
continue;
} else if (row[0] == '[') {
tok = strtok(row +1, " ]\n");
section = config_add_section(tok);
if (!section) {
log_print("config_parse(): invalid section in row %d", i);
ret = 0;
break;
}
continue;
} else if (!section) {
log_print("config_parse(): missing section in row %d", i);
ret = 0;
break;
}
if ((tok = strtok(row, " \n")) && (tok2 = strtok(NULL, " \n")))
if (!config_add_tupel(section, tok, tok2))
log_print("config_parse(): invalid row %d", i);
}
fclose(fz);
free(row);
if (atexit(config_free) != 0) {
log_print("config_parse(): atexit()");
return 0;
}
#ifdef DEBUG
{
struct conf_section *section;
struct conf_tupel *tupel;
list_for_each_entry(section, &config_list, list)
list_for_each_entry(tupel, &section->tupel, list)
printf("%s: %s = %s\n", section->name, tupel->option, tupel->parameter);
}
#endif
return ret;
}
/**
* config_get_section()
* gibt einen pointer auf die erste section mit dem
* angegebenen namen zurueck
* wenn nicht vorhanden NULL
*
* @param char *name
* @return struct conf_section *
*/
struct conf_section * config_get_section(char *name) {
struct conf_section *section;
list_for_each_entry(section, &config_list, list) {
if (!strcmp(section->name, name))
return section;
}
return NULL;
}
/**
* config_get_parameter()
* gibt den parameter der ersten passenden option
* in einer section zurueck
*
* @param struct conf_section *section
* @param char *option
* @return char *
*/
char * config_get_parameter(struct conf_section *section, char *option) {
struct conf_tupel *tupel;
list_for_each_entry(tupel, &section->tupel, list) {
if (!strcmp(tupel->option, option))
return tupel->parameter;
}
return NULL;
}
/**
* config_get_string()
* gibt den parameter des section/option tupels zurueck
* wenn nicht vorhanden, wird def zurueckgegeben
* @param char *section
* @param chat *option
* @param char *def
* @return char *
*/
char * config_get_string(char *section, char *option, char *def) {
struct conf_section *tmp;
char *ret;
tmp = config_get_section(section);
if (tmp && (ret = config_get_parameter(tmp, option)))
return ret;
return def;
}
/**
* config_get_int()
* gibt den parameter des section/option tupels zurueck
* wenn nicht vorhanden, wird def zurueckgegeben
* @param char *section
* @param char *option
* @param int def
* @return int
*/
int config_get_int(char *section, char *option, int def) {
char *ret;
ret = config_get_string(section, option, NULL);
return ret ? atoi(ret) : def;
}

View File

@ -1,179 +0,0 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdlib.h>
#include <dlfcn.h>
#include <pthread.h>
#include "hlswmaster.h"
#include "plugin.h"
#include "configfile.h"
#include "netpkt.h"
#include "list.h"
/* liste der geladenen plugins */
static LIST_HEAD(plugin_list);
/* sichert die plugin list UND die plugins ab */
static pthread_mutex_t plugin_lock = PTHREAD_MUTEX_INITIALIZER;
/**
* plugin_load()
* laedt ein shared object,
* fuehrt wenn vorhanden init() aus
* und haengt den plugin an das ende der liste
*
* @param char *name
* @return false on error
*/
int plugin_load(char *name) {
struct hlswmaster_plugin *plugin;
void *tmp;
struct conf_section *section;
dlerror();
if ((tmp = dlopen(name, RTLD_NOW))) {
if ((plugin = dlsym(tmp, "plugin"))) {
plugin->dlref = tmp;
section = config_get_section(plugin->name);
log_print("loading plugin '%s'", plugin->name);
if (!plugin->init || (plugin->init(section))) {
pthread_mutex_lock(&plugin_lock);
list_add_tail(&plugin->list, &plugin_list);
pthread_mutex_unlock(&plugin_lock);
return 1;
}
log_print("failed to load '%s'", name);
dlclose(tmp);
return 0;
}
dlclose(tmp);
}
log_print("%s", dlerror());
return 0;
}
/**
* plugin_load_all()
* laedt alle in der config angegebenen plugins
*
* @return false on error
*/
int plugin_load_all() {
struct conf_section *section;
struct conf_tupel *tupel;
section = config_get_section("global");
if (section) {
list_for_each_entry(tupel, &section->tupel, list)
if (!strcmp(tupel->option, "plugin"))
plugin_load(tupel->parameter);
}
return 1;
}
/**
* plugin_unload_all()
* entfernt alle plugins aus der liste,
* ruft wenn vorhanden fini() auf
* und entlaed das shared object
*
* @return false on error
*/
int plugin_unload_all() {
struct hlswmaster_plugin *plugin, *tmp;
pthread_mutex_lock(&plugin_lock);
list_for_each_entry_safe(plugin, tmp, &plugin_list, list) {
list_del(&plugin->list);
if (plugin->fini)
plugin->fini();
log_print("plugin '%s' unloaded", plugin->name);
dlclose(plugin->dlref);
}
pthread_mutex_unlock(&plugin_lock);
return 1;
}
/**
* plugins_scan()
* ruft die scan() Funktionen der Plugins auf (wenn vorhanden)
*
* @return true
*/
int plugins_scan(void) {
struct hlswmaster_plugin *plugin;
pthread_mutex_lock(&plugin_lock);
list_for_each_entry(plugin, &plugin_list, list)
if (plugin->scan && !plugin->scan())
log_print("plugin %s: scan error", plugin->name);
pthread_mutex_unlock(&plugin_lock);
return 1;
}
/**
* plugins_parse()
* ruft die parse() Funktionen der Plugins auf (wenn vorhanden)
* bis ein Plugin das Paket annimmt
*
* @param struct net_pkt *pkt
* @return false wenn kein Plugin das Paket angenommen hat
*/
int plugins_parse(struct net_pkt *pkt) {
struct hlswmaster_plugin *plugin;
pthread_mutex_lock(&plugin_lock);
list_for_each_entry(plugin, &plugin_list, list) {
if (plugin->parse && plugin->parse(pkt)) {
pthread_mutex_unlock(&plugin_lock);
return 1;
}
}
pthread_mutex_unlock(&plugin_lock);
return 0;
}
/**
* plugins_gc()
* ruft die gc() Funktionen der Plugins auf (wenn vorhanden)
*
* @param unsigned long timeout
* @return true
*/
int plugins_gc(unsigned long timeout) {
struct hlswmaster_plugin *plugin;
pthread_mutex_lock(&plugin_lock);
list_for_each_entry(plugin, &plugin_list, list)
if (plugin->gc)
plugin->gc(timeout);
pthread_mutex_unlock(&plugin_lock);
return 1;
}

View File

@ -1,173 +0,0 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#define __USE_GNU
#include <string.h>
#include <ctype.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include "hlswmaster.h"
#include "netpkt.h"
#include "plugin.h"
#include "plugin_helper.h"
/**
* pkt_queue_portarr()
* erzeugt ein net_pkt aus den parametern und legt es in die send queue
*
* @param char *dstip - pointer auf eine IP, wenn NULL wird broadcast angenommen
* @param struct scan_ports *port_arr
* @param char *buf - pointer auf den zu sendenen speicherbereich
* @param unsigned int size - groesse des speicherbereichs
* @return false bei fehler
*/
int pkt_send_portarr(struct in_addr *dstip, struct scan_ports *portarr, char *buf, unsigned int size) {
unsigned short port;
while (portarr && portarr->portlo) {
for (port = portarr->portlo; port <= portarr->porthi; port++)
pkt_send(dstip, port, buf, size);
portarr++;
}
return 1;
}
/**
* pkt_check_portarr()
* prueft ob der src-port des pakets in der portliste vorhanden ist
*
* @param struct net_pkt *pkt
* @param struct scan_ports *port_arr
* @return die gameid der portrange oder 0 wenn nicht vorhanden
*/
int pkt_check_portarr(struct net_pkt *pkt, struct scan_ports *portarr) {
unsigned short port;
while (portarr && portarr->portlo) {
for (port = portarr->portlo; port <= portarr->porthi; port++)
if (port == ntohs(pkt->addr.sin_port))
return portarr->gameid;
portarr++;
}
return 0;
}
/**
* pkt_memcmp()
* vergleicht das Paket mit einem Speicherbereich
*
* @param struct net_pkt *pkt
* @param unsigned int offset
* @param char *search
* @param unsigned int size
* @return true wenn gleich
*/
int pkt_memcmp(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size) {
if (offset >= pkt->size)
return 1;
if (offset + size >= pkt->size)
size = pkt->size - offset;
return memcmp(pkt->buf + offset, search, size);
}
/**
* pkt_memmem()
* sucht einen Speicherbereich in dem Paket
*
* @param struct net_pkt *pkt
* @param unsigned int offset
* @param char *search
* @param unsigned int size
* @return pointer auf den string im Paket
*/
void * pkt_memmem(struct net_pkt *pkt, unsigned int offset, char *search, unsigned int size) {
if (offset >= pkt->size)
return NULL;
return memmem(pkt->buf + offset, pkt->size, search, size);
}
/**
* server_add_pkt()
* fuegt der serverliste einen server hinzu
*
* @param unsigned int gameid
* @param struct net_pkt *pkt
* @return false bei fehler
*/
int server_add_pkt(unsigned int gameid, struct net_pkt *pkt) {
return server_add(gameid, pkt->addr.sin_addr.s_addr, ntohs(pkt->addr.sin_port), 0);
}
/**
* pkt_ntoa()
* gibt die IP des Pakets als String zurueck
*
* @param struct net_pkt *pkt
* @return pointer auf String
*/
char * pkt_ntoa(struct net_pkt *pkt) {
return inet_ntoa(pkt->addr.sin_addr);
}
/**
* pkt_getport()
* gibt den Port des Pakets als short zurueck
*
* @param struct net_pkt *pkt
* @return portnr
*/
unsigned short pkt_getport(struct net_pkt *pkt) {
return ntohs(pkt->addr.sin_port);
}
/**
* pkt_atoi()
* gibt den integer in dem paket ab der position zurueck
*
* @param struct net_pkt *pkt
* @return int
*/
int pkt_atoi(struct net_pkt *pkt, void *p) {
int val = 0;
void *max = ((void *)pkt->buf + pkt->size);
char *c = p;
/* check lower bounds */
if ((void *)pkt->buf > p || p > max)
return 0;
while (isdigit(*c) && (void *)c < max)
val = (val * 10) + (*c++ - 0x30);
return val;
}

View File

@ -1,307 +0,0 @@
/***************************************************************************
* Copyright (C) 03/2005 by Olaf Rempel *
* razzor@kopf-tisch.de *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 2 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write to the *
* Free Software Foundation, Inc., *
* 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
***************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <arpa/inet.h>
#include <sys/ioctl.h>
#include <pthread.h>
#include <time.h>
#include "list.h"
#include "netpkt.h"
#include "configfile.h"
#include "hlswmaster.h"
#define DEBUG 1
/* die interne serverliste */
static LIST_HEAD(serverlist);
/* sichert die server liste */
static pthread_mutex_t serverlist_lock = PTHREAD_MUTEX_INITIALIZER;
/* scan socket */
static int scan_sock;
/**
* server_cmp()
* LIST_FIND helper
*
* @param struct game_server *a
* @param struct game_server *b
* @return true wenn es sich um den selben server handelt
*/
static inline int server_cmp(const struct game_server *a, struct game_server *b) {
return (a->gameid == b->gameid && a->ip == b->ip &&
a->port1 == b->port1 && a->port2 == b->port2);
}
/**
* server_add()
* fuegt der internen serverliste einen server hinzu
* wenn dieser server schon in der liste vorhanden ist, wird nur
* die modtime angepasst
*
* @param unsigned int gameid
* @param struct in_addr ip
* @param u_int16_t port1
* @param u_int16_t port2
* @return false bei fehler
*/
int server_add(u_int16_t gameid, u_int32_t ip, u_int16_t port1, u_int16_t port2) {
struct game_server server, *nserver;
server.gameid = gameid;
server.ip = ip;
server.port1 = port1;
server.port2 = port2;
pthread_mutex_lock(&serverlist_lock);
/* diesen server in der liste suchen */
nserver = LIST_FIND(&serverlist, server_cmp, struct game_server *, &server);
if (!nserver) {
/* neuen eintrag anlegen */
if (!(nserver = malloc(sizeof(struct game_server)))) {
pthread_mutex_unlock(&serverlist_lock);
log_print("server_add(): malloc()");
return 0;
}
#ifdef DEBUG
{
struct in_addr tmp;
tmp.s_addr = server.ip;
printf("server_add_new: gameid=%2d ip=%15s port1=%5d port2=%5d\n",
server.gameid, inet_ntoa(tmp), server.port1, server.port2);
}
#endif
memcpy(nserver, &server, sizeof(struct game_server));
list_add_tail(&nserver->list, &serverlist);
}
/* modtime anpassen */
nserver->modtime = time(NULL);
pthread_mutex_unlock(&serverlist_lock);
return 1;
}
/**
* serverlist_refresh()
* loescht alte server aus der liste
* baut aus den verbleibenden die client_liste auf
*
* @param long timeout
*/
static void serverlist_refresh(long timeout) {
struct game_server *server, *tmp;
long now = time(NULL);
pthread_mutex_lock(&serverlist_lock);
list_for_each_entry_safe(server, tmp, &serverlist, list) {
if ((server->modtime + timeout) < now) {
#ifdef DEBUG
{
struct in_addr tmp2;
tmp2.s_addr = server->ip;
printf("server timeout: gameid=%2d ip=%15s port1=%5d port2=%5d\n",
server->gameid, inet_ntoa(tmp2), server->port1, server->port2);
}
#endif
list_del(&server->list);
free(server);
} else {
client_pkt_add(server);
}
}
pthread_mutex_unlock(&serverlist_lock);
client_pkt_commit();
}
/**
* pkt_send()
* schickt ein paket ab
*
* @param struct in_addr *dstip - pointer auf eine IP, wenn NULL wird broadcast angenommen
* @param unsigned int dstport - destination port
* @param char *buf - pointer auf den zu sendenen speicherbereich
* @param unsigned int size - groesse des speicherbereichs
* @return false bei fehler
*/
int pkt_send(struct in_addr *dstip, unsigned int dstport, char *buf, unsigned int size) {
struct sockaddr_in addr;
addr.sin_family = AF_INET;
addr.sin_port = htons(dstport);
addr.sin_addr.s_addr = (dstip ? dstip->s_addr : 0xFFFFFFFF);
//inet_aton("10.4.1.1", &addr.sin_addr);
if (sendto(scan_sock, buf, size, 0, (struct sockaddr *)&addr, sizeof(addr)) < 0)
log_print("scan_send(): sendto()");
usleep(10000);
return 1;
}
/**
* scan_control()
* triggert den scan der plugins
* arbeitet dann die sender queue ab
* triggert den gc der plugins
*/
void scan_control(void) {
struct net_pkt *pkt, *tmp;
long now;
long last_plugin_gc = 0, last_list_refresh = 0, last_scan = 0;
int plugin_timeout, list_timeout, list_refresh, scan_interval;
plugin_timeout = config_get_int("global", "plugin_timeout", 30);
list_timeout = config_get_int("global", "serverlist_timeout", 30);
list_refresh = config_get_int("global", "serverlist_refresh", 5);
scan_interval = config_get_int("global", "scan_interval", 30);
log_print("thread_start: scan_control");
log_print(" scan_interval: %ds", scan_interval);
log_print(" serverlist_refresh: %ds", list_refresh);
log_print(" serverlist_timeout: %ds", list_timeout);
log_print(" plugin_timeout: %d", plugin_timeout);
while (1) {
now = time(NULL);
/* interne plugin daten aufraeumen */
if (last_plugin_gc + plugin_timeout < now) {
last_plugin_gc = now;
plugins_gc(plugin_timeout);
}
/* server liste aufraeumen, und neue client pkts erzeugen */
if (last_list_refresh + list_refresh < now) {
last_list_refresh = now;
serverlist_refresh(list_timeout);
}
/* neuen scan ausloesen */
if (last_scan + scan_interval < now) {
last_scan = now;
plugins_scan();
}
sleep(1);
}
}
/**
* scan_receive()
* wartet auf serverantworten und uebergibt die pakete den
* plugins zur auswertung
*/
void scan_receive(void) {
struct net_pkt *pkt;
fd_set fdsel, fdcpy;
int recvsize, i;
log_print("thread_start: scan_receiver");
FD_ZERO(&fdsel);
FD_SET(scan_sock, &fdsel);
while (1) {
memcpy(&fdcpy, &fdsel, sizeof(fdsel));
select(FD_SETSIZE, &fdcpy, NULL, NULL, NULL);
ioctl(scan_sock, FIONREAD, &recvsize);
if (recvsize <= 0) {
log_print("scan_receive(): drop short packet");
continue;
}
if (!(pkt = malloc(sizeof(struct net_pkt) + recvsize))) {
log_print("scan_receive(): malloc()");
continue;
}
i = sizeof(struct sockaddr_in);
pkt->size = recvfrom(scan_sock, pkt->buf, recvsize, 0, (struct sockaddr *)&pkt->addr, &i);
if (!plugins_parse(pkt)) {
log_print("scan_receive(): unknown packet: %s:%d size:%d",
inet_ntoa(pkt->addr.sin_addr), ntohs(pkt->addr.sin_port), pkt->size);
}
free(pkt);
}
}
/**
* schliesst den server scan socket
*/
static void scan_close() {
close(scan_sock);
}
/**
* scan_init()
* initialisiert den socket fuer den server scan
* @return false on error
*/
int scan_init() {
struct sockaddr_in dst;
int i = 1, port;
char *ip;
if ((scan_sock = socket(PF_INET, SOCK_DGRAM, 0)) < 0) {
log_print("scan_init(): socket()");
return 0;
}
ip = config_get_string("global", "scan_ip", "0.0.0.0");
port = config_get_int("global", "scan_port", 7130);
dst.sin_family = AF_INET;
dst.sin_port = htons(port);
inet_aton(ip, &dst.sin_addr);
if (bind(scan_sock, (struct sockaddr *)&dst, sizeof(dst)) < 0) {
log_print("scan_init(): bind()");
return 0;
}
if (setsockopt(scan_sock, SOL_SOCKET, SO_BROADCAST, &i, sizeof(i))) {
log_print("scan_init(): setsockopt()");
return 0;
}
if (atexit(scan_close) != 0) {
log_print("scan_init(): atexit()");
return 0;
}
log_print("scan socket initialized (%s:%d)", ip, port);
return 1;
}

View File

@ -1,6 +0,0 @@
AUTOMAKE_OPTIONS = foreign no-dependencies
INCLUDES = -I../include
bin_PROGRAMS = masterquery
masterquery_SOURCES = masterquery.c

View File

@ -1,433 +0,0 @@
# Makefile.in generated by automake 1.9.4 from Makefile.am.
# @configure_input@
# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
# 2003, 2004 Free Software Foundation, Inc.
# This Makefile.in is free software; the Free Software Foundation
# gives unlimited permission to copy and/or distribute it,
# with or without modifications, as long as this notice is preserved.
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
# PARTICULAR PURPOSE.
@SET_MAKE@
SOURCES = $(masterquery_SOURCES)
srcdir = @srcdir@
top_srcdir = @top_srcdir@
VPATH = @srcdir@
pkgdatadir = $(datadir)/@PACKAGE@
pkglibdir = $(libdir)/@PACKAGE@
pkgincludedir = $(includedir)/@PACKAGE@
top_builddir = ..
am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
INSTALL = @INSTALL@
install_sh_DATA = $(install_sh) -c -m 644
install_sh_PROGRAM = $(install_sh) -c
install_sh_SCRIPT = $(install_sh) -c
INSTALL_HEADER = $(INSTALL_DATA)
transform = $(program_transform_name)
NORMAL_INSTALL = :
PRE_INSTALL = :
POST_INSTALL = :
NORMAL_UNINSTALL = :
PRE_UNINSTALL = :
POST_UNINSTALL = :
build_triplet = @build@
host_triplet = @host@
bin_PROGRAMS = masterquery$(EXEEXT)
subdir = tools
DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
am__aclocal_m4_deps = $(top_srcdir)/configure.in
am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
$(ACLOCAL_M4)
mkinstalldirs = $(install_sh) -d
CONFIG_HEADER = $(top_builddir)/config.h
CONFIG_CLEAN_FILES =
am__installdirs = "$(DESTDIR)$(bindir)"
binPROGRAMS_INSTALL = $(INSTALL_PROGRAM)
PROGRAMS = $(bin_PROGRAMS)
am_masterquery_OBJECTS = masterquery.$(OBJEXT)
masterquery_OBJECTS = $(am_masterquery_OBJECTS)
masterquery_LDADD = $(LDADD)
DEFAULT_INCLUDES = -I. -I$(srcdir) -I$(top_builddir)
depcomp =
am__depfiles_maybe =
COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
$(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
LTCOMPILE = $(LIBTOOL) --tag=CC --mode=compile $(CC) $(DEFS) \
$(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \
$(AM_CFLAGS) $(CFLAGS)
CCLD = $(CC)
LINK = $(LIBTOOL) --tag=CC --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \
$(AM_LDFLAGS) $(LDFLAGS) -o $@
SOURCES = $(masterquery_SOURCES)
DIST_SOURCES = $(masterquery_SOURCES)
ETAGS = etags
CTAGS = ctags
DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
ACLOCAL = @ACLOCAL@
AMDEP_FALSE = @AMDEP_FALSE@
AMDEP_TRUE = @AMDEP_TRUE@
AMTAR = @AMTAR@
AR = @AR@
AUTOCONF = @AUTOCONF@
AUTOHEADER = @AUTOHEADER@
AUTOMAKE = @AUTOMAKE@
AWK = @AWK@
CC = @CC@
CCDEPMODE = @CCDEPMODE@
CFLAGS = @CFLAGS@
CPP = @CPP@
CPPFLAGS = @CPPFLAGS@
CXX = @CXX@
CXXCPP = @CXXCPP@
CXXDEPMODE = @CXXDEPMODE@
CXXFLAGS = @CXXFLAGS@
CYGPATH_W = @CYGPATH_W@
DEFS = @DEFS@
DEPDIR = @DEPDIR@
ECHO = @ECHO@
ECHO_C = @ECHO_C@
ECHO_N = @ECHO_N@
ECHO_T = @ECHO_T@
EGREP = @EGREP@
EXEEXT = @EXEEXT@
F77 = @F77@
FFLAGS = @FFLAGS@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_SCRIPT = @INSTALL_SCRIPT@
INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
LDFLAGS = @LDFLAGS@
LIBOBJS = @LIBOBJS@
LIBS = @LIBS@
LIBTOOL = @LIBTOOL@
LN_S = @LN_S@
LTLIBOBJS = @LTLIBOBJS@
MAINT = @MAINT@
MAINTAINER_MODE_FALSE = @MAINTAINER_MODE_FALSE@
MAINTAINER_MODE_TRUE = @MAINTAINER_MODE_TRUE@
MAKEINFO = @MAKEINFO@
OBJEXT = @OBJEXT@
PACKAGE = @PACKAGE@
PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
PACKAGE_NAME = @PACKAGE_NAME@
PACKAGE_STRING = @PACKAGE_STRING@
PACKAGE_TARNAME = @PACKAGE_TARNAME@
PACKAGE_VERSION = @PACKAGE_VERSION@
PATH_SEPARATOR = @PATH_SEPARATOR@
RANLIB = @RANLIB@
SET_MAKE = @SET_MAKE@
SHELL = @SHELL@
STRIP = @STRIP@
VERSION = @VERSION@
ac_ct_AR = @ac_ct_AR@
ac_ct_CC = @ac_ct_CC@
ac_ct_CXX = @ac_ct_CXX@
ac_ct_F77 = @ac_ct_F77@
ac_ct_RANLIB = @ac_ct_RANLIB@
ac_ct_STRIP = @ac_ct_STRIP@
am__fastdepCC_FALSE = @am__fastdepCC_FALSE@
am__fastdepCC_TRUE = @am__fastdepCC_TRUE@
am__fastdepCXX_FALSE = @am__fastdepCXX_FALSE@
am__fastdepCXX_TRUE = @am__fastdepCXX_TRUE@
am__include = @am__include@
am__leading_dot = @am__leading_dot@
am__quote = @am__quote@
am__tar = @am__tar@
am__untar = @am__untar@
bindir = @bindir@
build = @build@
build_alias = @build_alias@
build_cpu = @build_cpu@
build_os = @build_os@
build_vendor = @build_vendor@
datadir = @datadir@
exec_prefix = @exec_prefix@
host = @host@
host_alias = @host_alias@
host_cpu = @host_cpu@
host_os = @host_os@
host_vendor = @host_vendor@
includedir = @includedir@
infodir = @infodir@
install_sh = @install_sh@
libdir = @libdir@
libexecdir = @libexecdir@
localstatedir = @localstatedir@
mandir = @mandir@
mkdir_p = @mkdir_p@
oldincludedir = @oldincludedir@
prefix = @prefix@
program_transform_name = @program_transform_name@
sbindir = @sbindir@
sharedstatedir = @sharedstatedir@
sysconfdir = @sysconfdir@
target_alias = @target_alias@
AUTOMAKE_OPTIONS = foreign no-dependencies
INCLUDES = -I../include
masterquery_SOURCES = masterquery.c
all: all-am
.SUFFIXES:
.SUFFIXES: .c .lo .o .obj
$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps)
@for dep in $?; do \
case '$(am__configure_deps)' in \
*$$dep*) \
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
&& exit 0; \
exit 1;; \
esac; \
done; \
echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign tools/Makefile'; \
cd $(top_srcdir) && \
$(AUTOMAKE) --foreign tools/Makefile
.PRECIOUS: Makefile
Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
@case '$?' in \
*config.status*) \
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
*) \
echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
esac;
$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
install-binPROGRAMS: $(bin_PROGRAMS)
@$(NORMAL_INSTALL)
test -z "$(bindir)" || $(mkdir_p) "$(DESTDIR)$(bindir)"
@list='$(bin_PROGRAMS)'; for p in $$list; do \
p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \
if test -f $$p \
|| test -f $$p1 \
; then \
f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \
echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) --mode=install $(binPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(bindir)/$$f'"; \
$(INSTALL_PROGRAM_ENV) $(LIBTOOL) --mode=install $(binPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(bindir)/$$f" || exit 1; \
else :; fi; \
done
uninstall-binPROGRAMS:
@$(NORMAL_UNINSTALL)
@list='$(bin_PROGRAMS)'; for p in $$list; do \
f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \
echo " rm -f '$(DESTDIR)$(bindir)/$$f'"; \
rm -f "$(DESTDIR)$(bindir)/$$f"; \
done
clean-binPROGRAMS:
@list='$(bin_PROGRAMS)'; for p in $$list; do \
f=`echo $$p|sed 's/$(EXEEXT)$$//'`; \
echo " rm -f $$p $$f"; \
rm -f $$p $$f ; \
done
masterquery$(EXEEXT): $(masterquery_OBJECTS) $(masterquery_DEPENDENCIES)
@rm -f masterquery$(EXEEXT)
$(LINK) $(masterquery_LDFLAGS) $(masterquery_OBJECTS) $(masterquery_LDADD) $(LIBS)
mostlyclean-compile:
-rm -f *.$(OBJEXT)
distclean-compile:
-rm -f *.tab.c
.c.o:
$(COMPILE) -c $<
.c.obj:
$(COMPILE) -c `$(CYGPATH_W) '$<'`
.c.lo:
$(LTCOMPILE) -c -o $@ $<
mostlyclean-libtool:
-rm -f *.lo
clean-libtool:
-rm -rf .libs _libs
distclean-libtool:
-rm -f libtool
uninstall-info-am:
ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
mkid -fID $$unique
tags: TAGS
TAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
test -n "$$unique" || unique=$$empty_fix; \
$(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
$$tags $$unique; \
fi
ctags: CTAGS
CTAGS: $(HEADERS) $(SOURCES) $(TAGS_DEPENDENCIES) \
$(TAGS_FILES) $(LISP)
tags=; \
here=`pwd`; \
list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
unique=`for i in $$list; do \
if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
done | \
$(AWK) ' { files[$$0] = 1; } \
END { for (i in files) print i; }'`; \
test -z "$(CTAGS_ARGS)$$tags$$unique" \
|| $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
$$tags $$unique
GTAGS:
here=`$(am__cd) $(top_builddir) && pwd` \
&& cd $(top_srcdir) \
&& gtags -i $(GTAGS_ARGS) $$here
distclean-tags:
-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
distdir: $(DISTFILES)
@srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; \
topsrcdirstrip=`echo "$(top_srcdir)" | sed 's|.|.|g'`; \
list='$(DISTFILES)'; for file in $$list; do \
case $$file in \
$(srcdir)/*) file=`echo "$$file" | sed "s|^$$srcdirstrip/||"`;; \
$(top_srcdir)/*) file=`echo "$$file" | sed "s|^$$topsrcdirstrip/|$(top_builddir)/|"`;; \
esac; \
if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
dir=`echo "$$file" | sed -e 's,/[^/]*$$,,'`; \
if test "$$dir" != "$$file" && test "$$dir" != "."; then \
dir="/$$dir"; \
$(mkdir_p) "$(distdir)$$dir"; \
else \
dir=''; \
fi; \
if test -d $$d/$$file; then \
if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
fi; \
cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
else \
test -f $(distdir)/$$file \
|| cp -p $$d/$$file $(distdir)/$$file \
|| exit 1; \
fi; \
done
check-am: all-am
check: check-am
all-am: Makefile $(PROGRAMS)
installdirs:
for dir in "$(DESTDIR)$(bindir)"; do \
test -z "$$dir" || $(mkdir_p) "$$dir"; \
done
install: install-am
install-exec: install-exec-am
install-data: install-data-am
uninstall: uninstall-am
install-am: all-am
@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
installcheck: installcheck-am
install-strip:
$(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
`test -z '$(STRIP)' || \
echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
mostlyclean-generic:
clean-generic:
distclean-generic:
-test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
maintainer-clean-generic:
@echo "This command is intended for maintainers to use"
@echo "it deletes files that may require special tools to rebuild."
clean: clean-am
clean-am: clean-binPROGRAMS clean-generic clean-libtool mostlyclean-am
distclean: distclean-am
-rm -f Makefile
distclean-am: clean-am distclean-compile distclean-generic \
distclean-libtool distclean-tags
dvi: dvi-am
dvi-am:
html: html-am
info: info-am
info-am:
install-data-am:
install-exec-am: install-binPROGRAMS
install-info: install-info-am
install-man:
installcheck-am:
maintainer-clean: maintainer-clean-am
-rm -f Makefile
maintainer-clean-am: distclean-am maintainer-clean-generic
mostlyclean: mostlyclean-am
mostlyclean-am: mostlyclean-compile mostlyclean-generic \
mostlyclean-libtool
pdf: pdf-am
pdf-am:
ps: ps-am
ps-am:
uninstall-am: uninstall-binPROGRAMS uninstall-info-am
.PHONY: CTAGS GTAGS all all-am check check-am clean clean-binPROGRAMS \
clean-generic clean-libtool ctags distclean distclean-compile \
distclean-generic distclean-libtool distclean-tags distdir dvi \
dvi-am html html-am info info-am install install-am \
install-binPROGRAMS install-data install-data-am install-exec \
install-exec-am install-info install-info-am install-man \
install-strip installcheck installcheck-am installdirs \
maintainer-clean maintainer-clean-generic mostlyclean \
mostlyclean-compile mostlyclean-generic mostlyclean-libtool \
pdf pdf-am ps ps-am tags uninstall uninstall-am \
uninstall-binPROGRAMS uninstall-info-am
# Tell versions [3.59,3.63) of GNU make to not export all variables.
# Otherwise a system limit (for SysV at least) may be exceeded.
.NOEXPORT: