Skip to content

Commit

Permalink
Use host key checking outside localhost
Browse files Browse the repository at this point in the history
Verify ssh host keys, when connecting to a remote server.

The first connection will prompt, if not in known_hosts.

Signed-off-by: Anders F Björklund <anders.f.bjorklund@gmail.com>
  • Loading branch information
afbjorklund committed Nov 29, 2023
1 parent 64f4462 commit 5b84678
Show file tree
Hide file tree
Showing 5 changed files with 23 additions and 11 deletions.
10 changes: 8 additions & 2 deletions cmd/limactl/copy.go
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ func copyAction(cmd *cobra.Command, args []string) error {
if err != nil {
return err
}
instAddr := "127.0.0.1"
instDirs := make(map[string]string)
scpFlags := []string{}
scpArgs := []string{}
Expand All @@ -68,6 +69,7 @@ func copyAction(cmd *cobra.Command, args []string) error {
if sshutil.DetectOpenSSHVersion().LessThan(*semver.New("8.0.0")) {
legacySSH = true
}
localhostOnly := true
for _, arg := range args {
path := strings.Split(arg, ":")
switch len(path) {
Expand All @@ -91,6 +93,10 @@ func copyAction(cmd *cobra.Command, args []string) error {
} else {
scpArgs = append(scpArgs, fmt.Sprintf("scp://%s@%s:%d/%s", u.Username, inst.SSHAddress, inst.SSHLocalPort, path[1]))
}
if inst.SSHAddress != "127.0.0.1" {
instAddr = inst.SSHAddress
localhostOnly = false
}
instDirs[instName] = inst.Dir
default:
return fmt.Errorf("path %q contains multiple colons", arg)
Expand All @@ -108,14 +114,14 @@ func copyAction(cmd *cobra.Command, args []string) error {
// arguments such as ControlPath. This is preferred as we can multiplex
// sessions without re-authenticating (MaxSessions permitting).
for _, instDir := range instDirs {
sshOpts, err = sshutil.SSHOpts(instDir, false, false, false, false)
sshOpts, err = sshutil.SSHOpts(instDir, false, instAddr, false, false, false)
if err != nil {
return err
}
}
} else {
// Copying among multiple hosts; we can't pass in host-specific options.
sshOpts, err = sshutil.CommonOpts(false)
sshOpts, err = sshutil.CommonOpts(false, localhostOnly)
if err != nil {
return err
}
Expand Down
2 changes: 1 addition & 1 deletion cmd/limactl/shell.go
Original file line number Diff line number Diff line change
Expand Up @@ -168,7 +168,7 @@ func shellAction(cmd *cobra.Command, args []string) error {
}
}

sshOpts, err := sshutil.SSHOpts(inst.Dir, *y.SSH.LoadDotSSHPubKeys, *y.SSH.ForwardAgent, *y.SSH.ForwardX11, *y.SSH.ForwardX11Trusted)
sshOpts, err := sshutil.SSHOpts(inst.Dir, *y.SSH.LoadDotSSHPubKeys, *y.SSH.Address, *y.SSH.ForwardAgent, *y.SSH.ForwardX11, *y.SSH.ForwardX11Trusted)
if err != nil {
return err
}
Expand Down
2 changes: 1 addition & 1 deletion cmd/limactl/show_ssh.go
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ func showSSHAction(cmd *cobra.Command, args []string) error {
if err != nil {
return err
}
opts, err := sshutil.SSHOpts(inst.Dir, *y.SSH.LoadDotSSHPubKeys, *y.SSH.ForwardAgent, *y.SSH.ForwardX11, *y.SSH.ForwardX11Trusted)
opts, err := sshutil.SSHOpts(inst.Dir, *y.SSH.LoadDotSSHPubKeys, *y.SSH.Address, *y.SSH.ForwardAgent, *y.SSH.ForwardX11, *y.SSH.ForwardX11Trusted)
if err != nil {
return err
}
Expand Down
2 changes: 1 addition & 1 deletion pkg/hostagent/hostagent.go
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ func New(instName string, stdout io.Writer, sigintCh chan os.Signal, opts ...Opt
return nil, err
}

sshOpts, err := sshutil.SSHOpts(inst.Dir, *y.SSH.LoadDotSSHPubKeys, *y.SSH.ForwardAgent, *y.SSH.ForwardX11, *y.SSH.ForwardX11Trusted)
sshOpts, err := sshutil.SSHOpts(inst.Dir, *y.SSH.LoadDotSSHPubKeys, *y.SSH.Address, *y.SSH.ForwardAgent, *y.SSH.ForwardX11, *y.SSH.ForwardX11Trusted)
if err != nil {
return nil, err
}
Expand Down
18 changes: 12 additions & 6 deletions pkg/sshutil/sshutil.go
Original file line number Diff line number Diff line change
Expand Up @@ -125,7 +125,7 @@ var sshInfo struct {
//
// The result always contains the IdentityFile option.
// The result never contains the Port option.
func CommonOpts(useDotSSH bool) ([]string, error) {
func CommonOpts(useDotSSH bool, localhost bool) ([]string, error) {
configDir, err := dirnames.LimaConfigDir()
if err != nil {
return nil, err
Expand Down Expand Up @@ -180,14 +180,20 @@ func CommonOpts(useDotSSH bool) ([]string, error) {
}
}

if localhost {
opts = append(opts,
"StrictHostKeyChecking=no",
"UserKnownHostsFile=/dev/null",
"BatchMode=yes",
)
}

opts = append(opts,
"StrictHostKeyChecking=no",
"UserKnownHostsFile=/dev/null",
"NoHostAuthenticationForLocalhost=yes",
"GSSAPIAuthentication=no",
"PreferredAuthentications=publickey",
"Compression=no",
"BatchMode=yes",
"PasswordAuthentication=no",
"IdentitiesOnly=yes",
)

Expand Down Expand Up @@ -222,7 +228,7 @@ func CommonOpts(useDotSSH bool) ([]string, error) {
}

// SSHOpts adds the following options to CommonOptions: User, ControlMaster, ControlPath, ControlPersist
func SSHOpts(instDir string, useDotSSH, forwardAgent bool, forwardX11 bool, forwardX11Trusted bool) ([]string, error) {
func SSHOpts(instDir string, useDotSSH bool, hostAddress string, forwardAgent bool, forwardX11 bool, forwardX11Trusted bool) ([]string, error) {
controlSock := filepath.Join(instDir, filenames.SSHSock)
if len(controlSock) >= osutil.UnixPathMax {
return nil, fmt.Errorf("socket path %q is too long: >= UNIX_PATH_MAX=%d", controlSock, osutil.UnixPathMax)
Expand All @@ -231,7 +237,7 @@ func SSHOpts(instDir string, useDotSSH, forwardAgent bool, forwardX11 bool, forw
if err != nil {
return nil, err
}
opts, err := CommonOpts(useDotSSH)
opts, err := CommonOpts(useDotSSH, hostAddress == "127.0.0.1")
if err != nil {
return nil, err
}
Expand Down

0 comments on commit 5b84678

Please sign in to comment.