From 5b453e6305ab962b6fb1c9a38ccb262e91034ce8 Mon Sep 17 00:00:00 2001 From: Sam Alba Date: Sun, 24 May 2015 23:59:02 -0700 Subject: [PATCH 1/4] Implemented '--tls-san' global arg for adding extra SANs (subject alt names) to server-side certificates Signed-off-by: Sam Alba --- cmd/machine.go | 6 ++++++ commands/create.go | 1 + libmachine/auth/auth.go | 2 +- libmachine/provision/utils.go | 7 +++++-- 4 files changed, 13 insertions(+), 3 deletions(-) diff --git a/cmd/machine.go b/cmd/machine.go index c4c24d5b95..b080066c86 100644 --- a/cmd/machine.go +++ b/cmd/machine.go @@ -133,6 +133,12 @@ func main() { Usage: "Token to use for requests to the Github API", Value: "", }, + cli.StringSliceFlag{ + EnvVar: "MACHINE_TLS_SAN", + Name: "tls-san", + Usage: "Support extra SANs for TLS certs", + Value: &cli.StringSlice{}, + }, cli.BoolFlag{ EnvVar: "MACHINE_NATIVE_SSH", Name: "native-ssh", diff --git a/commands/create.go b/commands/create.go index 4b13bfc384..f56eae019a 100644 --- a/commands/create.go +++ b/commands/create.go @@ -178,6 +178,7 @@ func cmdCreateInner(c CommandLine) error { ServerCertPath: filepath.Join(mcndirs.GetMachineDir(), name, "server.pem"), ServerKeyPath: filepath.Join(mcndirs.GetMachineDir(), name, "server-key.pem"), StorePath: filepath.Join(mcndirs.GetMachineDir(), name), + ServerCertSANs: c.GlobalStringSlice("tls-san"), }, EngineOptions: &engine.Options{ ArbitraryFlags: c.StringSlice("engine-opt"), diff --git a/libmachine/auth/auth.go b/libmachine/auth/auth.go index b375e9eee3..86ae79d232 100644 --- a/libmachine/auth/auth.go +++ b/libmachine/auth/auth.go @@ -11,7 +11,7 @@ type Options struct { ServerCertRemotePath string ServerKeyRemotePath string ClientCertPath string - + ServerCertSANs []string // StorePath is left in for historical reasons, but not really meant to // be used directly. StorePath string diff --git a/libmachine/provision/utils.go b/libmachine/provision/utils.go index 2595d6f771..1119d5267c 100644 --- a/libmachine/provision/utils.go +++ b/libmachine/provision/utils.go @@ -85,17 +85,20 @@ func ConfigureAuth(p Provisioner) error { return fmt.Errorf("Copying key.pem to machine dir failed: %s", err) } - log.Debugf("generating server cert: %s ca-key=%s private-key=%s org=%s", + // The Host IP is always added to the certificate's SANs list + certSANs := append(authOptions.ServerCertSANs, ip) + log.Debugf("generating server cert: %s ca-key=%s private-key=%s org=%s san=%s", authOptions.ServerCertPath, authOptions.CaCertPath, authOptions.CaPrivateKeyPath, org, + certSANs, ) // TODO: Switch to passing just authOptions to this func // instead of all these individual fields err = cert.GenerateCert( - []string{ip, "localhost"}, + certSANs, authOptions.ServerCertPath, authOptions.ServerKeyPath, authOptions.CaCertPath, From b82f9a850926cdc8cd66b1e3309ee830aefa40ef Mon Sep 17 00:00:00 2001 From: Sam Alba Date: Wed, 27 May 2015 17:59:51 -0700 Subject: [PATCH 2/4] Implemented integration tests for --tls-san option Signed-off-by: Sam Alba --- test/integration/certs-extra-san.bats | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) create mode 100644 test/integration/certs-extra-san.bats diff --git a/test/integration/certs-extra-san.bats b/test/integration/certs-extra-san.bats new file mode 100644 index 0000000000..66ea492c83 --- /dev/null +++ b/test/integration/certs-extra-san.bats @@ -0,0 +1,26 @@ +#!/usr/bin/env bats + +load helpers + +export DRIVER=virtualbox +export NAME="bats-$DRIVER-test" +export MACHINE_STORAGE_PATH=/tmp/machine-bats-test-$DRIVER + +@test "$DRIVER: create" { + run machine --tls-san foo.bar.tld --tls-san 10.42.42.42 create -d $DRIVER $NAME +} + +@test "$DRIVER: verify that server cert contains the extra SANs" { + machine ssh $NAME -- openssl x509 -in /var/lib/boot2docker/server.pem -text | grep 'DNS:foo.bar.tld' + machine ssh $NAME -- openssl x509 -in /var/lib/boot2docker/server.pem -text | grep 'IP Address:10.42.42.42' +} + +@test "$DRIVER: verify that server cert SANs are still there after 'regenerate-certs'" { + machine regenerate-certs -f $NAME + machine ssh $NAME -- openssl x509 -in /var/lib/boot2docker/server.pem -text | grep 'DNS:foo.bar.tld' + machine ssh $NAME -- openssl x509 -in /var/lib/boot2docker/server.pem -text | grep 'IP Address:10.42.42.42' +} + +@test "cleanup" { + machine rm $NAME +} From b6519d43e921755caefcdb54fd6faf3c79d9febd Mon Sep 17 00:00:00 2001 From: Jean-Laurent de Morlhon Date: Thu, 19 Nov 2015 17:15:11 +0100 Subject: [PATCH 3/4] More readable code Signed-off-by: Jean-Laurent de Morlhon --- commands/create.go | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/commands/create.go b/commands/create.go index f56eae019a..4e5474e3a2 100644 --- a/commands/create.go +++ b/commands/create.go @@ -356,14 +356,14 @@ func getDriverOpts(c CommandLine, mcnflags []mcnflag.Flag) drivers.DriverOptions for _, name := range c.FlagNames() { getter, ok := c.Generic(name).(flag.Getter) - if !ok { + if ok { + driverOpts.Values[name] = getter.Get() + } else { // TODO: This is pretty hacky. StringSlice is the only // type so far we have to worry about which is not a // Getter, though. driverOpts.Values[name] = c.StringSlice(name) - continue } - driverOpts.Values[name] = getter.Get() } return driverOpts From a55bba3ed2b34ecc3e4f4270ff358268eb029791 Mon Sep 17 00:00:00 2001 From: Jean-Laurent de Morlhon Date: Mon, 23 Nov 2015 12:26:46 +0100 Subject: [PATCH 4/4] Move tls-san flag to a local flag for create Signed-off-by: Jean-Laurent de Morlhon --- cmd/machine.go | 6 ------ commands/create.go | 7 ++++++- libmachine/provision/utils.go | 6 +++--- test/integration/{ => core}/certs-extra-san.bats | 13 ++++--------- 4 files changed, 13 insertions(+), 19 deletions(-) rename test/integration/{ => core}/certs-extra-san.bats (73%) diff --git a/cmd/machine.go b/cmd/machine.go index b080066c86..c4c24d5b95 100644 --- a/cmd/machine.go +++ b/cmd/machine.go @@ -133,12 +133,6 @@ func main() { Usage: "Token to use for requests to the Github API", Value: "", }, - cli.StringSliceFlag{ - EnvVar: "MACHINE_TLS_SAN", - Name: "tls-san", - Usage: "Support extra SANs for TLS certs", - Value: &cli.StringSlice{}, - }, cli.BoolFlag{ EnvVar: "MACHINE_NATIVE_SSH", Name: "native-ssh", diff --git a/commands/create.go b/commands/create.go index 4e5474e3a2..bbe4bd71c2 100644 --- a/commands/create.go +++ b/commands/create.go @@ -115,6 +115,11 @@ var ( Usage: "addr to advertise for Swarm (default: detect and use the machine IP)", Value: "", }, + cli.StringSliceFlag{ + Name: "tls-san", + Usage: "Support extra SANs for TLS certs", + Value: &cli.StringSlice{}, + }, } ) @@ -178,7 +183,7 @@ func cmdCreateInner(c CommandLine) error { ServerCertPath: filepath.Join(mcndirs.GetMachineDir(), name, "server.pem"), ServerKeyPath: filepath.Join(mcndirs.GetMachineDir(), name, "server-key.pem"), StorePath: filepath.Join(mcndirs.GetMachineDir(), name), - ServerCertSANs: c.GlobalStringSlice("tls-san"), + ServerCertSANs: c.StringSlice("tls-san"), }, EngineOptions: &engine.Options{ ArbitraryFlags: c.StringSlice("engine-opt"), diff --git a/libmachine/provision/utils.go b/libmachine/provision/utils.go index 1119d5267c..0681c648c7 100644 --- a/libmachine/provision/utils.go +++ b/libmachine/provision/utils.go @@ -86,19 +86,19 @@ func ConfigureAuth(p Provisioner) error { } // The Host IP is always added to the certificate's SANs list - certSANs := append(authOptions.ServerCertSANs, ip) + hosts := append(authOptions.ServerCertSANs, ip, "localhost") log.Debugf("generating server cert: %s ca-key=%s private-key=%s org=%s san=%s", authOptions.ServerCertPath, authOptions.CaCertPath, authOptions.CaPrivateKeyPath, org, - certSANs, + hosts, ) // TODO: Switch to passing just authOptions to this func // instead of all these individual fields err = cert.GenerateCert( - certSANs, + hosts, authOptions.ServerCertPath, authOptions.ServerKeyPath, authOptions.CaCertPath, diff --git a/test/integration/certs-extra-san.bats b/test/integration/core/certs-extra-san.bats similarity index 73% rename from test/integration/certs-extra-san.bats rename to test/integration/core/certs-extra-san.bats index 66ea492c83..4973fb5259 100644 --- a/test/integration/certs-extra-san.bats +++ b/test/integration/core/certs-extra-san.bats @@ -1,13 +1,12 @@ #!/usr/bin/env bats -load helpers +load ${BASE_TEST_DIR}/helpers.bash -export DRIVER=virtualbox -export NAME="bats-$DRIVER-test" -export MACHINE_STORAGE_PATH=/tmp/machine-bats-test-$DRIVER @test "$DRIVER: create" { - run machine --tls-san foo.bar.tld --tls-san 10.42.42.42 create -d $DRIVER $NAME + run machine create --tls-san foo.bar.tld --tls-san 10.42.42.42 -d $DRIVER $NAME + echo ${output} + [ "$status" -eq 0 ] } @test "$DRIVER: verify that server cert contains the extra SANs" { @@ -20,7 +19,3 @@ export MACHINE_STORAGE_PATH=/tmp/machine-bats-test-$DRIVER machine ssh $NAME -- openssl x509 -in /var/lib/boot2docker/server.pem -text | grep 'DNS:foo.bar.tld' machine ssh $NAME -- openssl x509 -in /var/lib/boot2docker/server.pem -text | grep 'IP Address:10.42.42.42' } - -@test "cleanup" { - machine rm $NAME -}