[tor-commits] [websocket/master] Add dummy server example.

dcf at torproject.org dcf at torproject.org
Sun Oct 27 00:20:48 UTC 2013


commit 2933979a66bd70809a12a1137cfa9e109fc27914
Author: David Fifield <david at bamsoftware.com>
Date:   Sat Oct 26 17:01:54 2013 -0700

    Add dummy server example.
---
 src/pt/.gitignore                            |    1 +
 src/pt/examples/dummy-server/dummy-server.go |  121 ++++++++++++++++++++++++++
 2 files changed, 122 insertions(+)

diff --git a/src/pt/.gitignore b/src/pt/.gitignore
index bdcad5a..beb9ac5 100644
--- a/src/pt/.gitignore
+++ b/src/pt/.gitignore
@@ -1 +1,2 @@
 /examples/dummy-client
+/examples/dummy-server
diff --git a/src/pt/examples/dummy-server/dummy-server.go b/src/pt/examples/dummy-server/dummy-server.go
new file mode 100644
index 0000000..26314d0
--- /dev/null
+++ b/src/pt/examples/dummy-server/dummy-server.go
@@ -0,0 +1,121 @@
+// Usage (in torrc):
+//   BridgeRelay 1
+//   ORPort 9001
+//   ExtORPort 6669
+//   ServerTransportPlugin dummy exec dummy-server
+
+package main
+
+import (
+	"io"
+	"net"
+	"os"
+	"os/signal"
+	"sync"
+	"syscall"
+)
+
+import "git.torproject.org/pluggable-transports/websocket.git/src/pt"
+
+var ptInfo pt.ServerInfo
+
+// When a connection handler starts, +1 is written to this channel; when it
+// ends, -1 is written.
+var handlerChan = make(chan int)
+
+func copyLoop(a, b net.Conn) {
+	var wg sync.WaitGroup
+	wg.Add(2)
+
+	go func() {
+		io.Copy(b, a)
+		wg.Done()
+	}()
+	go func() {
+		io.Copy(a, b)
+		wg.Done()
+	}()
+
+	wg.Wait()
+}
+
+func handleConnection(conn net.Conn) {
+	handlerChan <- 1
+	defer func() {
+		handlerChan <- -1
+	}()
+
+	or, err := pt.ConnectOr(&ptInfo, conn, "dummy")
+	if err != nil {
+		return
+	}
+	copyLoop(conn, or)
+}
+
+func acceptLoop(ln net.Listener) error {
+	for {
+		conn, err := ln.Accept()
+		if err != nil {
+			return err
+		}
+		go handleConnection(conn)
+	}
+	return nil
+}
+
+func startListener(addr *net.TCPAddr) (net.Listener, error) {
+	ln, err := net.ListenTCP("tcp", addr)
+	if err != nil {
+		return nil, err
+	}
+	go acceptLoop(ln)
+	return ln, nil
+}
+
+func main() {
+	ptInfo = pt.ServerSetup([]string{"dummy"})
+
+	listeners := make([]net.Listener, 0)
+	for _, bindAddr := range ptInfo.BindAddrs {
+		ln, err := startListener(bindAddr.Addr)
+		if err != nil {
+			pt.SmethodError(bindAddr.MethodName, err.Error())
+			continue
+		}
+		pt.Smethod(bindAddr.MethodName, ln.Addr())
+		listeners = append(listeners, ln)
+	}
+	pt.SmethodsDone()
+
+	var numHandlers int = 0
+	var sig os.Signal
+	sigChan := make(chan os.Signal, 1)
+	signal.Notify(sigChan, syscall.SIGINT, syscall.SIGTERM)
+
+	// wait for first signal
+	sig = nil
+	for sig == nil {
+		select {
+		case n := <-handlerChan:
+			numHandlers += n
+		case sig = <-sigChan:
+		}
+	}
+	for _, ln := range listeners {
+		ln.Close()
+	}
+
+	if sig == syscall.SIGTERM {
+		return
+	}
+
+	// wait for second signal or no more handlers
+	sig = nil
+	for sig == nil && numHandlers != 0 {
+		select {
+		case n := <-handlerChan:
+			numHandlers += n
+		case sig = <-sigChan:
+		}
+	}
+}



More information about the tor-commits mailing list