From 9197213c5177e852678d88eb219c36b256a9f41d Mon Sep 17 00:00:00 2001 From: Roman Dodin Date: Thu, 21 Sep 2023 20:28:58 +0200 Subject: [PATCH] Fix panic when no keys present for srl node (#1604) * fix keys catenation for 0.0 builds when no keys present * added rn --- docs/rn/0.45.md | 6 ++++++ nodes/srl/srl.go | 2 +- nodes/srl/sshkey.go | 22 ++++++++++++++++------ 3 files changed, 23 insertions(+), 7 deletions(-) diff --git a/docs/rn/0.45.md b/docs/rn/0.45.md index f6baaa304..a10f338c1 100644 --- a/docs/rn/0.45.md +++ b/docs/rn/0.45.md @@ -24,3 +24,9 @@ Now @steiler enhanced this functionality by making sure that if a user provides * #1571 - ansible proxy variable is added to containerlab produced ansible inventory * #1592 - ca cert and node certs now have a default country code set to US * #1583 - default link MTU is now fixed to be 9500 again + +## Patches + +### 0.45.1 + +* fix panic when no keys are present for srlinux node diff --git a/nodes/srl/srl.go b/nodes/srl/srl.go index 13e5e5688..45b56200e 100644 --- a/nodes/srl/srl.go +++ b/nodes/srl/srl.go @@ -565,7 +565,7 @@ func (n *srl) addDefaultConfig(ctx context.Context) error { // in srlinux >= v23.10+ linuxadmin and admin user ssh keys can only be configured via the cli // so we add the keys to the template data for rendering. - if semver.Compare(n.swVersion.String(), "v23.10") >= 0 || n.swVersion.major == "0" { + if len(n.sshPubKeys) > 0 && (semver.Compare(n.swVersion.String(), "v23.10") >= 0 || n.swVersion.major == "0") { tplData.SSHPubKeys = catenateKeys(n.sshPubKeys) } diff --git a/nodes/srl/sshkey.go b/nodes/srl/sshkey.go index 8fab37739..81243b92e 100644 --- a/nodes/srl/sshkey.go +++ b/nodes/srl/sshkey.go @@ -2,7 +2,6 @@ package srl import ( "bytes" - "fmt" "strings" "golang.org/x/crypto/ssh" @@ -14,19 +13,30 @@ import ( // for users. func catenateKeys(in []ssh.PublicKey) string { var keys strings.Builder + // pre-allocate the string builder capacity + keys.Grow(len(in) * 100) // iterate through keys - for _, k := range in { + for i, k := range in { // extract the keys in AuthorizedKeys format (e.g. "ssh-rsa ") ks := bytes.TrimSpace(ssh.MarshalAuthorizedKey(k)) - // add a seperator, leading quote, the key string and trailing quote - fmt.Fprintf(&keys, " \"%s\"", ks) + // add a separator, leading quote, the key string and trailing quote + if i > 0 { + keys.WriteByte(' ') + } + keys.WriteByte('"') + keys.Write(ks) + keys.WriteByte('"') } - // return all but the first leading seperator of the string builders content as string - return keys.String()[1:] + // return the string builders content as string + return keys.String() } // filterSSHPubKeys removes non-rsa keys from n.sshPubKeys until srl adds support for them. func (n *srl) filterSSHPubKeys() { + if len(n.sshPubKeys) == 0 { + return + } + var filteredKeys []ssh.PublicKey for _, k := range n.sshPubKeys {