From 2267da443a77b5dd8c8736d53d417edf53332653 Mon Sep 17 00:00:00 2001 From: Christian Pointner Date: Mon, 9 Jun 2014 19:45:40 +0200 Subject: [PATCH] This adds tcpproxy a simple tcp connection proxy. Signed-off-by: Christian Pointner --- net/tcpproxy/Makefile | 84 + net/tcpproxy/files/tcpproxy.config | 26 + net/tcpproxy/files/tcpproxy.init | 96 ++ .../patches/001-ragel_generated.patch | 1378 +++++++++++++++++ 4 files changed, 1584 insertions(+) create mode 100644 net/tcpproxy/Makefile create mode 100644 net/tcpproxy/files/tcpproxy.config create mode 100644 net/tcpproxy/files/tcpproxy.init create mode 100644 net/tcpproxy/patches/001-ragel_generated.patch diff --git a/net/tcpproxy/Makefile b/net/tcpproxy/Makefile new file mode 100644 index 000000000..c1056d955 --- /dev/null +++ b/net/tcpproxy/Makefile @@ -0,0 +1,84 @@ +# +# Copyright (C) 2010 Christian Pointner, +# +# +# This is free software, licensed under the GNU General Public License v2. +# See /LICENSE for more information. +# +# This Makefile builds tcpproxy Package for OpenWRT +# +# $Id: $ + +include $(TOPDIR)/rules.mk + +PKG_NAME:=tcpproxy +PKG_VERSION:=1.1 +PKG_RELEASE:=1 + +PKG_BUILD_DIR:=$(BUILD_DIR)/$(PKG_NAME)-$(PKG_VERSION) +PKG_SOURCE:=$(PKG_NAME)-$(PKG_VERSION).tar.gz +PKG_SOURCE_URL:=http://www.spreadspace.org/tcpproxy/releases/ +PKG_MD5SUM:=55126473bcde635f9ee019c6caf19bb7 + +include $(INCLUDE_DIR)/package.mk + + +define Package/tcpproxy + SECTION:=net + CATEGORY:=Network + SUBMENU:=Routing and Redirection + TITLE:=IPv4/IPv6 tcp connection proxy + URL:=http://www.spreadspace.org/tcpproxy/ + MAINTAINER:=Christian Pointner +endef + +define Package/tcpproxy/conffiles +/etc/config/tcpproxy +endef + +define Package/tcpproxy/description +tcpproxy is a simple tcp connection proxy which combines the features of rinetd and 6tunnel. + tcpproxy supports IPv4 and IPv6 and also supports connections from IPv6 to IPv4 endpoints and vice versa. +endef + +define Package/tcpproxy/configure +endef + +define Build/Configure + (cd $(PKG_BUILD_DIR)/src; \ + touch include.mk; \ + echo '#ifndef TCPPROXY_config_h_INCLUDED' > config.h; \ + echo '#define TCPPROXY_config_h_INCLUDED' >> config.h; \ + echo '' >> config.h; \ + echo '#define VERSION_STRING_0 "tcpproxy version '`cat $(PKG_BUILD_DIR)/version`'"' >> config.h; \ + echo '#define VERSION_STRING_1 "built on '`hostname`', '`date +"%d.%m.%Y %H:%M:%S %Z"`'"' >> config.h; \ + echo '' >> config.h; \ + echo '#define TARGET "linux"' >> config.h; \ + echo '#define PREFIX "/usr"' >> config.h; \ + echo '#define BINDIR "/usr/bin"' >> config.h; \ + echo '#define ETCDIR "/etc"' >> config.h; \ + echo '#define CONFFILE "/etc/tcpproxy.conf"' >> config.h; \ + echo '' >> config.h; \ + echo '#endif' >> config.h \ + ) +endef + +define Build/Compile + $(MAKE) -C $(PKG_BUILD_DIR)/src \ + $(TARGET_CONFIGURE_OPTS) \ + TARGET=Linux \ + CFLAGS="$(TARGET_CFLAGS)" \ + LDFLAGS="$(TARGET_LDFLAGS)" + $(STRIP) $(PKG_BUILD_DIR)/src/tcpproxy +endef + +define Package/tcpproxy/install + $(INSTALL_DIR) $(1)/etc/config + $(INSTALL_DATA) ./files/tcpproxy.config $(1)/etc/config/tcpproxy + $(INSTALL_DIR) $(1)/usr/bin + $(INSTALL_BIN) $(PKG_BUILD_DIR)/$(2)/src/tcpproxy $(1)/usr/bin/tcpproxy + $(INSTALL_DIR) $(1)/etc/init.d + $(INSTALL_BIN) ./files/tcpproxy.init $(1)/etc/init.d/tcpproxy +endef + +$(eval $(call BuildPackage,tcpproxy)) diff --git a/net/tcpproxy/files/tcpproxy.config b/net/tcpproxy/files/tcpproxy.config new file mode 100644 index 000000000..cd3f67cad --- /dev/null +++ b/net/tcpproxy/files/tcpproxy.config @@ -0,0 +1,26 @@ +config tcpproxy + option username 'nobody' + option groupname 'nogroup' +# option chroot "/var/run/tcpproxy" +# option log 'syslog:3,tcpproxy,daemon' + +config listen + option disabled 1 + + option local_port '8000' + option resolv 'ipv4' + + option remote_addr 'www.google.at' + option remote_port '80' + option remote_resolv 'ipv6' + option source_addr '2a02:3e0:2002:1:215:58ff:fe31:2ce7' + +config listen + option disabled 1 + + option local_addr '2a02:3e0:2002:1:215:58ff:fe31:2ce7' + option local_port '1234' + + option remote_addr 'www.google.at' + option remote_port '80' + option remote_resolv 'ipv4' diff --git a/net/tcpproxy/files/tcpproxy.init b/net/tcpproxy/files/tcpproxy.init new file mode 100644 index 000000000..4587a1c7b --- /dev/null +++ b/net/tcpproxy/files/tcpproxy.init @@ -0,0 +1,96 @@ +#!/bin/sh /etc/rc.common +START=50 + +BIN=tcpproxy +DAEMON=/usr/bin/$BIN +DAEMON_ARGS="" +DESC=$BIN +RUN_D=/var/run +CONFIG_DIR=/var/etc +CONFIG_FILE=$CONFIG_DIR/$BIN.conf + +tcpproxy_write_config() { + local cfg="$1" + + config_get_bool value "$cfg" disabled 0 + [ "$value" -ne 0 ] && return + + local local_addr="" + local resolv="" + local local_port="" + local remote_addr="" + local remote_resolv="" + local remote_port="" + local source_addr="" + + config_get local_addr "$cfg" local_addr + config_get local_port "$cfg" local_port + config_get resolv "$cfg" resolv + config_get remote_addr "$cfg" remote_addr + config_get remote_port "$cfg" remote_port + config_get remote_resolv "$cfg" remote_resolv + config_get source_addr "$cfg" source_addr + + if [ -z "$local_addr" ]; then + local_addr="*" + fi + + echo "listen $local_addr $local_port" >> $CONFIG_FILE + echo "{" >> $CONFIG_FILE + if [ -n "$resolv" ]; then + echo " resolv: $resolv;" >> $CONFIG_FILE + fi + echo " remote: $remote_addr $remote_port;" >> $CONFIG_FILE + if [ -n "$remote_resolv" ]; then + echo " remote-resolv: $remote_resolv;" >> $CONFIG_FILE + fi + if [ -n "$source_addr" ]; then + echo " source: $source_addr;" >> $CONFIG_FILE + fi + echo "};" >> $CONFIG_FILE + echo "" >> $CONFIG_FILE +} + +tcpproxy_generate_args() { + local cfg="$1" + local option + local value + + for option in username groupname chroot log + do + config_get value "$cfg" "$option" + option=`echo $option | tr '_' '-'` + if [ -n "$value" ]; then + DAEMON_ARGS="$DAEMON_ARGS --$option $value" + fi + done +} + +tcpproxy_rebuild_config() { + mkdir -p $CONFIG_DIR + rm -f $CONFIG_FILE + touch $CONFIG_FILE + config_load $BIN + config_foreach tcpproxy_write_config listen +} + +start() { + echo -n "Starting $DESC " + tcpproxy_rebuild_config + config_foreach tcpproxy_generate_args $BIN + $DAEMON $DAEMON_ARGS --config $CONFIG_FILE --write-pid "$RUN_D/$BIN.pid" + echo "." +} + +reload() { + echo -n "Reloading $DESC " + tcpproxy_rebuild_config + kill -SIGHUP `cat "$RUN_D/$BIN.pid"` + echo "." +} + +stop() { + echo -n "Stopping $DESC " + kill `cat $RUN_D/$BIN.pid` > /dev/null 2>&1 + echo "." +} diff --git a/net/tcpproxy/patches/001-ragel_generated.patch b/net/tcpproxy/patches/001-ragel_generated.patch new file mode 100644 index 000000000..38d6bc77e --- /dev/null +++ b/net/tcpproxy/patches/001-ragel_generated.patch @@ -0,0 +1,1378 @@ +diff -Nur tcpproxy-1.1.orig/src/cfg_parser.c tcpproxy-1.1/src/cfg_parser.c +--- tcpproxy-1.1.orig/src/cfg_parser.c 1970-01-01 01:00:00.000000000 +0100 ++++ tcpproxy-1.1/src/cfg_parser.c 2014-02-24 04:05:11.087171984 +0100 +@@ -0,0 +1,1374 @@ ++ ++#line 1 "cfg_parser.rl" ++/* ++ * tcpproxy ++ * ++ * tcpproxy is a simple tcp connection proxy which combines the ++ * features of rinetd and 6tunnel. tcpproxy supports IPv4 and ++ * IPv6 and also supports connections from IPv6 to IPv4 ++ * endpoints and vice versa. ++ * ++ * ++ * Copyright (C) 2010-2013 Christian Pointner ++ * ++ * This file is part of tcpproxy. ++ * ++ * tcpproxy 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 3 of the License, or ++ * any later version. ++ * ++ * tcpproxy 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 tcpproxy. If not, see . ++ */ ++ ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++#include ++ ++#include "datatypes.h" ++#include "log.h" ++#include "options.h" ++#include "tcp.h" ++#include "listener.h" ++ ++struct listener { ++ char* la_; ++ resolv_type_t lrt_; ++ char* lp_; ++ char* ra_; ++ resolv_type_t rrt_; ++ char* rp_; ++ char* sa_; ++}; ++ ++static void init_listener_struct(struct listener* l) ++{ ++ if(!l) return; ++ ++ l->la_ = NULL; ++ l->lrt_ = ANY; ++ l->lp_ = NULL; ++ l->ra_ = NULL; ++ l->rrt_ = ANY; ++ l->rp_ = NULL; ++ l->sa_ = NULL; ++} ++ ++static void clear_listener_struct(struct listener* l) ++{ ++ if(!l) return; ++ ++ if(l->la_) ++ free(l->la_); ++ if(l->lp_) ++ free(l->lp_); ++ if(l->ra_) ++ free(l->ra_); ++ if(l->rp_) ++ free(l->rp_); ++ if(l->sa_) ++ free(l->sa_); ++ ++ init_listener_struct(l); ++} ++ ++static int owrt_string(char** dest, char* start, char* end) ++{ ++ if(!dest || start >= end) ++ return -1; ++ ++ if(*dest) free(*dest); ++ int n = end - start; ++ *dest = malloc(n+1); ++ if(!(*dest)) ++ return -2; ++ ++ memcpy(*dest, start, n); ++ (*dest)[n] = 0; ++ ++ return 0; ++} ++ ++ ++#line 162 "cfg_parser.rl" ++ ++ ++ ++int parse_listener(char* p, char* pe, listeners_t* listener) ++{ ++ int cs, ret = 0, cur_line = 1; ++ ++ ++#line 114 "cfg_parser.c" ++static const int cfg_parser_start = 67; ++static const int cfg_parser_first_final = 67; ++static const int cfg_parser_error = 0; ++ ++static const int cfg_parser_en_main = 67; ++ ++ ++#line 170 "cfg_parser.rl" ++ ++#line 124 "cfg_parser.c" ++ { ++ cs = cfg_parser_start; ++ } ++ ++#line 171 "cfg_parser.rl" ++ ++ char* cpy_start = NULL; ++ struct listener lst; ++ init_listener_struct(&lst); ++ ++ char* eof = pe; ++ ++#line 137 "cfg_parser.c" ++ { ++ if ( p == pe ) ++ goto _test_eof; ++ goto _resume; ++ ++_again: ++ switch ( cs ) { ++ case 67: goto st67; ++ case 0: goto st0; ++ case 1: goto st1; ++ case 2: goto st2; ++ case 3: goto st3; ++ case 4: goto st4; ++ case 5: goto st5; ++ case 6: goto st6; ++ case 7: goto st7; ++ case 8: goto st8; ++ case 9: goto st9; ++ case 10: goto st10; ++ case 11: goto st11; ++ case 12: goto st12; ++ case 13: goto st13; ++ case 14: goto st14; ++ case 15: goto st15; ++ case 16: goto st16; ++ case 17: goto st17; ++ case 18: goto st18; ++ case 19: goto st19; ++ case 20: goto st20; ++ case 21: goto st21; ++ case 22: goto st22; ++ case 23: goto st23; ++ case 24: goto st24; ++ case 25: goto st25; ++ case 26: goto st26; ++ case 27: goto st27; ++ case 28: goto st28; ++ case 29: goto st29; ++ case 30: goto st30; ++ case 31: goto st31; ++ case 32: goto st32; ++ case 33: goto st33; ++ case 34: goto st34; ++ case 35: goto st35; ++ case 36: goto st36; ++ case 37: goto st37; ++ case 38: goto st38; ++ case 39: goto st39; ++ case 40: goto st40; ++ case 41: goto st41; ++ case 42: goto st42; ++ case 43: goto st43; ++ case 44: goto st44; ++ case 45: goto st45; ++ case 46: goto st46; ++ case 47: goto st47; ++ case 48: goto st48; ++ case 49: goto st49; ++ case 50: goto st50; ++ case 51: goto st51; ++ case 52: goto st52; ++ case 53: goto st53; ++ case 54: goto st54; ++ case 55: goto st55; ++ case 56: goto st56; ++ case 57: goto st57; ++ case 58: goto st58; ++ case 59: goto st59; ++ case 60: goto st60; ++ case 61: goto st61; ++ case 62: goto st62; ++ case 63: goto st63; ++ case 64: goto st64; ++ case 65: goto st65; ++ case 66: goto st66; ++ default: break; ++ } ++ ++ if ( ++p == pe ) ++ goto _test_eof; ++_resume: ++ switch ( cs ) ++ { ++tr1: ++#line 127 "cfg_parser.rl" ++ {cur_line++;} ++ goto st67; ++tr90: ++#line 114 "cfg_parser.rl" ++ { ++ ret = listeners_add(listener, lst.la_, lst.lrt_, lst.lp_, lst.ra_, lst.rrt_, lst.rp_, lst.sa_); ++ clear_listener_struct(&lst); ++ } ++ goto st67; ++st67: ++ if ( ++p == pe ) ++ goto _test_eof67; ++case 67: ++#line 236 "cfg_parser.c" ++ switch( (*p) ) { ++ case 10: goto tr1; ++ case 32: goto st67; ++ case 35: goto st1; ++ case 108: goto st2; ++ } ++ if ( 9 <= (*p) && (*p) <= 13 ) ++ goto st67; ++ goto tr2; ++tr2: ++#line 118 "cfg_parser.rl" ++ { ++ if(p == eof) ++ log_printf(ERROR, "config file syntax error: unexpected end of file"); ++ else ++ log_printf(ERROR, "config file syntax error at line %d", cur_line); ++ ++ {cs = (cfg_parser_error); goto _again;} ++ } ++ goto st0; ++#line 257 "cfg_parser.c" ++st0: ++cs = 0; ++ goto _out; ++st1: ++ if ( ++p == pe ) ++ goto _test_eof1; ++case 1: ++ if ( (*p) == 10 ) ++ goto tr1; ++ goto st1; ++st2: ++ if ( ++p == pe ) ++ goto _test_eof2; ++case 2: ++ if ( (*p) == 105 ) ++ goto st3; ++ goto tr2; ++st3: ++ if ( ++p == pe ) ++ goto _test_eof3; ++case 3: ++ if ( (*p) == 115 ) ++ goto st4; ++ goto tr2; ++st4: ++ if ( ++p == pe ) ++ goto _test_eof4; ++case 4: ++ if ( (*p) == 116 ) ++ goto st5; ++ goto tr2; ++st5: ++ if ( ++p == pe ) ++ goto _test_eof5; ++case 5: ++ if ( (*p) == 101 ) ++ goto st6; ++ goto tr2; ++st6: ++ if ( ++p == pe ) ++ goto _test_eof6; ++case 6: ++ if ( (*p) == 110 ) ++ goto st7; ++ goto tr2; ++st7: ++ if ( ++p == pe ) ++ goto _test_eof7; ++case 7: ++ switch( (*p) ) { ++ case 9: goto st8; ++ case 32: goto st8; ++ } ++ goto tr2; ++st8: ++ if ( ++p == pe ) ++ goto _test_eof8; ++case 8: ++ switch( (*p) ) { ++ case 9: goto st8; ++ case 32: goto st8; ++ case 42: goto st9; ++ case 58: goto tr12; ++ } ++ if ( (*p) < 65 ) { ++ if ( (*p) > 46 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto tr11; ++ } else if ( (*p) >= 45 ) ++ goto tr10; ++ } else if ( (*p) > 70 ) { ++ if ( (*p) < 97 ) { ++ if ( 71 <= (*p) && (*p) <= 90 ) ++ goto tr10; ++ } else if ( (*p) > 102 ) { ++ if ( 103 <= (*p) && (*p) <= 122 ) ++ goto tr10; ++ } else ++ goto tr11; ++ } else ++ goto tr11; ++ goto tr2; ++st9: ++ if ( ++p == pe ) ++ goto _test_eof9; ++case 9: ++ switch( (*p) ) { ++ case 9: goto st10; ++ case 32: goto st10; ++ } ++ goto tr2; ++tr91: ++#line 105 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.la_), cpy_start, p); cpy_start = NULL; } ++ goto st10; ++st10: ++ if ( ++p == pe ) ++ goto _test_eof10; ++case 10: ++#line 357 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto st10; ++ case 32: goto st10; ++ case 45: goto tr14; ++ } ++ if ( (*p) < 65 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto tr14; ++ } else if ( (*p) > 90 ) { ++ if ( 97 <= (*p) && (*p) <= 122 ) ++ goto tr14; ++ } else ++ goto tr14; ++ goto tr2; ++tr14: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st11; ++st11: ++ if ( ++p == pe ) ++ goto _test_eof11; ++case 11: ++#line 380 "cfg_parser.c" ++ switch( (*p) ) { ++ case 10: goto tr16; ++ case 32: goto tr15; ++ case 35: goto tr17; ++ case 45: goto st11; ++ case 123: goto tr19; ++ } ++ if ( (*p) < 48 ) { ++ if ( 9 <= (*p) && (*p) <= 13 ) ++ goto tr15; ++ } else if ( (*p) > 57 ) { ++ if ( (*p) > 90 ) { ++ if ( 97 <= (*p) && (*p) <= 122 ) ++ goto st11; ++ } else if ( (*p) >= 65 ) ++ goto st11; ++ } else ++ goto st11; ++ goto tr2; ++tr21: ++#line 127 "cfg_parser.rl" ++ {cur_line++;} ++ goto st12; ++tr15: ++#line 106 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.lp_), cpy_start, p); cpy_start = NULL; } ++ goto st12; ++tr16: ++#line 106 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.lp_), cpy_start, p); cpy_start = NULL; } ++#line 127 "cfg_parser.rl" ++ {cur_line++;} ++ goto st12; ++st12: ++ if ( ++p == pe ) ++ goto _test_eof12; ++case 12: ++#line 418 "cfg_parser.c" ++ switch( (*p) ) { ++ case 10: goto tr21; ++ case 32: goto st12; ++ case 35: goto st13; ++ case 123: goto st14; ++ } ++ if ( 9 <= (*p) && (*p) <= 13 ) ++ goto st12; ++ goto tr2; ++tr17: ++#line 106 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.lp_), cpy_start, p); cpy_start = NULL; } ++ goto st13; ++st13: ++ if ( ++p == pe ) ++ goto _test_eof13; ++case 13: ++#line 436 "cfg_parser.c" ++ if ( (*p) == 10 ) ++ goto tr21; ++ goto st13; ++tr24: ++#line 127 "cfg_parser.rl" ++ {cur_line++;} ++ goto st14; ++tr19: ++#line 106 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.lp_), cpy_start, p); cpy_start = NULL; } ++ goto st14; ++tr48: ++#line 110 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.rp_), cpy_start, p); cpy_start = NULL; } ++ goto st14; ++tr87: ++#line 113 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.sa_), cpy_start, p); cpy_start = NULL; } ++ goto st14; ++st14: ++ if ( ++p == pe ) ++ goto _test_eof14; ++case 14: ++#line 460 "cfg_parser.c" ++ switch( (*p) ) { ++ case 10: goto tr24; ++ case 32: goto st14; ++ case 35: goto st15; ++ case 114: goto st16; ++ case 115: goto st52; ++ case 125: goto st63; ++ } ++ if ( 9 <= (*p) && (*p) <= 13 ) ++ goto st14; ++ goto tr2; ++st15: ++ if ( ++p == pe ) ++ goto _test_eof15; ++case 15: ++ if ( (*p) == 10 ) ++ goto tr24; ++ goto st15; ++st16: ++ if ( ++p == pe ) ++ goto _test_eof16; ++case 16: ++ if ( (*p) == 101 ) ++ goto st17; ++ goto tr2; ++st17: ++ if ( ++p == pe ) ++ goto _test_eof17; ++case 17: ++ switch( (*p) ) { ++ case 109: goto st18; ++ case 115: goto st43; ++ } ++ goto tr2; ++st18: ++ if ( ++p == pe ) ++ goto _test_eof18; ++case 18: ++ if ( (*p) == 111 ) ++ goto st19; ++ goto tr2; ++st19: ++ if ( ++p == pe ) ++ goto _test_eof19; ++case 19: ++ if ( (*p) == 116 ) ++ goto st20; ++ goto tr2; ++st20: ++ if ( ++p == pe ) ++ goto _test_eof20; ++case 20: ++ if ( (*p) == 101 ) ++ goto st21; ++ goto tr2; ++st21: ++ if ( ++p == pe ) ++ goto _test_eof21; ++case 21: ++ switch( (*p) ) { ++ case 9: goto st22; ++ case 32: goto st22; ++ case 45: goto st31; ++ case 58: goto st23; ++ } ++ goto tr2; ++st22: ++ if ( ++p == pe ) ++ goto _test_eof22; ++case 22: ++ switch( (*p) ) { ++ case 9: goto st22; ++ case 32: goto st22; ++ case 58: goto st23; ++ } ++ goto tr2; ++st23: ++ if ( ++p == pe ) ++ goto _test_eof23; ++case 23: ++ switch( (*p) ) { ++ case 9: goto st24; ++ case 32: goto st24; ++ } ++ goto tr2; ++st24: ++ if ( ++p == pe ) ++ goto _test_eof24; ++case 24: ++ switch( (*p) ) { ++ case 9: goto st24; ++ case 32: goto st24; ++ case 58: goto tr41; ++ } ++ if ( (*p) < 65 ) { ++ if ( (*p) > 46 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto tr40; ++ } else if ( (*p) >= 45 ) ++ goto tr39; ++ } else if ( (*p) > 70 ) { ++ if ( (*p) < 97 ) { ++ if ( 71 <= (*p) && (*p) <= 90 ) ++ goto tr39; ++ } else if ( (*p) > 102 ) { ++ if ( 103 <= (*p) && (*p) <= 122 ) ++ goto tr39; ++ } else ++ goto tr40; ++ } else ++ goto tr40; ++ goto tr2; ++tr39: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st25; ++st25: ++ if ( ++p == pe ) ++ goto _test_eof25; ++case 25: ++#line 581 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr42; ++ case 32: goto tr42; ++ } ++ if ( (*p) < 48 ) { ++ if ( 45 <= (*p) && (*p) <= 46 ) ++ goto st25; ++ } else if ( (*p) > 57 ) { ++ if ( (*p) > 90 ) { ++ if ( 97 <= (*p) && (*p) <= 122 ) ++ goto st25; ++ } else if ( (*p) >= 65 ) ++ goto st25; ++ } else ++ goto st25; ++ goto tr2; ++tr42: ++#line 109 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.ra_), cpy_start, p); cpy_start = NULL; } ++ goto st26; ++st26: ++ if ( ++p == pe ) ++ goto _test_eof26; ++case 26: ++#line 606 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto st26; ++ case 32: goto st26; ++ case 45: goto tr45; ++ } ++ if ( (*p) < 65 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto tr45; ++ } else if ( (*p) > 90 ) { ++ if ( 97 <= (*p) && (*p) <= 122 ) ++ goto tr45; ++ } else ++ goto tr45; ++ goto tr2; ++tr45: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st27; ++st27: ++ if ( ++p == pe ) ++ goto _test_eof27; ++case 27: ++#line 629 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr46; ++ case 32: goto tr46; ++ case 45: goto st27; ++ case 59: goto tr48; ++ } ++ if ( (*p) < 65 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto st27; ++ } else if ( (*p) > 90 ) { ++ if ( 97 <= (*p) && (*p) <= 122 ) ++ goto st27; ++ } else ++ goto st27; ++ goto tr2; ++tr46: ++#line 110 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.rp_), cpy_start, p); cpy_start = NULL; } ++ goto st28; ++tr63: ++#line 111 "cfg_parser.rl" ++ { lst.rrt_ = IPV4_ONLY; } ++ goto st28; ++tr64: ++#line 112 "cfg_parser.rl" ++ { lst.rrt_ = IPV6_ONLY; } ++ goto st28; ++tr73: ++#line 107 "cfg_parser.rl" ++ { lst.lrt_ = IPV4_ONLY; } ++ goto st28; ++tr74: ++#line 108 "cfg_parser.rl" ++ { lst.lrt_ = IPV6_ONLY; } ++ goto st28; ++tr85: ++#line 113 "cfg_parser.rl" ++ { ret = owrt_string(&(lst.sa_), cpy_start, p); cpy_start = NULL; } ++ goto st28; ++st28: ++ if ( ++p == pe ) ++ goto _test_eof28; ++case 28: ++#line 673 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto st28; ++ case 32: goto st28; ++ case 59: goto st14; ++ } ++ goto tr2; ++tr40: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st29; ++st29: ++ if ( ++p == pe ) ++ goto _test_eof29; ++case 29: ++#line 688 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr42; ++ case 32: goto tr42; ++ case 58: goto st30; ++ } ++ if ( (*p) < 65 ) { ++ if ( (*p) > 46 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto st29; ++ } else if ( (*p) >= 45 ) ++ goto st25; ++ } else if ( (*p) > 70 ) { ++ if ( (*p) < 97 ) { ++ if ( 71 <= (*p) && (*p) <= 90 ) ++ goto st25; ++ } else if ( (*p) > 102 ) { ++ if ( 103 <= (*p) && (*p) <= 122 ) ++ goto st25; ++ } else ++ goto st29; ++ } else ++ goto st29; ++ goto tr2; ++tr41: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st30; ++st30: ++ if ( ++p == pe ) ++ goto _test_eof30; ++case 30: ++#line 720 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr42; ++ case 32: goto tr42; ++ } ++ if ( (*p) < 65 ) { ++ if ( 48 <= (*p) && (*p) <= 58 ) ++ goto st30; ++ } else if ( (*p) > 70 ) { ++ if ( 97 <= (*p) && (*p) <= 102 ) ++ goto st30; ++ } else ++ goto st30; ++ goto tr2; ++st31: ++ if ( ++p == pe ) ++ goto _test_eof31; ++case 31: ++ if ( (*p) == 114 ) ++ goto st32; ++ goto tr2; ++st32: ++ if ( ++p == pe ) ++ goto _test_eof32; ++case 32: ++ if ( (*p) == 101 ) ++ goto st33; ++ goto tr2; ++st33: ++ if ( ++p == pe ) ++ goto _test_eof33; ++case 33: ++ if ( (*p) == 115 ) ++ goto st34; ++ goto tr2; ++st34: ++ if ( ++p == pe ) ++ goto _test_eof34; ++case 34: ++ if ( (*p) == 111 ) ++ goto st35; ++ goto tr2; ++st35: ++ if ( ++p == pe ) ++ goto _test_eof35; ++case 35: ++ if ( (*p) == 108 ) ++ goto st36; ++ goto tr2; ++st36: ++ if ( ++p == pe ) ++ goto _test_eof36; ++case 36: ++ if ( (*p) == 118 ) ++ goto st37; ++ goto tr2; ++st37: ++ if ( ++p == pe ) ++ goto _test_eof37; ++case 37: ++ switch( (*p) ) { ++ case 9: goto st37; ++ case 32: goto st37; ++ case 58: goto st38; ++ } ++ goto tr2; ++st38: ++ if ( ++p == pe ) ++ goto _test_eof38; ++case 38: ++ switch( (*p) ) { ++ case 9: goto st39; ++ case 32: goto st39; ++ } ++ goto tr2; ++st39: ++ if ( ++p == pe ) ++ goto _test_eof39; ++case 39: ++ switch( (*p) ) { ++ case 9: goto st39; ++ case 32: goto st39; ++ case 73: goto st40; ++ case 105: goto st40; ++ } ++ goto tr2; ++st40: ++ if ( ++p == pe ) ++ goto _test_eof40; ++case 40: ++ switch( (*p) ) { ++ case 80: goto st41; ++ case 112: goto st41; ++ } ++ goto tr2; ++st41: ++ if ( ++p == pe ) ++ goto _test_eof41; ++case 41: ++ switch( (*p) ) { ++ case 86: goto st42; ++ case 118: goto st42; ++ } ++ goto tr2; ++st42: ++ if ( ++p == pe ) ++ goto _test_eof42; ++case 42: ++ switch( (*p) ) { ++ case 52: goto tr63; ++ case 54: goto tr64; ++ } ++ goto tr2; ++st43: ++ if ( ++p == pe ) ++ goto _test_eof43; ++case 43: ++ if ( (*p) == 111 ) ++ goto st44; ++ goto tr2; ++st44: ++ if ( ++p == pe ) ++ goto _test_eof44; ++case 44: ++ if ( (*p) == 108 ) ++ goto st45; ++ goto tr2; ++st45: ++ if ( ++p == pe ) ++ goto _test_eof45; ++case 45: ++ if ( (*p) == 118 ) ++ goto st46; ++ goto tr2; ++st46: ++ if ( ++p == pe ) ++ goto _test_eof46; ++case 46: ++ switch( (*p) ) { ++ case 9: goto st46; ++ case 32: goto st46; ++ case 58: goto st47; ++ } ++ goto tr2; ++st47: ++ if ( ++p == pe ) ++ goto _test_eof47; ++case 47: ++ switch( (*p) ) { ++ case 9: goto st48; ++ case 32: goto st48; ++ } ++ goto tr2; ++st48: ++ if ( ++p == pe ) ++ goto _test_eof48; ++case 48: ++ switch( (*p) ) { ++ case 9: goto st48; ++ case 32: goto st48; ++ case 73: goto st49; ++ case 105: goto st49; ++ } ++ goto tr2; ++st49: ++ if ( ++p == pe ) ++ goto _test_eof49; ++case 49: ++ switch( (*p) ) { ++ case 80: goto st50; ++ case 112: goto st50; ++ } ++ goto tr2; ++st50: ++ if ( ++p == pe ) ++ goto _test_eof50; ++case 50: ++ switch( (*p) ) { ++ case 86: goto st51; ++ case 118: goto st51; ++ } ++ goto tr2; ++st51: ++ if ( ++p == pe ) ++ goto _test_eof51; ++case 51: ++ switch( (*p) ) { ++ case 52: goto tr73; ++ case 54: goto tr74; ++ } ++ goto tr2; ++st52: ++ if ( ++p == pe ) ++ goto _test_eof52; ++case 52: ++ if ( (*p) == 111 ) ++ goto st53; ++ goto tr2; ++st53: ++ if ( ++p == pe ) ++ goto _test_eof53; ++case 53: ++ if ( (*p) == 117 ) ++ goto st54; ++ goto tr2; ++st54: ++ if ( ++p == pe ) ++ goto _test_eof54; ++case 54: ++ if ( (*p) == 114 ) ++ goto st55; ++ goto tr2; ++st55: ++ if ( ++p == pe ) ++ goto _test_eof55; ++case 55: ++ if ( (*p) == 99 ) ++ goto st56; ++ goto tr2; ++st56: ++ if ( ++p == pe ) ++ goto _test_eof56; ++case 56: ++ if ( (*p) == 101 ) ++ goto st57; ++ goto tr2; ++st57: ++ if ( ++p == pe ) ++ goto _test_eof57; ++case 57: ++ switch( (*p) ) { ++ case 9: goto st57; ++ case 32: goto st57; ++ case 58: goto st58; ++ } ++ goto tr2; ++st58: ++ if ( ++p == pe ) ++ goto _test_eof58; ++case 58: ++ switch( (*p) ) { ++ case 9: goto st59; ++ case 32: goto st59; ++ } ++ goto tr2; ++st59: ++ if ( ++p == pe ) ++ goto _test_eof59; ++case 59: ++ switch( (*p) ) { ++ case 9: goto st59; ++ case 32: goto st59; ++ case 58: goto tr84; ++ } ++ if ( (*p) < 65 ) { ++ if ( (*p) > 46 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto tr83; ++ } else if ( (*p) >= 45 ) ++ goto tr82; ++ } else if ( (*p) > 70 ) { ++ if ( (*p) < 97 ) { ++ if ( 71 <= (*p) && (*p) <= 90 ) ++ goto tr82; ++ } else if ( (*p) > 102 ) { ++ if ( 103 <= (*p) && (*p) <= 122 ) ++ goto tr82; ++ } else ++ goto tr83; ++ } else ++ goto tr83; ++ goto tr2; ++tr82: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st60; ++st60: ++ if ( ++p == pe ) ++ goto _test_eof60; ++case 60: ++#line 1000 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr85; ++ case 32: goto tr85; ++ case 59: goto tr87; ++ } ++ if ( (*p) < 48 ) { ++ if ( 45 <= (*p) && (*p) <= 46 ) ++ goto st60; ++ } else if ( (*p) > 57 ) { ++ if ( (*p) > 90 ) { ++ if ( 97 <= (*p) && (*p) <= 122 ) ++ goto st60; ++ } else if ( (*p) >= 65 ) ++ goto st60; ++ } else ++ goto st60; ++ goto tr2; ++tr83: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st61; ++st61: ++ if ( ++p == pe ) ++ goto _test_eof61; ++case 61: ++#line 1026 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr85; ++ case 32: goto tr85; ++ case 58: goto st62; ++ case 59: goto tr87; ++ } ++ if ( (*p) < 65 ) { ++ if ( (*p) > 46 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto st61; ++ } else if ( (*p) >= 45 ) ++ goto st60; ++ } else if ( (*p) > 70 ) { ++ if ( (*p) < 97 ) { ++ if ( 71 <= (*p) && (*p) <= 90 ) ++ goto st60; ++ } else if ( (*p) > 102 ) { ++ if ( 103 <= (*p) && (*p) <= 122 ) ++ goto st60; ++ } else ++ goto st61; ++ } else ++ goto st61; ++ goto tr2; ++tr84: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st62; ++st62: ++ if ( ++p == pe ) ++ goto _test_eof62; ++case 62: ++#line 1059 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr85; ++ case 32: goto tr85; ++ case 59: goto tr87; ++ } ++ if ( (*p) < 65 ) { ++ if ( 48 <= (*p) && (*p) <= 58 ) ++ goto st62; ++ } else if ( (*p) > 70 ) { ++ if ( 97 <= (*p) && (*p) <= 102 ) ++ goto st62; ++ } else ++ goto st62; ++ goto tr2; ++st63: ++ if ( ++p == pe ) ++ goto _test_eof63; ++case 63: ++ if ( (*p) == 59 ) ++ goto tr90; ++ goto tr2; ++tr10: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st64; ++st64: ++ if ( ++p == pe ) ++ goto _test_eof64; ++case 64: ++#line 1089 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr91; ++ case 32: goto tr91; ++ } ++ if ( (*p) < 48 ) { ++ if ( 45 <= (*p) && (*p) <= 46 ) ++ goto st64; ++ } else if ( (*p) > 57 ) { ++ if ( (*p) > 90 ) { ++ if ( 97 <= (*p) && (*p) <= 122 ) ++ goto st64; ++ } else if ( (*p) >= 65 ) ++ goto st64; ++ } else ++ goto st64; ++ goto tr2; ++tr11: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st65; ++st65: ++ if ( ++p == pe ) ++ goto _test_eof65; ++case 65: ++#line 1114 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr91; ++ case 32: goto tr91; ++ case 58: goto st66; ++ } ++ if ( (*p) < 65 ) { ++ if ( (*p) > 46 ) { ++ if ( 48 <= (*p) && (*p) <= 57 ) ++ goto st65; ++ } else if ( (*p) >= 45 ) ++ goto st64; ++ } else if ( (*p) > 70 ) { ++ if ( (*p) < 97 ) { ++ if ( 71 <= (*p) && (*p) <= 90 ) ++ goto st64; ++ } else if ( (*p) > 102 ) { ++ if ( 103 <= (*p) && (*p) <= 122 ) ++ goto st64; ++ } else ++ goto st65; ++ } else ++ goto st65; ++ goto tr2; ++tr12: ++#line 104 "cfg_parser.rl" ++ { cpy_start = p; } ++ goto st66; ++st66: ++ if ( ++p == pe ) ++ goto _test_eof66; ++case 66: ++#line 1146 "cfg_parser.c" ++ switch( (*p) ) { ++ case 9: goto tr91; ++ case 32: goto tr91; ++ } ++ if ( (*p) < 65 ) { ++ if ( 48 <= (*p) && (*p) <= 58 ) ++ goto st66; ++ } else if ( (*p) > 70 ) { ++ if ( 97 <= (*p) && (*p) <= 102 ) ++ goto st66; ++ } else ++ goto st66; ++ goto tr2; ++ } ++ _test_eof67: cs = 67; goto _test_eof; ++ _test_eof1: cs = 1; goto _test_eof; ++ _test_eof2: cs = 2; goto _test_eof; ++ _test_eof3: cs = 3; goto _test_eof; ++ _test_eof4: cs = 4; goto _test_eof; ++ _test_eof5: cs = 5; goto _test_eof; ++ _test_eof6: cs = 6; goto _test_eof; ++ _test_eof7: cs = 7; goto _test_eof; ++ _test_eof8: cs = 8; goto _test_eof; ++ _test_eof9: cs = 9; goto _test_eof; ++ _test_eof10: cs = 10; goto _test_eof; ++ _test_eof11: cs = 11; goto _test_eof; ++ _test_eof12: cs = 12; goto _test_eof; ++ _test_eof13: cs = 13; goto _test_eof; ++ _test_eof14: cs = 14; goto _test_eof; ++ _test_eof15: cs = 15; goto _test_eof; ++ _test_eof16: cs = 16; goto _test_eof; ++ _test_eof17: cs = 17; goto _test_eof; ++ _test_eof18: cs = 18; goto _test_eof; ++ _test_eof19: cs = 19; goto _test_eof; ++ _test_eof20: cs = 20; goto _test_eof; ++ _test_eof21: cs = 21; goto _test_eof; ++ _test_eof22: cs = 22; goto _test_eof; ++ _test_eof23: cs = 23; goto _test_eof; ++ _test_eof24: cs = 24; goto _test_eof; ++ _test_eof25: cs = 25; goto _test_eof; ++ _test_eof26: cs = 26; goto _test_eof; ++ _test_eof27: cs = 27; goto _test_eof; ++ _test_eof28: cs = 28; goto _test_eof; ++ _test_eof29: cs = 29; goto _test_eof; ++ _test_eof30: cs = 30; goto _test_eof; ++ _test_eof31: cs = 31; goto _test_eof; ++ _test_eof32: cs = 32; goto _test_eof; ++ _test_eof33: cs = 33; goto _test_eof; ++ _test_eof34: cs = 34; goto _test_eof; ++ _test_eof35: cs = 35; goto _test_eof; ++ _test_eof36: cs = 36; goto _test_eof; ++ _test_eof37: cs = 37; goto _test_eof; ++ _test_eof38: cs = 38; goto _test_eof; ++ _test_eof39: cs = 39; goto _test_eof; ++ _test_eof40: cs = 40; goto _test_eof; ++ _test_eof41: cs = 41; goto _test_eof; ++ _test_eof42: cs = 42; goto _test_eof; ++ _test_eof43: cs = 43; goto _test_eof; ++ _test_eof44: cs = 44; goto _test_eof; ++ _test_eof45: cs = 45; goto _test_eof; ++ _test_eof46: cs = 46; goto _test_eof; ++ _test_eof47: cs = 47; goto _test_eof; ++ _test_eof48: cs = 48; goto _test_eof; ++ _test_eof49: cs = 49; goto _test_eof; ++ _test_eof50: cs = 50; goto _test_eof; ++ _test_eof51: cs = 51; goto _test_eof; ++ _test_eof52: cs = 52; goto _test_eof; ++ _test_eof53: cs = 53; goto _test_eof; ++ _test_eof54: cs = 54; goto _test_eof; ++ _test_eof55: cs = 55; goto _test_eof; ++ _test_eof56: cs = 56; goto _test_eof; ++ _test_eof57: cs = 57; goto _test_eof; ++ _test_eof58: cs = 58; goto _test_eof; ++ _test_eof59: cs = 59; goto _test_eof; ++ _test_eof60: cs = 60; goto _test_eof; ++ _test_eof61: cs = 61; goto _test_eof; ++ _test_eof62: cs = 62; goto _test_eof; ++ _test_eof63: cs = 63; goto _test_eof; ++ _test_eof64: cs = 64; goto _test_eof; ++ _test_eof65: cs = 65; goto _test_eof; ++ _test_eof66: cs = 66; goto _test_eof; ++ ++ _test_eof: {} ++ if ( p == eof ) ++ { ++ switch ( cs ) { ++ case 1: ++ case 2: ++ case 3: ++ case 4: ++ case 5: ++ case 6: ++ case 7: ++ case 8: ++ case 9: ++ case 10: ++ case 11: ++ case 12: ++ case 13: ++ case 14: ++ case 15: ++ case 16: ++ case 17: ++ case 18: ++ case 19: ++ case 20: ++ case 21: ++ case 22: ++ case 23: ++ case 24: ++ case 25: ++ case 26: ++ case 27: ++ case 28: ++ case 29: ++ case 30: ++ case 31: ++ case 32: ++ case 33: ++ case 34: ++ case 35: ++ case 36: ++ case 37: ++ case 38: ++ case 39: ++ case 40: ++ case 41: ++ case 42: ++ case 43: ++ case 44: ++ case 45: ++ case 46: ++ case 47: ++ case 48: ++ case 49: ++ case 50: ++ case 51: ++ case 52: ++ case 53: ++ case 54: ++ case 55: ++ case 56: ++ case 57: ++ case 58: ++ case 59: ++ case 60: ++ case 61: ++ case 62: ++ case 63: ++ case 64: ++ case 65: ++ case 66: ++#line 118 "cfg_parser.rl" ++ { ++ if(p == eof) ++ log_printf(ERROR, "config file syntax error: unexpected end of file"); ++ else ++ log_printf(ERROR, "config file syntax error at line %d", cur_line); ++ ++ {cs = (cfg_parser_error); goto _again;} ++ } ++ break; ++#line 1309 "cfg_parser.c" ++ } ++ } ++ ++ _out: {} ++ } ++ ++#line 178 "cfg_parser.rl" ++ ++ if(cs == cfg_parser_error) { ++ listeners_revert(listener); ++ ret = 1; ++ } ++ else ++ ret = listeners_update(listener); ++ ++ clear_listener_struct(&lst); ++ ++ return ret; ++} ++ ++int read_configfile(const char* filename, listeners_t* listener) ++{ ++ int fd = open(filename, 0); ++ if(fd < 0) { ++ log_printf(ERROR, "open('%s') failed: %s", filename, strerror(errno)); ++ return -1; ++ } ++ ++ struct stat sb; ++ if(fstat(fd, &sb) == -1) { ++ log_printf(ERROR, "fstat() error: %s", strerror(errno)); ++ close(fd); ++ return -1; ++ } ++ ++ if(!sb.st_size) { ++ log_printf(ERROR, "config file %s is empty", filename); ++ close(fd); ++ return -1; ++ } ++ ++ if(!S_ISREG(sb.st_mode)) { ++ log_printf(ERROR, "config file %s is not a regular file", filename); ++ close(fd); ++ return -1; ++ } ++ ++ char* p = (char*)mmap(NULL, sb.st_size, PROT_READ, MAP_SHARED, fd, 0); ++ if(p == MAP_FAILED) { ++ log_printf(ERROR, "mmap() error: %s", strerror(errno)); ++ close(fd); ++ return -1; ++ } ++ close(fd); ++ ++ log_printf(DEBUG, "mapped %ld bytes from file %s at address 0x%08lX", sb.st_size, filename, p); ++ int ret = parse_listener(p, p + sb.st_size, listener); ++ ++ if(munmap(p, sb.st_size) == -1) { ++ log_printf(ERROR, "munmap() error: %s", strerror(errno)); ++ return -1; ++ } ++ log_printf(DEBUG, "unmapped file %s", filename); ++ ++ return ret; ++}