Documentation ¶
Overview ¶
Package vpn contains the API to create an OpenVPN client that can connect to a remote OpenVPN endpoint and provide you with a tunnel where to send packets.
The recommended way to use this package is to use the dialer methods.
Index ¶
- Constants
- Variables
- func NewClientFromOptions(opt *Options) vpnClient
- type Client
- func (c *Client) Close() error
- func (c *Client) Dial(ctx context.Context) (net.Conn, error)
- func (c *Client) LocalAddr() net.Addr
- func (c *Client) Read(b []byte) (int, error)
- func (c *Client) RemoteAddr() net.Addr
- func (c *Client) SetDeadline(t time.Time) error
- func (c *Client) SetReadDeadline(t time.Time) error
- func (c *Client) SetWriteDeadline(t time.Time) error
- func (c *Client) Start(ctx context.Context) error
- func (c *Client) Write(b []byte) (int, error)
- type DialContextFn
- type DialerContext
- type Logger
- type Options
- type RawDialer
- type TLSConn
- func (t *TLSConn) Close() error
- func (t *TLSConn) LocalAddr() net.Addr
- func (t *TLSConn) Read(b []byte) (int, error)
- func (t *TLSConn) RemoteAddr() net.Addr
- func (t *TLSConn) SetDeadline(tt time.Time) error
- func (t *TLSConn) SetReadDeadline(tt time.Time) error
- func (t *TLSConn) SetWriteDeadline(tt time.Time) error
- func (t *TLSConn) Write(b []byte) (int, error)
- type TLSModeTransporter
- type TunDialer
- Bugs
Constants ¶
const ( UDPMode = iota TCPMode )
Variables ¶
var ( // ErrDialError is a generic error while dialing ErrDialError = errors.New("dial error") // ErrAlreadyStarted is returned when trying to start the tunnel more than once ErrAlreadyStarted = errors.New("tunnel already started") )
var ( ErrBadHandshake = errors.New("bad vpn handshake") ErrBadDataHandshake = errors.New("bad data handshake") )
var ( // ErrBadTLSHandshake is returned when the OpenVPN handshake failed. ErrBadTLSHandshake = errors.New("handshake failure") // ErrBadCA is returned when the CA file cannot be found or is not valid. ErrBadCA = errors.New("bad ca conf") // ErrBadKeypair is returned when the key or cert file cannot be found or is not valid. ErrBadKeypair = errors.New("bad keypair conf") // ErrBadParrot is returned for errors during TLS parroting ErrBadParrot = errors.New("cannot parrot") // ErrCannotVerifyCertChain is returned for certificate chain validation errors. ErrCannotVerifyCertChain = errors.New("cannot verify chain") )
var ( // ErrBadConnNetwork indicates that the conn's network is neither TCP nor UDP. ErrBadConnNetwork = errors.New("bad conn.Network value") // ErrPacketTooShort indicates that a packet is too short. ErrPacketTooShort = errors.New("packet too short") )
Functions ¶
func NewClientFromOptions ¶
func NewClientFromOptions(opt *Options) vpnClient
NewClientFromOptions returns a Client configured with the given Options.
Types ¶
type Client ¶
type Client struct { Opts *Options Dialer DialerContext Log Logger // contains filtered or unexported fields }
Client implements the OpenVPN protocol. If you're just interested in writing to and reading from the tunnel you should use the dialer methods instead. This type is only intended to be instantiated by users that need a finer control of the protocol steps (i.e., you want to be sure that you are only calling the handshake, etc.)
func (*Client) Dial ¶
Dial opens a TCP/UDP socket against the remote, and creates an internal data channel. It is the second step in an OpenVPN connection (out of five). (In UDP mode no network connection is done at this step).
func (*Client) RemoteAddr ¶
TODO(ainghazal): should get the remote _tunnel_ ip addr somehow
type DialerContext ¶
DialerContext is anything that features a net.Dialer-like DialContext method.
type Logger ¶
type Logger interface { // Debug emits a debug message. Debug(msg string) // Debugf formats and emits a debug message. Debugf(format string, v ...interface{}) // Info emits an informational message. Info(msg string) // Infof formats and emits an informational message. Infof(format string, v ...interface{}) // Warn emits a warning message. Warn(msg string) // Warnf formats and emits a warning message. Warnf(format string, v ...interface{}) // Error emits an error message Error(msg string) // Errorf formats and emits an error message. Errorf(format string, v ...interface{}) }
Logger is compatible with github.com/apex/log
type Options ¶
type Options struct { Remote string Port string Proto int Username string Password string Ca string Cert string Key string Compress compression Cipher string Auth string TLSMaxVer string // below are options that do not conform to the OpenVPN configuration format. ProxyOBFS4 string Log Logger }
Options make all the relevant configuration options accessible to the different modules that need it.
func ParseConfigFile ¶
ParseConfigFile expects a path to a valid config file and returns an Option object after parsing the file.
type RawDialer ¶
type RawDialer struct { Options *Options // contains filtered or unexported fields }
func NewRawDialer ¶
NewRawDialer returns a new *RawDialer constructed from the passed options.
type TLSConn ¶
type TLSConn struct {
// contains filtered or unexported fields
}
TLSConn implements net.Conn, and is passed to the tls.Client to perform a TLS Handshake over OpenVPN control packets.
func NewTLSConn ¶
NewTLSConn returns a TLSConn. It requires the on-the-wire net.Conn that will be used underneath, and a configured session. It returns also an error if the operation cannot be completed.
func (*TLSConn) Read ¶
Read over the control channel. This method implements the reliability layer: it retries reads until the _next_ packet is received (according to the packetID). Returns also an error if the operation cannot be completed.
func (*TLSConn) RemoteAddr ¶
type TLSModeTransporter ¶
type TLSModeTransporter interface { // ReadPacket reads an OpenVPN packet from the wire. ReadPacket() (p *packet, err error) // WritePacket writes an OpenVPN packet to the wire. WritePacket(opcodeKeyID uint8, data []byte) error // SetDeadline sets the underlying conn's deadline. SetDeadline(deadline time.Time) error // SetReadDeadline sets the underlying conn's read deadline. SetReadDeadline(deadline time.Time) error // SetWriteDeadline sets the underlying conn's write deadline. SetWriteDeadline(deadline time.Time) error // Close closes the underlying conn. Close() error // LocalAddr returns the underlying conn's local addr. LocalAddr() net.Addr // RemoteAddr returns the underlying conn's remote addr. RemoteAddr() net.Addr }
TLSModeTransporter is a transport for OpenVPN in TLS mode.
See https://openvpn.net/community-resources/openvpn-protocol/ for documentation on the protocol used by OpenVPN on the wire.
func NewTLSModeTransport ¶
func NewTLSModeTransport(conn net.Conn, s *session) (TLSModeTransporter, error)
NewTLSModeTransport creates a new TLSModeTransporter using the given net.Conn.
type TunDialer ¶
type TunDialer struct { Dialer DialerContext // contains filtered or unexported fields }
A TunDialer contains options for obtaining a network connection tunneled through an OpenVPN endpoint. It uses a userspace gVisor virtual device over the raw VPN tunnel.
func NewTunDialer ¶
NewTunDialer creates a new Dialer with the default nameservers (OpenDNS).
func NewTunDialerFromOptions ¶
NewDialerFromOptions creates a new Dialer directly from an Options object.
func NewTunDialerWithNameservers ¶
NewDialerWithNameservers creates a new Dialer with the passed nameservers. You probably want to pass the nameservers for your own VPN service here.
func (TunDialer) Dial ¶
Dial connects to the address on the named network, via the OpenVPN endpoint that is configured in the dialer.
The return value implements the net.Conn interface, but it is a socket created on a virtual device, using gVisor userspace network stack. This means that the kernel only sees UDP packets with an encrypted payload.
The addresses are resolved via the OpenVPN tunnel too, and against the nameservers configured in the dialer. This feature uses wireguard's little custom DNS client implementation.
Known networks are "tcp", "tcp4" (IPv4-only), "tcp6" (IPv6-only), "udp", "udp4" (IPv4-only), "udp6" (IPv6-only), "ping4", "ping6".
func (TunDialer) DialContext ¶
DialContext connects to the address on the named network using the provided context.
Notes ¶
Bugs ¶
we cannot use the tun-mtu that the remote advertises, so we subtract a "safety" margin for now.