From a22ae2d4e9378b8e9bbf0eb79c21631cf9413f3a Mon Sep 17 00:00:00 2001 From: Boshi Lian Date: Sun, 10 Sep 2023 00:49:42 -0700 Subject: [PATCH] import new ssh crypto (#220) --- cmd/sshpiperd/daemon.go | 19 +++++++ cmd/sshpiperd/key.go | 112 ---------------------------------------- crypto | 2 +- go.mod | 8 +-- go.sum | 12 ++--- 5 files changed, 30 insertions(+), 123 deletions(-) delete mode 100644 cmd/sshpiperd/key.go diff --git a/cmd/sshpiperd/daemon.go b/cmd/sshpiperd/daemon.go index f8585e74..4cb81c2f 100644 --- a/cmd/sshpiperd/daemon.go +++ b/cmd/sshpiperd/daemon.go @@ -1,7 +1,10 @@ package main import ( + "crypto/ed25519" + "crypto/rand" "encoding/base64" + "encoding/pem" "fmt" "net" "os" @@ -24,6 +27,22 @@ type daemon struct { filterHostkeysReqeust bool } +func generateSshKey(keyfile string) error { + _, privateKey, err := ed25519.GenerateKey(rand.Reader) + if err != nil { + return err + } + + privateKeyPEM, err := ssh.MarshalPrivateKey(privateKey, "") + if err != nil { + return err + } + + privateKeyBytes := pem.EncodeToMemory(privateKeyPEM) + + return os.WriteFile(keyfile, privateKeyBytes, 0600) +} + func newDaemon(ctx *cli.Context) (*daemon, error) { config := &plugin.GrpcPluginConfig{} config.SetDefaults() diff --git a/cmd/sshpiperd/key.go b/cmd/sshpiperd/key.go deleted file mode 100644 index d1f50cc5..00000000 --- a/cmd/sshpiperd/key.go +++ /dev/null @@ -1,112 +0,0 @@ -package main - -import ( - "crypto/ed25519" - crand "crypto/rand" - "encoding/pem" - "math/rand" - "os" - - "golang.org/x/crypto/ssh" -) - -func generateSshKey(keyfile string) error { - _, privateKey, err := ed25519.GenerateKey(crand.Reader) - if err != nil { - return err - } - - privateKeyPEM := &pem.Block{ - Type: "OPENSSH PRIVATE KEY", - Bytes: marshalED25519PrivateKey(privateKey), - } - - privateKeyBytes := pem.EncodeToMemory(privateKeyPEM) - - return os.WriteFile(keyfile, privateKeyBytes, 0600) -} - -// copy from https://github.com/mikesmitty/edkey/blob/master/edkey.go - -/* - Writes ed25519 private keys into the new OpenSSH private key format. - -I have no idea why this isn't implemented anywhere yet, you can do seemingly -everything except write it to disk in the OpenSSH private key format. -*/ -func marshalED25519PrivateKey(key ed25519.PrivateKey) []byte { - // Add our key header (followed by a null byte) - magic := append([]byte("openssh-key-v1"), 0) - - var w struct { - CipherName string - KdfName string - KdfOpts string - NumKeys uint32 - PubKey []byte - PrivKeyBlock []byte - } - - // Fill out the private key fields - pk1 := struct { - Check1 uint32 - Check2 uint32 - Keytype string - Pub []byte - Priv []byte - Comment string - Pad []byte `ssh:"rest"` - }{} - - // Set our check ints - ci := rand.Uint32() - pk1.Check1 = ci - pk1.Check2 = ci - - // Set our key type - pk1.Keytype = ssh.KeyAlgoED25519 - - // Add the pubkey to the optionally-encrypted block - pk, ok := key.Public().(ed25519.PublicKey) - if !ok { - //fmt.Fprintln(os.Stderr, "ed25519.PublicKey type assertion failed on an ed25519 public key. This should never ever happen.") - return nil - } - pubKey := []byte(pk) - pk1.Pub = pubKey - - // Add our private key - pk1.Priv = []byte(key) - - // Might be useful to put something in here at some point - pk1.Comment = "" - - // Add some padding to match the encryption block size within PrivKeyBlock (without Pad field) - // 8 doesn't match the documentation, but that's what ssh-keygen uses for unencrypted keys. *shrug* - bs := 8 - blockLen := len(ssh.Marshal(pk1)) - padLen := (bs - (blockLen % bs)) % bs - pk1.Pad = make([]byte, padLen) - - // Padding is a sequence of bytes like: 1, 2, 3... - for i := 0; i < padLen; i++ { - pk1.Pad[i] = byte(i + 1) - } - - // Generate the pubkey prefix "\0\0\0\nssh-ed25519\0\0\0 " - prefix := []byte{0x0, 0x0, 0x0, 0x0b} - prefix = append(prefix, []byte(ssh.KeyAlgoED25519)...) - prefix = append(prefix, []byte{0x0, 0x0, 0x0, 0x20}...) - - // Only going to support unencrypted keys for now - w.CipherName = "none" - w.KdfName = "none" - w.KdfOpts = "" - w.NumKeys = 1 - w.PubKey = append(prefix, pubKey...) - w.PrivKeyBlock = ssh.Marshal(pk1) - - magic = append(magic, ssh.Marshal(w)...) - - return magic -} diff --git a/crypto b/crypto index 527d43d0..a82ddfcf 160000 --- a/crypto +++ b/crypto @@ -1 +1 @@ -Subproject commit 527d43d0ff08eef922fccc76c03fbd571071cf5a +Subproject commit a82ddfcf53beef5e78e1a395d4dc8ec3b2816d20 diff --git a/go.mod b/go.mod index 5cafd2ed..e4143391 100644 --- a/go.mod +++ b/go.mod @@ -19,7 +19,7 @@ require ( github.com/tg123/jobobject v0.1.0 github.com/tg123/remotesigner v0.0.1 github.com/urfave/cli/v2 v2.25.7 - golang.org/x/crypto v0.12.0 + golang.org/x/crypto v0.13.0 google.golang.org/grpc v1.57.0 google.golang.org/protobuf v1.31.0 gopkg.in/yaml.v3 v3.0.1 @@ -92,9 +92,9 @@ require ( golang.org/x/mod v0.10.0 // indirect golang.org/x/net v0.14.0 // indirect golang.org/x/oauth2 v0.8.0 // indirect - golang.org/x/sys v0.11.0 // indirect - golang.org/x/term v0.11.0 - golang.org/x/text v0.12.0 // indirect + golang.org/x/sys v0.12.0 // indirect + golang.org/x/term v0.12.0 + golang.org/x/text v0.13.0 // indirect golang.org/x/time v0.3.0 // indirect golang.org/x/tools v0.8.0 // indirect google.golang.org/appengine v1.6.7 // indirect diff --git a/go.sum b/go.sum index dfecbedb..1f9b242c 100644 --- a/go.sum +++ b/go.sum @@ -226,21 +226,21 @@ golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBc golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.11.0 h1:eG7RXZHdqOJ1i+0lgLgCpSXAp6M3LYlAo6osgSi0xOM= -golang.org/x/sys v0.11.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.12.0 h1:CM0HF96J0hcLAwsHPJZjfdNzs0gftsLfgKt57wWHJ0o= +golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo= -golang.org/x/term v0.11.0 h1:F9tnn/DA/Im8nCwm+fX+1/eBwi4qFjRT++MhtVC4ZX0= -golang.org/x/term v0.11.0/go.mod h1:zC9APTIj3jG3FdV/Ons+XE1riIZXG4aZ4GTHiPZJPIU= +golang.org/x/term v0.12.0 h1:/ZfYdc3zq+q02Rv9vGqTeSItdzZTSNDmfTi0mBAuidU= +golang.org/x/term v0.12.0/go.mod h1:owVbMEjm3cBLCHdkQu9b1opXd4ETQWc3BhuQGKgXgvU= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= -golang.org/x/text v0.12.0 h1:k+n5B8goJNdU7hSvEtMUz3d1Q6D/XW4COJSJR6fN0mc= -golang.org/x/text v0.12.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= +golang.org/x/text v0.13.0 h1:ablQoSUd0tRdKxZewP80B+BaqeKJuVhuRxj/dkrun3k= +golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/time v0.3.0 h1:rg5rLMjNzMS1RkNLzCG38eapWhnYLFYXDXj2gOlr8j4= golang.org/x/time v0.3.0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=