[Pkg-privacy-commits] [onioncat] 74/340: split ocatroute.c to ocatsocks.c and ocatlibe.c bugfix in ocat_setup.c
Ximin Luo
infinity0 at moszumanska.debian.org
Sat Aug 22 13:04:26 UTC 2015
This is an automated email from the git hooks/post-receive script.
infinity0 pushed a commit to branch debian
in repository onioncat.
commit b1f98efc169c447901f07e17cf9659346d0a43fa
Author: eagle <eagle at 58e1ccc2-750e-0410-8d0d-f93ca75ab447>
Date: Thu Nov 27 10:23:57 2008 +0000
split ocatroute.c to ocatsocks.c and ocatlibe.c
bugfix in ocat_setup.c
git-svn-id: http://www.cypherpunk.at/svn/onioncat/trunk@363 58e1ccc2-750e-0410-8d0d-f93ca75ab447
---
src/Makefile.am | 2 +-
src/Makefile.in | 7 +-
src/ocat.h | 9 +++
src/ocatlibe.c | 64 ++++++++++++++++
src/ocatroute.c | 47 ++++--------
src/ocatsetup.c | 6 +-
src/ocatsocks.c | 226 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++
7 files changed, 323 insertions(+), 38 deletions(-)
diff --git a/src/Makefile.am b/src/Makefile.am
index b2b1726..51aa8dd 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -1,4 +1,4 @@
bin_PROGRAMS = ocat
-ocat_SOURCES = ocat.c ocatlog.c ocatroute.c ocatthread.c ocattun.c ocatv6conv.c ocatcompat.c ocatpeer.c ocatsetup.c ocatipv4route.c ocateth.c
+ocat_SOURCES = ocat.c ocatlog.c ocatroute.c ocatthread.c ocattun.c ocatv6conv.c ocatcompat.c ocatpeer.c ocatsetup.c ocatipv4route.c ocateth.c ocatsocks.c ocatlibe.c
include_HEADERS = ocat.h strlcpy.c strlcat.c
diff --git a/src/Makefile.in b/src/Makefile.in
index f930659..8da46f6 100644
--- a/src/Makefile.in
+++ b/src/Makefile.in
@@ -48,7 +48,8 @@ PROGRAMS = $(bin_PROGRAMS)
am_ocat_OBJECTS = ocat.$(OBJEXT) ocatlog.$(OBJEXT) ocatroute.$(OBJEXT) \
ocatthread.$(OBJEXT) ocattun.$(OBJEXT) ocatv6conv.$(OBJEXT) \
ocatcompat.$(OBJEXT) ocatpeer.$(OBJEXT) ocatsetup.$(OBJEXT) \
- ocatipv4route.$(OBJEXT) ocateth.$(OBJEXT)
+ ocatipv4route.$(OBJEXT) ocateth.$(OBJEXT) ocatsocks.$(OBJEXT) \
+ ocatlibe.$(OBJEXT)
ocat_OBJECTS = $(am_ocat_OBJECTS)
ocat_LDADD = $(LDADD)
DEFAULT_INCLUDES = -I. at am__isrc@ -I$(top_builddir)
@@ -152,7 +153,7 @@ sysconfdir = @sysconfdir@
target_alias = @target_alias@
top_builddir = @top_builddir@
top_srcdir = @top_srcdir@
-ocat_SOURCES = ocat.c ocatlog.c ocatroute.c ocatthread.c ocattun.c ocatv6conv.c ocatcompat.c ocatpeer.c ocatsetup.c ocatipv4route.c ocateth.c
+ocat_SOURCES = ocat.c ocatlog.c ocatroute.c ocatthread.c ocattun.c ocatv6conv.c ocatcompat.c ocatpeer.c ocatsetup.c ocatipv4route.c ocateth.c ocatsocks.c ocatlibe.c
include_HEADERS = ocat.h strlcpy.c strlcat.c
all: all-am
@@ -224,10 +225,12 @@ distclean-compile:
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatcompat.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocateth.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatipv4route.Po at am__quote@
+ at AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatlibe.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatlog.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatpeer.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatroute.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatsetup.Po at am__quote@
+ at AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatsocks.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatthread.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocattun.Po at am__quote@
@AMDEP_TRUE@@am__include@ @am__quote at ./$(DEPDIR)/ocatv6conv.Po at am__quote@
diff --git a/src/ocat.h b/src/ocat.h
index 3aaae2c..8ab2772 100644
--- a/src/ocat.h
+++ b/src/ocat.h
@@ -355,6 +355,8 @@ void *socks_connector(void *);
void *socket_cleaner(void *);
void *ocat_controller(void *);
void *ctrl_handler(void *);
+int insert_peer(int, const SocksQueue_t *, time_t);
+
/* ocatthread.c */
const OcatThread_t *init_ocat_thread(const char *);
@@ -397,6 +399,13 @@ void print_mac_tbl(FILE *);
void mac_cleanup(void);
char *mac_hw2str(const uint8_t *, char *);
+/* ocatsocks.c */
+void socks_queue(const struct in6_addr *, int);
+
+/* ocatlibe.c */
+void oe_close(int);
+int oe_remtr(char *);
+
#endif
diff --git a/src/ocatlibe.c b/src/ocatlibe.c
new file mode 100644
index 0000000..166c434
--- /dev/null
+++ b/src/ocatlibe.c
@@ -0,0 +1,64 @@
+/* Copyright 2008 Bernhard R. Fischer, Daniel Haslinger.
+ *
+ * This file is part of OnionCat.
+ *
+ * OnionCat 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, version 3 of the License.
+ *
+ * OnionCat 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 OnionCat. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+/*! ocatlibe.c
+ * Contains some helper functions.
+ *
+ * @author Bernhard Fischer <rahra _at_ cypherpunk at>
+ * @version 2008/02/03-01
+ */
+
+#include "config.h"
+
+#include <stdio.h>
+#include <string.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <errno.h>
+
+#include "ocat.h"
+
+
+void oe_close(int fd)
+{
+ int r;
+
+ while (close(fd) == -1)
+ {
+ r = errno;
+ log_msg(L_ERROR, "failed to close %d: \"%s\"", fd, strerror(r));
+ if (r == EINTR)
+ {
+ log_debug("re-closing %d", fd);
+ continue;
+ }
+ break;
+ }
+}
+
+
+int oe_remtr(char *s)
+{
+ if (!s[0])
+ return 0;
+ if (s[0] && (s[strlen(s) - 1] == '\n'))
+ s[strlen(s) - 1] = '\0';
+ if (s[0] && (s[strlen(s) - 1] == '\r'))
+ s[strlen(s) - 1] = '\0';
+ return strlen(s);
+}
+
diff --git a/src/ocatroute.c b/src/ocatroute.c
index 3794bfb..418877f 100644
--- a/src/ocatroute.c
+++ b/src/ocatroute.c
@@ -77,13 +77,6 @@ static pthread_mutex_t queue_mutex_ = PTHREAD_MUTEX_INITIALIZER;
static pthread_cond_t queue_cond_ = PTHREAD_COND_INITIALIZER;
#endif
-// SOCKS connector queue vars
-static SocksQueue_t *socks_queue_ = NULL;
-static int socks_connect_cnt_ = 0;
-static int socks_thread_cnt_ = 0;
-static pthread_mutex_t socks_queue_mutex_ = PTHREAD_MUTEX_INITIALIZER;
-static pthread_cond_t socks_queue_cond_ = PTHREAD_COND_INITIALIZER;
-
int forward_packet(const struct in6_addr *addr, const char *buf, int buflen)
{
@@ -236,7 +229,7 @@ int check_tor_prefix(const struct ip6_hdr *ihd)
void cleanup_socket(int fd, OcatPeer_t *peer)
{
log_msg(L_NOTICE | L_FCONN, "fd %d reached EOF, closing.", fd);
- close(fd);
+ oe_close(fd);
lock_peers();
delete_peer(peer);
unlock_peers();
@@ -374,7 +367,7 @@ void *socket_receiver(void *p)
if (!len)
{
log_msg(L_NOTICE | L_FCONN, "fd %d reached EOF, closing.", peer->tcpfd);
- close(peer->tcpfd);
+ oe_close(peer->tcpfd);
unlock_peer(peer);
lock_peers();
delete_peer(peer);
@@ -416,7 +409,7 @@ void *socket_receiver(void *p)
if (handle_http(peer))
{
log_msg(L_NOTICE | L_FCONN, "closing %d due to HTTP", peer->tcpfd);
- close(peer->tcpfd);
+ oe_close(peer->tcpfd);
unlock_peer(peer);
lock_peers();
delete_peer(peer);
@@ -622,14 +615,14 @@ int create_listener(struct sockaddr *addr, int sock_len)
if (bind(fd, addr, sock_len) < 0)
{
log_msg(L_FATAL, "could not bind listener %d: \"%s\"", fd, strerror(errno));
- close(fd);
+ oe_close(fd);
return -1;
}
if (listen(fd, 32) < 0)
{
log_msg(L_FATAL, "could not bring listener %d to listening state: \"%s\"", fd, strerror(errno));
- close(fd);
+ oe_close(fd);
return -1;
}
@@ -727,6 +720,7 @@ void *socket_acceptor(void *p)
}
+#if 0
int socks_connect(const SocksQueue_t *sq)
//int socks_connect(const struct in6_addr *addr)
{
@@ -754,10 +748,10 @@ int socks_connect(const SocksQueue_t *sq)
return E_SOCKS_SOCK;
t = time(NULL);
- if (connect(fd, (struct sockaddr*) &in, sizeof(in)) < 0)
+ if (connect(fd, (struct sockaddr*) &in, sizeof(in)) == -1)
{
- log_msg(L_ERROR, "connect() to TOR failed");
- close(fd);
+ log_msg(L_ERROR, "connect() to TOR failed: \"%s\"", strerror(errno));
+ oe_close(fd);
return E_SOCKS_CONN;
}
@@ -782,7 +776,7 @@ int socks_connect(const SocksQueue_t *sq)
if (read(fd, shdr, sizeof(SocksHdr_t)) < sizeof(SocksHdr_t))
{
log_msg(L_ERROR | L_FCONN, "short read, closing.");
- close(fd);
+ oe_close(fd);
return E_SOCKS_REQ;
}
log_debug("SOCKS response received");
@@ -790,7 +784,7 @@ int socks_connect(const SocksQueue_t *sq)
if (shdr->ver || (shdr->cmd != 90))
{
log_msg(L_ERROR, "request failed, reason = %d", shdr->cmd);
- close(fd);
+ oe_close(fd);
return E_SOCKS_RQFAIL;
}
log_msg(L_NOTICE | L_FCONN, "connection to %s successfully opened on fd %d", onion, fd);
@@ -892,6 +886,7 @@ void *socks_connector(void *p)
}
return NULL;
}
+#endif
void packet_forwarder(void)
@@ -1083,7 +1078,7 @@ void *socket_cleaner(void *ptr)
peer = *p;
*p = peer->next;
log_msg(L_NOTICE | L_FCONN, "peer %d timed out, closing.", peer->tcpfd);
- close(peer->tcpfd);
+ oe_close(peer->tcpfd);
unlock_peer(peer);
delete_peer(peer);
if (!(*p))
@@ -1100,18 +1095,6 @@ void *socket_cleaner(void *ptr)
}
-int _remtr(char *s)
-{
- if (!s[0])
- return 0;
- if (s[0] && (s[strlen(s) - 1] == '\n'))
- s[strlen(s) - 1] = '\0';
- if (s[0] && (s[strlen(s) - 1] == '\r'))
- s[strlen(s) - 1] = '\0';
- return strlen(s);
-}
-
-
/**! ctrl_handler handles connections to local control port.
* @param p void* typcasted to int contains fd of connected socket.
* @return Currently always returns NULL.
@@ -1188,7 +1171,7 @@ void *ctrl_handler(void *p)
break;
}
- if (!(rlen = _remtr(buf)))
+ if (!(rlen = oe_remtr(buf)))
continue;
if (!strtok_r(buf, " \t\r\n", &tokbuf))
@@ -1225,7 +1208,7 @@ void *ctrl_handler(void *p)
if (peer->tcpfd == cfd)
{
log_msg(L_NOTICE | L_FCONN, "close request for %d", cfd);
- close(cfd);
+ oe_close(cfd);
delete_peer(peer);
break;
}
diff --git a/src/ocatsetup.c b/src/ocatsetup.c
index 78aed2a..e67841e 100644
--- a/src/ocatsetup.c
+++ b/src/ocatsetup.c
@@ -96,9 +96,9 @@ void print_setup_struct(FILE *f)
"use_tap = %d\n"
"ocat_hwaddr = %s\n"
"pid_file = \"%s\"\n"
- "logfn = \"%s\""
- "logf = %s"
- "daemon = %d",
+ "logfn = \"%s\"\n"
+ "logf = %s\n"
+ "daemon = %d\n",
IPV4_KEY, ntohl(setup.fhd_key[IPV4_KEY]), IPV6_KEY, ntohl(setup.fhd_key[IPV6_KEY]),
setup.fhd_key_len,
diff --git a/src/ocatsocks.c b/src/ocatsocks.c
new file mode 100644
index 0000000..40336f0
--- /dev/null
+++ b/src/ocatsocks.c
@@ -0,0 +1,226 @@
+/* Copyright 2008 Bernhard R. Fischer, Daniel Haslinger.
+ *
+ * This file is part of OnionCat.
+ *
+ * OnionCat 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, version 3 of the License.
+ *
+ * OnionCat 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 OnionCat. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+/*! ocatsocks.c
+ * Contains functions for connecting to TOR via SOCKS.
+ *
+ * @author Bernhard Fischer <rahra _at_ cypherpunk at>
+ * @version 2008/02/03-01
+ */
+
+#include "config.h"
+
+#include <stdio.h>
+#include <string.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include <pthread.h>
+#include <arpa/inet.h>
+#include <errno.h>
+#include <sys/time.h>
+#include <sys/select.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <sys/socket.h>
+#include <sys/ioctl.h>
+#ifdef HAVE_LINUX_SOCKIOS_H
+#include <linux/sockios.h>
+#endif
+#ifdef HAVE_NETINET_IN_SYSTM_H
+#include <netinet/in_systm.h>
+#endif
+#ifdef HAVE_NETINET_IP_H
+#include <netinet/ip.h>
+#endif
+
+#include "ocat.h"
+
+
+// SOCKS connector queue vars
+static SocksQueue_t *socks_queue_ = NULL;
+static int socks_connect_cnt_ = 0;
+static int socks_thread_cnt_ = 0;
+static pthread_mutex_t socks_queue_mutex_ = PTHREAD_MUTEX_INITIALIZER;
+static pthread_cond_t socks_queue_cond_ = PTHREAD_COND_INITIALIZER;
+
+
+int socks_connect(const SocksQueue_t *sq)
+{
+ struct sockaddr_in in;
+ int fd, t, len;
+ char buf[FRAME_SIZE], onion[ONION_NAME_SIZE];
+ SocksHdr_t *shdr = (SocksHdr_t*) buf;
+
+ log_debug("called");
+
+ memset(&in, 0, sizeof(in));
+ in.sin_family = AF_INET;
+ in.sin_port = htons(setup.tor_socks_port);
+ in.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
+#ifdef HAVE_SIN_LEN
+ in.sin_len = sizeof(in);
+#endif
+
+ ipv6tonion(&sq->addr, onion);
+ strlcat(onion, ".onion", sizeof(onion));
+
+ log_msg(L_NOTICE, "trying to connect to \"%s\" [%s]", onion, inet_ntop(AF_INET6, &sq->addr, buf, FRAME_SIZE));
+
+ if ((fd = socket(PF_INET, SOCK_STREAM, 0)) < 0)
+ return E_SOCKS_SOCK;
+
+ t = time(NULL);
+ if (connect(fd, (struct sockaddr*) &in, sizeof(in)) == -1)
+ {
+ log_msg(L_ERROR, "connect() to TOR failed: \"%s\"", strerror(errno));
+ oe_close(fd);
+ return E_SOCKS_CONN;
+ }
+
+ log_debug("connected to TOR, doing SOCKS handshake");
+
+ shdr->ver = 4;
+ shdr->cmd = 1;
+ shdr->port = htons(setup.ocat_dest_port);
+ shdr->addr.s_addr = htonl(0x00000001);
+ /*
+ strlcpy(buf + sizeof(SocksHdr_t), usrname_, strlen(usrname_) + 1);
+ strlcpy(buf + sizeof(SocksHdr_t) + strlen(usrname_) + 1, onion, sizeof(onion));
+ */
+ memcpy(buf + sizeof(SocksHdr_t), setup.usrname, strlen(setup.usrname) + 1);
+ memcpy(buf + sizeof(SocksHdr_t) + strlen(setup.usrname) + 1, onion, strlen(onion) + 1);
+ len = sizeof(SocksHdr_t) + strlen(setup.usrname) + strlen(onion) + 2;
+ if (write(fd, shdr, len) != len)
+ // FIXME: there should be some additional error handling
+ log_msg(L_ERROR, "couldn't write %d bytes to SOCKS connection %d", len, fd);
+ log_debug("connect request sent");
+
+ if (read(fd, shdr, sizeof(SocksHdr_t)) < sizeof(SocksHdr_t))
+ {
+ log_msg(L_ERROR | L_FCONN, "short read, closing.");
+ oe_close(fd);
+ return E_SOCKS_REQ;
+ }
+ log_debug("SOCKS response received");
+
+ if (shdr->ver || (shdr->cmd != 90))
+ {
+ log_msg(L_ERROR, "request failed, reason = %d", shdr->cmd);
+ oe_close(fd);
+ return E_SOCKS_RQFAIL;
+ }
+ log_msg(L_NOTICE | L_FCONN, "connection to %s successfully opened on fd %d", onion, fd);
+
+ insert_peer(fd, sq, time(NULL) - t);
+
+ return fd;
+}
+
+
+void socks_queue(const struct in6_addr *addr, int perm)
+{
+ SocksQueue_t *squeue;
+
+ pthread_mutex_lock(&socks_queue_mutex_);
+ for (squeue = socks_queue_; squeue; squeue = squeue->next)
+ //if (!memcmp(&squeue->addr, addr, sizeof(struct in6_addr)))
+ if (IN6_ARE_ADDR_EQUAL(&squeue->addr, addr))
+ break;
+ if (!squeue)
+ {
+ log_debug("queueing new SOCKS connection request");
+ if (!(squeue = calloc(1, sizeof(SocksQueue_t))))
+ log_msg(L_FATAL, "could not get memory for SocksQueue entry: \"%s\"", strerror(errno)), exit(1);
+ memcpy(&squeue->addr, addr, sizeof(struct in6_addr));
+ squeue->perm = perm;
+ squeue->next = socks_queue_;
+ socks_queue_ = squeue;
+ log_debug("signalling connector");
+ pthread_cond_signal(&socks_queue_cond_);
+ }
+ else
+ log_debug("connection already exists, not queueing SOCKS connection");
+ pthread_mutex_unlock(&socks_queue_mutex_);
+}
+
+
+void *socks_connector(void *p)
+{
+ OcatPeer_t *peer;
+ SocksQueue_t **squeue, *sq;
+ int i, rc, ps, run = 1;
+
+ if ((rc = pthread_detach(pthread_self())))
+ log_msg(L_ERROR, "couldn't detach: \"%s\"", rc);
+
+ pthread_mutex_lock(&socks_queue_mutex_);
+ socks_thread_cnt_++;
+ pthread_mutex_unlock(&socks_queue_mutex_);
+
+ while (run)
+ {
+ pthread_mutex_lock(&socks_queue_mutex_);
+ do
+ {
+ pthread_cond_wait(&socks_queue_cond_, &socks_queue_mutex_);
+ for (squeue = &socks_queue_; *squeue; squeue = &(*squeue)->next)
+ if (!(*squeue)->state)
+ break;
+ }
+ while (!(*squeue));
+
+ // spawn spare thread if there is no one left
+ (*squeue)->state = SOCKS_CONNECTING;
+ socks_connect_cnt_++;
+ if (socks_thread_cnt_ <= socks_connect_cnt_)
+ run_ocat_thread("connector", socks_connector, NULL);
+ pthread_mutex_unlock(&socks_queue_mutex_);
+
+ // search for existing peer
+ lock_peers();
+ peer = search_peer(&(*squeue)->addr);
+ unlock_peers();
+
+ // connect via SOCKS if no peer exists
+ if (!peer)
+ for (i = 0, ps = -1; i < SOCKS_MAX_RETRY && ps < 0; i++)
+ ps = socks_connect(*squeue);
+ //ps = socks_connect(&(*squeue)->addr);
+ else
+ log_msg(L_NOTICE, "peer already exists, ignoring");
+
+ // remove request from queue after connect
+ log_debug("removing destination from SOCKS queue");
+ pthread_mutex_lock(&socks_queue_mutex_);
+ sq = *squeue;
+ *squeue = (*squeue)->next;
+ free(sq);
+ socks_connect_cnt_--;
+
+ // if there are more threads then pending connections
+ // terminate thread
+ if (socks_connect_cnt_ < socks_thread_cnt_ - 1)
+ {
+ socks_thread_cnt_--;
+ run = 0;
+ }
+ pthread_mutex_unlock(&socks_queue_mutex_);
+ }
+ return NULL;
+}
+
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-privacy/packages/onioncat.git
More information about the Pkg-privacy-commits
mailing list