Example #1
0
File: main.go Project: kanocz/lcvpn
func rcvrThread(proto string, port int, iface *water.Interface) {
	conn, err := reuseport.NewReusableUDPPortConn(proto, fmt.Sprintf(":%v", port))
	if nil != err {
		log.Fatalln("Unable to get UDP socket:", err)
	}

	buf := make([]byte, BUFFERSIZE)
	for {
		n, _, err := conn.ReadFrom(buf)

		if err != nil {
			fmt.Println("Error: ", err)
			continue
		}

		// ReadFromUDP can return 0 bytes on timeout
		if 0 == n {
			continue
		}

		if n%aes.BlockSize != 0 {
			fmt.Println("packet size ", n, " is not a multiple of the block size")
			continue
		}

		iv := buf[:aes.BlockSize]
		ciphertext := buf[aes.BlockSize:n]

		conf := config.Load().(VPNState)

		mode := cipher.NewCBCDecrypter(conf.Main.block, iv)

		var size int

		if conf.Main.hasalt {

			// if we have alternative key we need store orig packet for second try

			pcopy := make([]byte, n)
			copy(pcopy, buf[:n])

			mode.CryptBlocks(ciphertext, ciphertext)

			size = int(ciphertext[0]) + (256 * int(ciphertext[1]))
			if (n-aes.BlockSize-2)-size > 16 || (n-aes.BlockSize-2)-size < 0 || 4 != ((ciphertext)[2]>>4) {
				// don't looks like anything is ok, trying second key

				copy(buf[:n], pcopy)
				cipher.NewCBCDecrypter(conf.Main.altblock, iv).CryptBlocks(ciphertext, ciphertext)

				size = int(ciphertext[0]) + (256 * int(ciphertext[1]))
				if (n-aes.BlockSize-2)-size > 16 || (n-aes.BlockSize-2)-size < 0 || 4 != ((ciphertext)[2]>>4) {
					fmt.Println("Invalid size field or IPv4 id in decrypted message", size, (n - aes.BlockSize - 2))
					continue
				}
			}

		} else {

			mode.CryptBlocks(ciphertext, ciphertext)

			size = int(ciphertext[0]) + (256 * int(ciphertext[1]))
			if (n-aes.BlockSize-2)-size > 16 || (n-aes.BlockSize-2)-size < 0 {
				fmt.Println("Invalid size field in decrypted message", size, (n - aes.BlockSize - 2))
				continue
			}

			if 4 != ((ciphertext)[2] >> 4) {
				fmt.Println("Non IPv4 packet after decryption, possible corupted packet")
				continue
			}
		}

		iface.Write(ciphertext[2 : 2+size])

	}
}