From 1894e101ba9c22c1d07b8af2926e5254e5bbdddb Mon Sep 17 00:00:00 2001 From: Benoit BERNARD Date: Fri, 3 Jan 2025 18:04:09 +0100 Subject: [PATCH 1/3] Fixed > Cast to ReportMessage exception in Discovery.GetResponse --- SharpSnmpLib/Messaging/Discovery.cs | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/SharpSnmpLib/Messaging/Discovery.cs b/SharpSnmpLib/Messaging/Discovery.cs index ab4abbdf..054a815e 100644 --- a/SharpSnmpLib/Messaging/Discovery.cs +++ b/SharpSnmpLib/Messaging/Discovery.cs @@ -197,7 +197,17 @@ public ReportMessage GetResponse(int timeout, IPEndPoint receiver) } using var socket = receiver.GetSocket(); - return (ReportMessage)_discovery.GetResponse(timeout, receiver, Empty, socket); + var response = _discovery.GetResponse(timeout, receiver, Empty, socket); + + try + { + return (ReportMessage)response; + } + catch + { + //The cast was not possible with a system that needed contextname=public + return new ReportMessage(response.Version, response.Header, response.Parameters, response.Scope, response.Privacy, response?.ToBytes()); + } } /// From e67d498f223c025facd8d8afda62b1eb80387271 Mon Sep 17 00:00:00 2001 From: Benoit BERNARD Date: Fri, 3 Jan 2025 18:27:55 +0100 Subject: [PATCH 2/3] fixed > v3 Discovery can be initialized with a contextName --- SharpSnmpLib/Messaging/Discoverer.cs | 10 ++++++---- SharpSnmpLib/Messaging/Discovery.cs | 24 ++++++++++++++++-------- SharpSnmpLib/Messaging/Messenger.cs | 5 +++-- SharpSnmpLib/Messaging/Net6Discoverer.cs | 9 +++++---- 4 files changed, 30 insertions(+), 18 deletions(-) diff --git a/SharpSnmpLib/Messaging/Discoverer.cs b/SharpSnmpLib/Messaging/Discoverer.cs index a8905291..a2b2db8a 100644 --- a/SharpSnmpLib/Messaging/Discoverer.cs +++ b/SharpSnmpLib/Messaging/Discoverer.cs @@ -57,8 +57,9 @@ public sealed partial class Discoverer /// The broadcast address. /// The community. /// The discovering time interval, in milliseconds. + /// The optional Context Name. /// must be configured to a valid multicast address when IPv6 is used. For example, "[ff02::1]:161" - public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval) + public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval, OctetString? contextName = null) { if (broadcastAddress == null) { @@ -75,7 +76,7 @@ public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetStri _requestId = Messenger.NextRequestId; if (version == VersionCode.V3) { - var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize); + var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize, contextName); bytes = discovery.ToBytes(); } else @@ -282,8 +283,9 @@ private void HandleMessage(byte[] buffer, int count, IPEndPoint remote) /// The broadcast address. /// The community. /// The discovering time interval, in milliseconds. + /// The optional context name. /// must be an IPv4 address. IPv6 is not yet supported here. - public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval) + public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval, OctetString? contextName = null) { if (broadcastAddress == null) { @@ -300,7 +302,7 @@ public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress _requestId = Messenger.NextRequestId; if (version == VersionCode.V3) { - var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize); + var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize, contextName); bytes = discovery.ToBytes(); } else diff --git a/SharpSnmpLib/Messaging/Discovery.cs b/SharpSnmpLib/Messaging/Discovery.cs index 054a815e..9edb2b6f 100644 --- a/SharpSnmpLib/Messaging/Discovery.cs +++ b/SharpSnmpLib/Messaging/Discovery.cs @@ -57,8 +57,12 @@ public sealed partial class Discovery /// The request id. /// The message id. /// The max size of message. - public Discovery(int messageId, int requestId, int maxMessageSize) + /// The optional Context Name. + public Discovery(int messageId, int requestId, int maxMessageSize, OctetString? contextName = null) { + if (contextName == null) + contextName = OctetString.Empty; + _discovery = new GetRequestMessage( VersionCode.V3, new Header( @@ -68,7 +72,7 @@ public Discovery(int messageId, int requestId, int maxMessageSize) DefaultSecurityParameters, new Scope( OctetString.Empty, - OctetString.Empty, + contextName, new GetRequestPdu(requestId, new List())), DefaultPrivacyProvider.DefaultPair, null); @@ -81,8 +85,12 @@ public Discovery(int messageId, int requestId, int maxMessageSize) /// The message id. /// The max size of message. /// Message type. - public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type) + /// The optional Context Name. + public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type, OctetString? contextName = null) { + if (contextName == null) + contextName = OctetString.Empty; + switch (type) { case SnmpType.GetRequestPdu: @@ -96,7 +104,7 @@ public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type DefaultSecurityParameters, new Scope( OctetString.Empty, - OctetString.Empty, + contextName, new GetRequestPdu(requestId, new List())), DefaultPrivacyProvider.DefaultPair, null); @@ -114,7 +122,7 @@ public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type DefaultSecurityParameters, new Scope( OctetString.Empty, - OctetString.Empty, + contextName, new GetNextRequestPdu(requestId, new List())), DefaultPrivacyProvider.DefaultPair, null); @@ -132,7 +140,7 @@ public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type DefaultSecurityParameters, new Scope( OctetString.Empty, - OctetString.Empty, + contextName, new GetBulkRequestPdu(requestId, 0, 0, new List())), DefaultPrivacyProvider.DefaultPair, null); @@ -150,7 +158,7 @@ public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type DefaultSecurityParameters, new Scope( OctetString.Empty, - OctetString.Empty, + contextName, new SetRequestPdu(requestId, new List())), DefaultPrivacyProvider.DefaultPair, null); @@ -168,7 +176,7 @@ public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type DefaultSecurityParameters, new Scope( OctetString.Empty, - OctetString.Empty, + contextName, new InformRequestPdu(requestId)), DefaultPrivacyProvider.DefaultPair, null); diff --git a/SharpSnmpLib/Messaging/Messenger.cs b/SharpSnmpLib/Messaging/Messenger.cs index 9ba4ea93..ab93f44e 100644 --- a/SharpSnmpLib/Messaging/Messenger.cs +++ b/SharpSnmpLib/Messaging/Messenger.cs @@ -1205,10 +1205,11 @@ private static bool BulkHasNext(VersionCode version, IPEndPoint receiver, OctetS /// Returns a new discovery request. /// /// Message type. + /// The optional context name. /// - public static Discovery GetNextDiscovery(SnmpType type) + public static Discovery GetNextDiscovery(SnmpType type, OctetString? contextName = null) { - return new Discovery(NextMessageId, NextRequestId, MaxMessageSize, type); + return new Discovery(NextMessageId, NextRequestId, MaxMessageSize, type, contextName); } /// diff --git a/SharpSnmpLib/Messaging/Net6Discoverer.cs b/SharpSnmpLib/Messaging/Net6Discoverer.cs index 6c16f3f6..1e5c50d7 100644 --- a/SharpSnmpLib/Messaging/Net6Discoverer.cs +++ b/SharpSnmpLib/Messaging/Net6Discoverer.cs @@ -38,8 +38,9 @@ public sealed partial class Discoverer /// The broadcast address. /// The community. /// The cancellation token. + /// The optional context name. /// must be an IPv4 address. IPv6 is not yet supported here. - public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString? community, CancellationToken token) + public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString? community, CancellationToken token, OctetString? contextName = null) { if (broadcastAddress == null) { @@ -61,7 +62,7 @@ public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetStri _requestId = Messenger.NextRequestId; if (version == VersionCode.V3) { - var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize); + var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize, contextName); bytes = discovery.ToBytes(); } else @@ -141,7 +142,7 @@ private void AsyncBeginReceive(Socket socket, CancellationToken token) /// The community. /// The cancellation token. /// must be an IPv4 address. IPv6 is not yet supported here. - public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, CancellationToken token) + public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, CancellationToken token, OctetString? contextName = null) { if (broadcastAddress == null) { @@ -158,7 +159,7 @@ public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress _requestId = Messenger.NextRequestId; if (version == VersionCode.V3) { - var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize); + var discovery = new Discovery(Messenger.NextMessageId, _requestId, Messenger.MaxMessageSize, contextName); bytes = discovery.ToBytes(); } else From fbfcf80d1004761d37ad8055d2fa456562541f48 Mon Sep 17 00:00:00 2001 From: Benoit BERNARD Date: Wed, 8 Jan 2025 16:35:26 +0100 Subject: [PATCH 3/3] #690 Use default value OctetString.Empty instead of null --- SharpSnmpLib/Messaging/Discoverer.cs | 30 ++++- SharpSnmpLib/Messaging/Discovery.cs | 163 ++++++++++++++++++++--- SharpSnmpLib/Messaging/Messenger.cs | 13 +- SharpSnmpLib/Messaging/Net6Discoverer.cs | 31 ++++- 4 files changed, 212 insertions(+), 25 deletions(-) diff --git a/SharpSnmpLib/Messaging/Discoverer.cs b/SharpSnmpLib/Messaging/Discoverer.cs index a2b2db8a..e00fbe1a 100644 --- a/SharpSnmpLib/Messaging/Discoverer.cs +++ b/SharpSnmpLib/Messaging/Discoverer.cs @@ -50,6 +50,19 @@ public sealed partial class Discoverer /// The exception is typical here. public event EventHandler? ExceptionRaised; + /// + /// Discovers agents of the specified version in a specific time interval. + /// + /// The version. + /// The broadcast address. + /// The community. + /// The discovering time interval, in milliseconds. + /// must be configured to a valid multicast address when IPv6 is used. For example, "[ff02::1]:161" + public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval) + { + Discover(version, broadcastAddress, community, interval, OctetString.Empty); + } + /// /// Discovers agents of the specified version in a specific time interval. /// @@ -59,7 +72,7 @@ public sealed partial class Discoverer /// The discovering time interval, in milliseconds. /// The optional Context Name. /// must be configured to a valid multicast address when IPv6 is used. For example, "[ff02::1]:161" - public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval, OctetString? contextName = null) + public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval, OctetString contextName) { if (broadcastAddress == null) { @@ -276,6 +289,19 @@ private void HandleMessage(byte[] buffer, int count, IPEndPoint remote) } } + /// + /// Discovers agents of the specified version in a specific time interval. + /// + /// The version. + /// The broadcast address. + /// The community. + /// The discovering time interval, in milliseconds. + /// must be an IPv4 address. IPv6 is not yet supported here. + public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval) + { + await DiscoverAsync(version, broadcastAddress, community, interval, OctetString.Empty); + } + /// /// Discovers agents of the specified version in a specific time interval. /// @@ -285,7 +311,7 @@ private void HandleMessage(byte[] buffer, int count, IPEndPoint remote) /// The discovering time interval, in milliseconds. /// The optional context name. /// must be an IPv4 address. IPv6 is not yet supported here. - public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval, OctetString? contextName = null) + public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, int interval, OctetString contextName) { if (broadcastAddress == null) { diff --git a/SharpSnmpLib/Messaging/Discovery.cs b/SharpSnmpLib/Messaging/Discovery.cs index 9edb2b6f..c6c8fc42 100644 --- a/SharpSnmpLib/Messaging/Discovery.cs +++ b/SharpSnmpLib/Messaging/Discovery.cs @@ -57,25 +57,45 @@ public sealed partial class Discovery /// The request id. /// The message id. /// The max size of message. - /// The optional Context Name. - public Discovery(int messageId, int requestId, int maxMessageSize, OctetString? contextName = null) + public Discovery(int messageId, int requestId, int maxMessageSize) { - if (contextName == null) - contextName = OctetString.Empty; + _discovery = new GetRequestMessage( + VersionCode.V3, + new Header( + new Integer32(messageId), + new Integer32(maxMessageSize), + Levels.Reportable), + DefaultSecurityParameters, + new Scope( + OctetString.Empty, + OctetString.Empty, + new GetRequestPdu(requestId, new List())), + DefaultPrivacyProvider.DefaultPair, + null); + } + /// + /// Initializes a new instance of the class. + /// + /// The request id. + /// The message id. + /// The max size of message. + /// The optional Context Name. + public Discovery(int messageId, int requestId, int maxMessageSize, OctetString contextName) + { _discovery = new GetRequestMessage( - VersionCode.V3, - new Header( - new Integer32(messageId), - new Integer32(maxMessageSize), - Levels.Reportable), - DefaultSecurityParameters, - new Scope( - OctetString.Empty, - contextName, - new GetRequestPdu(requestId, new List())), - DefaultPrivacyProvider.DefaultPair, - null); + VersionCode.V3, + new Header( + new Integer32(messageId), + new Integer32(maxMessageSize), + Levels.Reportable), + DefaultSecurityParameters, + new Scope( + OctetString.Empty, + contextName, + new GetRequestPdu(requestId, new List())), + DefaultPrivacyProvider.DefaultPair, + null); } /// @@ -85,12 +105,115 @@ public Discovery(int messageId, int requestId, int maxMessageSize, OctetString? /// The message id. /// The max size of message. /// Message type. - /// The optional Context Name. - public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type, OctetString? contextName = null) + public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type) { - if (contextName == null) - contextName = OctetString.Empty; + switch (type) + { + case SnmpType.GetRequestPdu: + { + _discovery = new GetRequestMessage( + VersionCode.V3, + new Header( + new Integer32(messageId), + new Integer32(maxMessageSize), + Levels.Reportable), + DefaultSecurityParameters, + new Scope( + OctetString.Empty, + OctetString.Empty, + new GetRequestPdu(requestId, new List())), + DefaultPrivacyProvider.DefaultPair, + null); + break; + } + case SnmpType.GetNextRequestPdu: + { + _discovery = new GetNextRequestMessage( + VersionCode.V3, + new Header( + new Integer32(messageId), + new Integer32(maxMessageSize), + Levels.Reportable), + DefaultSecurityParameters, + new Scope( + OctetString.Empty, + OctetString.Empty, + new GetNextRequestPdu(requestId, new List())), + DefaultPrivacyProvider.DefaultPair, + null); + break; + } + + case SnmpType.GetBulkRequestPdu: + { + _discovery = new GetBulkRequestMessage( + VersionCode.V3, + new Header( + new Integer32(messageId), + new Integer32(maxMessageSize), + Levels.Reportable), + DefaultSecurityParameters, + new Scope( + OctetString.Empty, + OctetString.Empty, + new GetBulkRequestPdu(requestId, 0, 0, new List())), + DefaultPrivacyProvider.DefaultPair, + null); + break; + } + + case SnmpType.SetRequestPdu: + { + _discovery = new SetRequestMessage( + VersionCode.V3, + new Header( + new Integer32(messageId), + new Integer32(maxMessageSize), + Levels.Reportable), + DefaultSecurityParameters, + new Scope( + OctetString.Empty, + OctetString.Empty, + new SetRequestPdu(requestId, new List())), + DefaultPrivacyProvider.DefaultPair, + null); + break; + } + + case SnmpType.InformRequestPdu: + { + _discovery = new InformRequestMessage( + VersionCode.V3, + new Header( + new Integer32(messageId), + new Integer32(maxMessageSize), + Levels.Reportable), + DefaultSecurityParameters, + new Scope( + OctetString.Empty, + OctetString.Empty, + new InformRequestPdu(requestId)), + DefaultPrivacyProvider.DefaultPair, + null); + break; + } + + default: + throw new ArgumentException("Discovery message must be a request.", nameof(type)); + } + } + + /// + /// Initializes a new instance of the class. + /// + /// The request id. + /// The message id. + /// The max size of message. + /// Message type. + /// The optional Context Name. + public Discovery(int messageId, int requestId, int maxMessageSize, SnmpType type, OctetString contextName) + { switch (type) { case SnmpType.GetRequestPdu: diff --git a/SharpSnmpLib/Messaging/Messenger.cs b/SharpSnmpLib/Messaging/Messenger.cs index ab93f44e..ec53de72 100644 --- a/SharpSnmpLib/Messaging/Messenger.cs +++ b/SharpSnmpLib/Messaging/Messenger.cs @@ -1207,7 +1207,18 @@ private static bool BulkHasNext(VersionCode version, IPEndPoint receiver, OctetS /// Message type. /// The optional context name. /// - public static Discovery GetNextDiscovery(SnmpType type, OctetString? contextName = null) + public static Discovery GetNextDiscovery(SnmpType type) + { + return GetNextDiscovery(type, OctetString.Empty); + } + + /// + /// Returns a new discovery request. + /// + /// Message type. + /// The optional context name. + /// + public static Discovery GetNextDiscovery(SnmpType type, OctetString contextName) { return new Discovery(NextMessageId, NextRequestId, MaxMessageSize, type, contextName); } diff --git a/SharpSnmpLib/Messaging/Net6Discoverer.cs b/SharpSnmpLib/Messaging/Net6Discoverer.cs index 1e5c50d7..c02a0cb3 100644 --- a/SharpSnmpLib/Messaging/Net6Discoverer.cs +++ b/SharpSnmpLib/Messaging/Net6Discoverer.cs @@ -31,6 +31,19 @@ namespace Lextm.SharpSnmpLib.Messaging /// public sealed partial class Discoverer { + /// + /// Discovers agents of the specified version in a specific time interval. + /// + /// The version. + /// The broadcast address. + /// The community. + /// The cancellation token. + /// must be an IPv4 address. IPv6 is not yet supported here. + public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString? community, CancellationToken token) + { + Discover(version, broadcastAddress, community, token, OctetString.Empty); + } + /// /// Discovers agents of the specified version in a specific time interval. /// @@ -40,7 +53,7 @@ public sealed partial class Discoverer /// The cancellation token. /// The optional context name. /// must be an IPv4 address. IPv6 is not yet supported here. - public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString? community, CancellationToken token, OctetString? contextName = null) + public void Discover(VersionCode version, IPEndPoint broadcastAddress, OctetString? community, CancellationToken token, OctetString contextName) { if (broadcastAddress == null) { @@ -142,7 +155,21 @@ private void AsyncBeginReceive(Socket socket, CancellationToken token) /// The community. /// The cancellation token. /// must be an IPv4 address. IPv6 is not yet supported here. - public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, CancellationToken token, OctetString? contextName = null) + public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, CancellationToken token) + { + await DiscoverAsync(version, broadcastAddress, community, token, OctetString.Empty); + } + + /// + /// Discovers agents of the specified version in a specific time interval. + /// + /// The version. + /// The broadcast address. + /// The community. + /// The cancellation token. + /// The context name. + /// must be an IPv4 address. IPv6 is not yet supported here. + public async Task DiscoverAsync(VersionCode version, IPEndPoint broadcastAddress, OctetString community, CancellationToken token, OctetString contextName) { if (broadcastAddress == null) {