From 2401a0b4ea5e95292b6d7a23274992c5b57f5149 Mon Sep 17 00:00:00 2001 From: Robert Varga Date: Mon, 6 May 2019 22:56:54 +0200 Subject: [PATCH] Capture server key before returning from callback The key exchange structure is torn down immediately after KeyEstablished callback returns, hence we need to capture the server key before returning. JIRA: NETCONF-614 Change-Id: Iebe69fe374a766f1502325cb610eed8dadb5f099 Signed-off-by: Robert Varga --- .../callhome/protocol/NetconfCallHomeServer.java | 11 +++-------- .../callhome/protocol/NetconfCallHomeServerTest.java | 7 +++++++ .../callhome/mount/CallhomeStatusReporter.java | 4 ++++ 3 files changed, 14 insertions(+), 8 deletions(-) diff --git a/netconf/callhome-protocol/src/main/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServer.java b/netconf/callhome-protocol/src/main/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServer.java index c519d2bb7b..47ee60eecc 100644 --- a/netconf/callhome-protocol/src/main/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServer.java +++ b/netconf/callhome-protocol/src/main/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServer.java @@ -18,12 +18,10 @@ import org.apache.sshd.client.SshClient; import org.apache.sshd.client.future.AuthFuture; import org.apache.sshd.client.keyverifier.ServerKeyVerifier; import org.apache.sshd.client.session.ClientSession; -import org.apache.sshd.client.session.ClientSessionImpl; import org.apache.sshd.client.session.SessionFactory; import org.apache.sshd.common.future.SshFutureListener; import org.apache.sshd.common.io.IoAcceptor; import org.apache.sshd.common.io.IoServiceFactory; -import org.apache.sshd.common.kex.KeyExchange; import org.apache.sshd.common.session.Session; import org.apache.sshd.common.session.SessionListener; import org.apache.sshd.netty.NettyIoServiceFactory; @@ -119,6 +117,8 @@ public class NetconfCallHomeServer implements AutoCloseable, ServerKeyVerifier { } private SshFutureListener newAuthSshFutureListener(final ClientSession session) { + final PublicKey serverKey = session.getKex().getServerKey(); + return new SshFutureListener() { @Override public void operationComplete(final AuthFuture authFuture) { @@ -137,13 +137,8 @@ public class NetconfCallHomeServer implements AutoCloseable, ServerKeyVerifier { } private void onFailure(final Throwable throwable) { - ClientSessionImpl impl = (ClientSessionImpl) session; LOG.error("Authorize failed for session {}", session, throwable); - - KeyExchange kex = impl.getKex(); - PublicKey key = kex.getServerKey(); - recorder.reportFailedAuth(key); - + recorder.reportFailedAuth(serverKey); session.close(true); } diff --git a/netconf/callhome-protocol/src/test/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServerTest.java b/netconf/callhome-protocol/src/test/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServerTest.java index 27b829e0ef..e400f5e66f 100644 --- a/netconf/callhome-protocol/src/test/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServerTest.java +++ b/netconf/callhome-protocol/src/test/java/org/opendaylight/netconf/callhome/protocol/NetconfCallHomeServerTest.java @@ -33,6 +33,7 @@ import org.apache.sshd.common.future.SshFutureListener; import org.apache.sshd.common.io.IoAcceptor; import org.apache.sshd.common.io.IoHandler; import org.apache.sshd.common.io.IoServiceFactory; +import org.apache.sshd.common.kex.KeyExchange; import org.apache.sshd.common.session.Session; import org.apache.sshd.common.session.SessionListener; import org.junit.AfterClass; @@ -114,6 +115,12 @@ public class NetconfCallHomeServerTest { CallHomeSessionContext mockContext = mock(CallHomeSessionContext.class); doNothing().when(mockContext).openNetconfChannel(); doReturn(mockContext).when(mockSession).getAttribute(any(Session.AttributeKey.class)); + + final KeyExchange kex = mock(KeyExchange.class); + doReturn(kex).when(mockSession).getKex(); + final PublicKey serverKey = mock(PublicKey.class); + doReturn(serverKey).when(kex).getServerKey(); + SessionListener listener = instance.createSessionListener(); doReturn(mockAuthFuture).when(mockContext).authorize(); // when diff --git a/netconf/callhome-provider/src/main/java/org/opendaylight/netconf/callhome/mount/CallhomeStatusReporter.java b/netconf/callhome-provider/src/main/java/org/opendaylight/netconf/callhome/mount/CallhomeStatusReporter.java index 1f819ae0a3..7bff5acd4a 100644 --- a/netconf/callhome-provider/src/main/java/org/opendaylight/netconf/callhome/mount/CallhomeStatusReporter.java +++ b/netconf/callhome-provider/src/main/java/org/opendaylight/netconf/callhome/mount/CallhomeStatusReporter.java @@ -303,6 +303,10 @@ class CallhomeStatusReporter implements DataTreeChangeListener, StatusReco for (Device device : getDevicesAsList()) { String keyString = device.getSshHostKey(); + if (keyString == null) { + LOG.info("Whitelist device {} does not have a host key, skipping it", device.getUniqueId()); + continue; + } try { PublicKey pubKey = decoder.decodePublicKey(keyString); -- 2.36.6