ADDED:
* cryptpartse.TlsUri now has methods to returned dialed net.Conn and
  tls.Conn, or can use WithConn to add TLS to an already-dialed net.Conn.
This commit is contained in:
brent saner 2024-08-08 19:40:11 -04:00
parent 43d1ddfeb8
commit 77a85a4f84
Signed by: bts
GPG Key ID: 8C004C2F93481F6B
2 changed files with 96 additions and 6 deletions

View File

@ -13,13 +13,14 @@ var (
)

const (
MaxTlsCipher uint16 = tls.TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256
MaxCurveId tls.CurveID = tls.X25519 // 29
MinTlsVer uint16 = tls.VersionSSL30
MaxTlsVer uint16 = tls.VersionTLS13
MaxTlsCipher uint16 = tls.TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256
MaxCurveId tls.CurveID = tls.X25519 // 29
MinTlsVer uint16 = tls.VersionSSL30
MaxTlsVer uint16 = tls.VersionTLS13
DefaultNetType string = "tcp"
)

// TlsUriParam* specifiy URL query parameters to parse a tls:// URI.
// TlsUriParam* specifiy URL query parameters to parse a tls:// URI, and are used by TlsUri methods.
const (
/*
TlsUriParamCa specifies a path to a CA certificate PEM-encded DER file.
@ -110,6 +111,16 @@ const (
Only the first defined instance is parsed.
*/
TlsUriParamMaxTls string = "max_tls"
/*
TlsUriParamNet is used by TlsUri.ToConn and TlsUri.ToTlsConn to explicitly specify a network.

The default is "tcp".

See net.Dial()'s "network" parameter for valid network types.

Only the first defined instance is parsed.
*/
TlsUriParamNet string = "net"
)

var (

View File

@ -3,11 +3,59 @@ package cryptparse
import (
`crypto`
`crypto/tls`
`net`
`net/url`
`os`
`strings`
)

/*
WithConn returns a (crypto/)tls.Conn from an existing/already dialed net.Conn.

underlying should be a "bare" net.Conn; behavior is undefined/unknown if the underlying conn is already a (crypto/)tls.Conn.
*/
func (t *TlsUri) WithConn(underlying net.Conn) (conn *tls.Conn, err error) {

var cfg *tls.Config

if cfg, err = t.ToTlsConfig(); err != nil {
return
}

conn = tls.Client(underlying, cfg)

return
}

/*
ToConn returns a "bare" net.Conn (already dialed) from a TlsUri.

Note that this does NOT include the TLS configured or initialized; use TlsUri.ToTlsConn for that.
(A (crypto/)tls.Conn conforms to net.Conn.)

An error will be returned if no port is explicitly defined in the TlsUri.
*/
func (t *TlsUri) ToConn() (conn net.Conn, err error) {

var ok bool
var params map[string][]string
var netType string = DefaultNetType

params = t.Query()

if params != nil {
if _, ok = params[TlsUriParamNet]; ok {
netType = params[TlsUriParamNet][0]
}
}

if conn, err = net.Dial(netType, t.Host); err != nil {
return
}

return
}

/*
ToTlsConfig returns a *tls.Config from a TlsUri.

@ -22,6 +70,37 @@ func (t *TlsUri) ToTlsConfig() (cfg *tls.Config, err error) {
return
}

/*
ToTlsConn returns a (crypto/)tls.Conn (already dialed) from a TlsUri.

An error will be returned if no port is explicitly defined in the TlsUri.
*/
func (t *TlsUri) ToTlsConn() (conn *tls.Conn, err error) {

var ok bool
var cfg *tls.Config
var params map[string][]string
var netType string = DefaultNetType

if cfg, err = t.ToTlsConfig(); err != nil {
return
}

params = t.Query()

if params != nil {
if _, ok = params[TlsUriParamNet]; ok {
netType = params[TlsUriParamNet][0]
}
}

if conn, err = tls.Dial(netType, t.Host, cfg); err != nil {
return
}

return
}

// ToTlsFlat returns a *TlsFlat from a TlsUri.
func (t *TlsUri) ToTlsFlat() (tlsFlat *TlsFlat, err error) {

@ -146,7 +225,7 @@ func (t *TlsUri) ToTlsFlat() (tlsFlat *TlsFlat, err error) {
return
}

// ToURL returns the *url.URL representation of a TlsUri.
// ToURL returns the *url.URL representation of a TlsUri. Note that the params will remain, so remove them explicitly if needed.
func (t *TlsUri) ToURL() (u *url.URL) {

if t == nil {