diff --git a/Sharp7.Rx/S7ErrorCodes.cs b/Sharp7.Rx/S7ErrorCodes.cs
new file mode 100644
index 0000000..db1b5eb
--- /dev/null
+++ b/Sharp7.Rx/S7ErrorCodes.cs
@@ -0,0 +1,27 @@
+using System.Collections.Generic;
+
+namespace Sharp7.Rx
+{
+ public static class S7ErrorCodes
+ {
+ ///
+ /// This list is not exhaustive and should be considered work in progress.
+ ///
+ private static readonly HashSet notDisconnectedErrorCodes = new HashSet
+ {
+ 0x000000, // OK
+ 0xC00000, // CPU: Item not available
+ 0x900000, // CPU: Address out of range
+ };
+
+ ///
+ /// Some error codes indicate connection lost, in which case, the driver tries to reestablish connection.
+ /// Other error codes indicate a user error, like reading from an unavailable DB or exceeding
+ /// the DBs range. In this case the driver should not consider the connection to be lost.
+ ///
+ public static bool AssumeConnectionLost(int errorCode)
+ {
+ return !notDisconnectedErrorCodes.Contains(errorCode);
+ }
+ }
+}
\ No newline at end of file
diff --git a/Sharp7.Rx/Sharp7Connector.cs b/Sharp7.Rx/Sharp7Connector.cs
index 99c6644..3063471 100644
--- a/Sharp7.Rx/Sharp7Connector.cs
+++ b/Sharp7.Rx/Sharp7Connector.cs
@@ -52,7 +52,7 @@ namespace Sharp7.Rx
var result = await Task.Factory.StartNew(() => s7MultiVar.Read(), CancellationToken.None, TaskCreationOptions.None, scheduler);
if (result != 0)
{
- await EvaluateErrorCode(result);
+ EvaluateErrorCode(result);
throw new InvalidOperationException($"Error in MultiVar request for variables: {string.Join(",", variableNames)}");
}
@@ -88,7 +88,7 @@ namespace Sharp7.Rx
try
{
var errorCode = await Task.Factory.StartNew(() => sharp7.ConnectTo(ipAddress, rackNr, cpuSlotNr), CancellationToken.None, TaskCreationOptions.None, scheduler);
- var success = await EvaluateErrorCode(errorCode);
+ var success = EvaluateErrorCode(errorCode);
if (success)
{
connectionStateSubject.OnNext(Enums.ConnectionState.Connected);
@@ -168,7 +168,7 @@ namespace Sharp7.Rx
await Task.Factory.StartNew(() => sharp7.Disconnect(), CancellationToken.None, TaskCreationOptions.None, scheduler);
}
- private async Task EvaluateErrorCode(int errorCode)
+ private bool EvaluateErrorCode(int errorCode)
{
if (errorCode == 0)
return true;
@@ -178,7 +178,9 @@ namespace Sharp7.Rx
var errorText = sharp7.ErrorText(errorCode);
Logger?.LogError($"Error Code {errorCode} {errorText}");
- await SetConnectionLostState();
+
+ if (S7ErrorCodes.AssumeConnectionLost(errorCode))
+ SetConnectionLostState();
return false;
}
@@ -190,10 +192,9 @@ namespace Sharp7.Rx
return await Connect();
}
- private async Task SetConnectionLostState()
+ private void SetConnectionLostState()
{
- var state = await connectionStateSubject.FirstAsync();
- if (state == Enums.ConnectionState.ConnectionLost) return;
+ if (connectionStateSubject.Value == Enums.ConnectionState.ConnectionLost) return;
connectionStateSubject.OnNext(Enums.ConnectionState.ConnectionLost);
}
@@ -219,7 +220,7 @@ namespace Sharp7.Rx
if (result != 0)
{
- await EvaluateErrorCode(result);
+ EvaluateErrorCode(result);
var errorText = sharp7.ErrorText(result);
throw new InvalidOperationException($"Error reading {operand}{dBNr}:{startByteAddress}->{bytesToRead} ({errorText})");
}
@@ -265,7 +266,7 @@ namespace Sharp7.Rx
if (result != 0)
{
- await EvaluateErrorCode(result);
+ EvaluateErrorCode(result);
return 0;
}
return (ushort)(data.Length);
@@ -283,7 +284,7 @@ namespace Sharp7.Rx
if (result != 0)
{
- await EvaluateErrorCode(result);
+ EvaluateErrorCode(result);
return (false);
}
return (true);