Example #1
0
func tcpLoop() {
	listener, err := net.ListenTCP("tcp", transThis)
	if err != nil {
		kilog.Critical("%v", err.Error())
		os.Exit(-1)
	}
	for {
		clnt, err := listener.AcceptTCP()
		if err != nil {
			kilog.Critical("%v", err.Error())
			os.Exit(-1)
		}
		go func() {
			defer clnt.Close()
			defer clnt.CloseRead()
			defer clnt.CloseWrite()

			lol, err := clnt.File()
			if err != nil {
				panic(err.Error())
			}
			haha := C.getdestaddr_iptables(C.int(lol.Fd()))
			lol.Close()

			sdf := make([]byte, 4)
			binary.LittleEndian.PutUint32(sdf, uint32(haha.sin_addr.s_addr))

			port := binary.BigEndian.Uint16((*[2]byte)(unsafe.Pointer(&haha.sin_port))[:])

			rmAddr := &net.TCPAddr{sdf, int(port), ""}
			dnsLock.Lock()
			rmName, ok := ipToName[rmAddr.IP.String()]
			dnsLock.Unlock()
			var rmConn io.ReadWriteCloser
			// see if we should connect IP or name
			if !ok {
				kilog.Warning("unmapped IP received (%v), misconfig?", rmAddr)
				rmConn, err = socksConnectIP(socksNext, rmAddr)
			} else {
				kilog.Debug("mapped IP received (%v -> %v)", rmAddr, rmName)
				rmConn, err = socksConnectName(socksNext, rmName, rmAddr.Port)
			}
			if err != nil {
				kilog.Debug("%v", err)
				return
			}
			defer rmConn.Close()
			go func() {
				defer rmConn.Close()
				defer clnt.Close()
				defer clnt.CloseRead()
				defer clnt.CloseWrite()
				io.Copy(rmConn, clnt)
			}()
			io.Copy(clnt, rmConn)
			kilog.Debug("closing client")
		}()
	}
}
func NewSCServer(addr string) SCServer {
	listener, err := net.Listen("tcp", addr)

	if err != nil {
		panic(err.Error())
	}
	killer := make(chan bool)
	go func() {
		for {
			select {
			case <-killer:
				listener.Close()
				return
			default:
				// establish connection
				client, err := listener.Accept()
				//log.Debug("Of acceptings client: %s", client.RemoteAddr())
				if err != nil {
					kilog.Critical(err.Error())
					client.Close()
					continue
				}
				go func() {
					err := sc_server_handler(client)
					if err != nil {
						//log.Error(err.Error())
					}
				}()
			}
		}
	}()
	return SCServer{listener, killer}
}
func reorder_messages(input, output chan sc_message) {
	defer close(output)
	ptr := uint64(0)
	buffer := make(map[uint64]sc_message)
	for {
		thing, ok := <-input
		if !ok {
			return
		}
		buffer[thing.seqnum] = thing
		if len(buffer) > 4096 {
			kilog.Critical("reorder_messages buffer blown")
			return
		}
		for {
			thing, ok := buffer[ptr]
			if !ok {
				break
			}
			delete(buffer, ptr)
			output <- thing
			ptr++
		}
	}
}
Example #4
0
func dnsDispatch() {
	udpConn, err := net.ListenUDP("udp", dnsThis)
	if err != nil {
		kilog.Critical("%v", err.Error())
		os.Exit(-1)
	}

	// hack to make Windows happy
	nameToIP["dns.msftncsi.com."] = "131.107.255.255"

	dns.ActivateAndServe(nil, udpConn, dns.HandlerFunc(dnsHandle))
}
Example #5
0
func startSocks() {
	listener, err := net.Listen("tcp", fmt.Sprintf("0.0.0.0:%v", socksPort))
	if err != nil {
		kilog.Critical("failed to bind SOCKS5 listener: %v", err.Error())
		os.Exit(-1)
	}
	go func() {
		for {
			clnt, err := listener.Accept()
			if err != nil {
				continue
			}
			go handleSocks(clnt)
		}
	}()
	kilog.Info("SOCKS5 listener successfully bound at %v", listener.Addr())
}
Example #6
0
func startControl() {
	ctlState.prt2prv = make(map[int]natrium.EdDSAPrivate)
	ctlState.prt2lst = make(map[int]*kiricom.EasyListener)
	listener, err := net.Listen("tcp", "127.0.0.1:12377")
	if err != nil {
		kilog.Critical(err.Error())
		os.Exit(-1)
	}
	go func() {
		for {
			incoming, err := listener.Accept()
			if err != nil {
				continue
			}
			go handleControl(incoming)
		}
	}()
}
Example #7
0
func handleControl(clnt io.ReadWriteCloser) {
	defer clnt.Close()
	greeting := ctlGreeting{0xCACACACA, ctlVersion{0, 0, 0}, socksPort} // 0.0.0 means unnumbered version
	err := struc.Pack(clnt, &greeting)
	if err != nil {
		kilog.Debug("unable to write control greeting: %v", err.Error())
		return
	}
	var command ctlCommand
	err = struc.Unpack(clnt, &command)
	if err != nil {
		kilog.Debug("unable to read control command: %v", err.Error())
		return
	}

	var response ctlResponse
	defer struc.Pack(clnt, &response)

	// do the actual work
	switch command.Verb {
	case ctlCmdNOOP:
		return
	case ctlCmdHOST:
		kilog.Debug("received control request to forward port %v to %v, with %v",
			command.IntPort, command.ExtPort, command.PrivKey)
		ctlState.RLock()
		_, ok := ctlState.prt2prv[command.ExtPort]
		ctlState.RUnlock()
		if ok {
			kilog.Debug("port %v already occupied, refusing request!", command.ExtPort)
			response.Verb = ctlRespNOPE
			response.Name = "port already occupied"
			return
		}
		ctlState.Lock()
		defer ctlState.Unlock()
		newlistnr, err := kiricom.EasyListen(fmt.Sprintf("0.0.0.0:%v", command.ExtPort), command.PrivKey,
			command.PrivKey.PublicKey())
		kilog.Debug("startControl secret is %x", command.PrivKey.PublicKey())
		if err != nil {
			kilog.Debug("could not create ICOM listener")
			response.Verb = ctlRespNOPE
			response.Name = err.Error()
			return
		}
		ctlState.prt2lst[command.ExtPort] = newlistnr
		ctlState.prt2prv[command.ExtPort] = command.PrivKey
		response.Verb = ctlRespOKAY
		pubip, err := getPublicIP()
		if err != nil {
			kilog.Critical("computer does not seem to have an Internet connection; dying!")
			os.Exit(-1)
		}
		response.Name = sagiriNames.EdgeID{command.PrivKey.PublicKey(), pubip,
			uint16(command.ExtPort)}.String()

		groop, err := newServGroup(command.PrivKey)
		if err != nil {
			kilog.Debug("host: could not start servGroup %v", err.Error())
			return
		}

		// time to spin off threads to forward the connections
		handle := func(clnt io.ReadWriteCloser) {
			defer clnt.Close()
			fwd, err := net.Dial("tcp", fmt.Sprintf("127.0.0.1:%v", command.IntPort))
			if err != nil {
				kilog.Debug("host: could not forward %v", err.Error())
				return
			}
			kilog.Debug("host: completed forwarding")
			defer fwd.Close()
			go func() {
				defer fwd.Close()
				defer clnt.Close()
				io.Copy(fwd, clnt)
			}()
			io.Copy(clnt, fwd)
		}

		go func() {
			defer newlistnr.Close()
			defer groop.Destroy()
			for {
				clnt, err := newlistnr.Accept()
				if err != nil {
					kilog.Debug("host: direct error %v", err.Error())
					return
				}
				go handle(clnt)
			}
		}()

		go func() {
			defer groop.Destroy()
			defer newlistnr.Close()
		REDO:
			for {
				clnt, err := groop.Accept()
				if err != nil {
					kilog.Debug("host: onion error %v", err.Error())
					groop.Destroy()
					groop, err = newServGroup(command.PrivKey)
					if err != nil {
						kilog.Debug(err.Error())
						time.Sleep(time.Second)
					}
					goto REDO
				}
				go handle(clnt)
			}
		}()
	case ctlCmdSTOP:
		ctlState.Lock()
		defer ctlState.Unlock()
		_, ok := ctlState.prt2lst[command.ExtPort]
		if !ok {
			response.Verb = ctlRespNOPE
			response.Name = "no service with the given port"
			return
		}
		rlPriv := ctlState.prt2prv[command.ExtPort]
		if subtle.ConstantTimeCompare(rlPriv, command.PrivKey) != 1 {
			response.Verb = ctlRespNOPE
			response.Name = "given private key incorrect, refusing to remove"
			return
		}
		delete(ctlState.prt2prv, command.ExtPort)
		ctlState.prt2lst[command.ExtPort].Close()
		response.Verb = ctlRespOKAY
	}
}
func main() {
	rand.Seed(time.Now().UnixNano())
	go run_monitor_loop()
	flag.Parse()
	if *confloc == "" {
		kilog.Warning("No configuration file given, using defaults")
	} else {
		err := gcfg.ReadFileInto(&MasterConfig, *confloc)
		if err != nil {
			kilog.Warning("Configuration file broken, using defaults")
		}
	}
	if *singhop {
		MasterConfig.Network.MinCircuitLen = 1
	}
	kilog.Info("Kirisurf %s started! mkh=%s", version, MasterKeyHash)
	set_gui_progress(0.1)
	kilog.Info("Bootstrapping 10%%: finding directory address...")
	dirclient.DIRADDR, _ = dirclient.FindDirectoryURL()
	set_gui_progress(0.2)
	kilog.Info("Bootstrapping 20%%: found directory address, refreshing directory...")
	err := dirclient.RefreshDirectory()
	if err != nil {
		kilog.Critical("Stuck at 20%%: directory connection error %s", err.Error())
		for {
			time.Sleep(time.Second)
		}
	}
	set_gui_progress(0.3)
	kilog.Info("Bootstrapping 30%%: directory refreshed, beginning to build circuits...")
	go run_diagnostic_loop()
	dirclient.RefreshDirectory()
	if MasterConfig.General.Role == "server" {
		NewSCServer(MasterConfig.General.ORAddr)
		addr := RegisterNGSCServer(MasterConfig.General.ORAddr)
		prt, _ := strconv.Atoi(
			strings.Split(MasterConfig.General.ORAddr, ":")[1])
		go func() {
			err := UPnPForwardAddr(MasterConfig.General.ORAddr)
			err = UPnPForwardAddr(addr)
			if err != nil {
				kilog.Warning("UPnP failed: %s", err)
				if MasterConfig.Network.OverrideUPnP {
					go dirclient.RunRelay(prt, MasterKeyHash,
						MasterConfig.General.IsExit)
				}
				return
			}
			kilog.Info("UPnP successfully forwarded port")
			go dirclient.RunRelay(prt, MasterKeyHash,
				MasterConfig.General.IsExit)
		}()
		kilog.Info("Started server!")
		if *noclient {
			for {
				time.Sleep(time.Second)
			}
		}
	}
	run_client_loop()
	kilog.Info("Kirisurf exited")
}
Example #9
0
func main() {
	kilog.Info("DANASI 0.1 starting...")
	var _dnsThis string
	var _dnsNext string
	flag.StringVar(&_dnsThis, "dnsThis", "127.0.0.1:53535", "address on which to listen for DNS")
	flag.StringVar(&_dnsNext, "dnsNext", "8.8.8.8:53", "address to which unrelated requests are forwarded")

	var _transThis string
	var _socksNext string
	flag.StringVar(&_transThis, "transThis", "127.0.0.1:12377", "address to which TCP connections in the IP range should be forwarded")
	flag.StringVar(&_socksNext, "socksNext", "127.0.0.1:2377", "SOCKS5 proxy with which matching names are dialed upon")

	var _ipRange string
	flag.StringVar(&_ipRange, "ipRange", "100.64.0.0/10", "IP range from which addresses are allocated")

	var _namePattern string
	flag.StringVar(&_namePattern, "namePattern", ".*", "regexp (POSIX) matching DNS names to be intercepted")
	flag.Parse()
	kilog.Debug("flags read:")
	kilog.Debug("    dnsThis = %v", _dnsThis)
	kilog.Debug("    dnsNext = %v", _dnsNext)
	kilog.Debug("    transThis = %v", _transThis)
	kilog.Debug("    socksNext = %v", _socksNext)
	kilog.Debug("    ipRange = %v", _ipRange)
	kilog.Debug("    namePattern = %v", _namePattern)

	var err error

	// validate the command-line arguments
	dnsThis, err = net.ResolveUDPAddr("udp", _dnsThis)
	if err != nil {
		kilog.Critical("*** malformed dnsThis: %v ***", err.Error())
		os.Exit(-1)
	}
	dnsNext, err = net.ResolveUDPAddr("udp", _dnsNext)
	if err != nil {
		kilog.Critical("*** malformed dnsNext: %v ***", err.Error())
		os.Exit(-1)
	}

	transThis, err = net.ResolveTCPAddr("tcp", _transThis)
	if err != nil {
		kilog.Critical("*** malformed transThis: %v ***", err.Error())
		os.Exit(-1)
	}
	socksNext, err = net.ResolveTCPAddr("tcp", _socksNext)
	if err != nil {
		kilog.Critical("*** malformed socksNext: %v ***", err.Error())
		os.Exit(-1)
	}

	_, ipRange, err = net.ParseCIDR(_ipRange)
	if err != nil {
		kilog.Critical("*** malformed ipRange: %v ***", err.Error())
		os.Exit(-1)
	}

	namePattern, err = regexp.CompilePOSIX(_namePattern)
	if err != nil {
		kilog.Critical("*** malformed namePattern: %v ***", err.Error())
		os.Exit(-1)
	}

	go dnsDispatch()
	tcpLoop()
}