SlaveException.cs 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167
  1. using System;
  2. using System.Diagnostics.CodeAnalysis;
  3. using NModbus.Message;
  4. namespace NModbus
  5. {
  6. #if NET46
  7. using System.Runtime.Serialization;
  8. using System.Security.Permissions;
  9. #endif
  10. /// <summary>
  11. /// Represents slave errors that occur during communication.
  12. /// </summary>
  13. #if NET46
  14. [Serializable]
  15. #endif
  16. public class SlaveException : Exception
  17. {
  18. private const string SlaveAddressPropertyName = "SlaveAdress";
  19. private const string FunctionCodePropertyName = "FunctionCode";
  20. private const string SlaveExceptionCodePropertyName = "SlaveExceptionCode";
  21. #if NET5_0_OR_GREATER
  22. [AllowNull]
  23. #endif
  24. private readonly SlaveExceptionResponse _slaveExceptionResponse;
  25. /// <summary>
  26. /// Initializes a new instance of the <see cref="SlaveException" /> class.
  27. /// </summary>
  28. public SlaveException()
  29. {
  30. }
  31. /// <summary>
  32. /// Initializes a new instance of the <see cref="SlaveException" /> class.
  33. /// </summary>
  34. /// <param name="message">The message.</param>
  35. public SlaveException(string message)
  36. : base(message)
  37. {
  38. }
  39. /// <summary>
  40. /// Initializes a new instance of the <see cref="SlaveException" /> class.
  41. /// </summary>
  42. /// <param name="message">The message.</param>
  43. /// <param name="innerException">The inner exception.</param>
  44. public SlaveException(string message, Exception innerException)
  45. : base(message, innerException)
  46. {
  47. }
  48. internal SlaveException(SlaveExceptionResponse slaveExceptionResponse)
  49. {
  50. _slaveExceptionResponse = slaveExceptionResponse;
  51. }
  52. [SuppressMessage("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode", Justification = "Used by test code.")]
  53. internal SlaveException(string message, SlaveExceptionResponse slaveExceptionResponse)
  54. : base(message)
  55. {
  56. _slaveExceptionResponse = slaveExceptionResponse;
  57. }
  58. #if NET46
  59. /// <summary>
  60. /// Initializes a new instance of the <see cref="SlaveException" /> class.
  61. /// </summary>
  62. /// <param name="info">
  63. /// The <see cref="T:System.Runtime.Serialization.SerializationInfo"></see> that holds the serialized
  64. /// object data about the exception being thrown.
  65. /// </param>
  66. /// <param name="context">
  67. /// The <see cref="T:System.Runtime.Serialization.StreamingContext"></see> that contains contextual
  68. /// information about the source or destination.
  69. /// </param>
  70. /// <exception cref="T:System.Runtime.Serialization.SerializationException">
  71. /// The class name is null or
  72. /// <see cref="P:System.Exception.HResult"></see> is zero (0).
  73. /// </exception>
  74. /// <exception cref="T:System.ArgumentNullException">The info parameter is null. </exception>
  75. protected SlaveException(SerializationInfo info, StreamingContext context)
  76. : base(info, context)
  77. {
  78. if (info != null)
  79. {
  80. _slaveExceptionResponse = new SlaveExceptionResponse(
  81. info.GetByte(SlaveAddressPropertyName),
  82. info.GetByte(FunctionCodePropertyName),
  83. info.GetByte(SlaveExceptionCodePropertyName));
  84. }
  85. }
  86. #endif
  87. /// <summary>
  88. /// Gets a message that describes the current exception.
  89. /// </summary>
  90. /// <value>
  91. /// The error message that explains the reason for the exception, or an empty string.
  92. /// </value>
  93. public override string Message
  94. {
  95. get
  96. {
  97. string responseString;
  98. responseString = _slaveExceptionResponse != null ? string.Concat(Environment.NewLine, _slaveExceptionResponse) : string.Empty;
  99. return string.Concat(base.Message, responseString);
  100. }
  101. }
  102. /// <summary>
  103. /// Gets the response function code that caused the exception to occur, or 0.
  104. /// </summary>
  105. /// <value>The function code.</value>
  106. public byte FunctionCode => _slaveExceptionResponse != null ? _slaveExceptionResponse.FunctionCode : (byte)0;
  107. /// <summary>
  108. /// Gets the slave exception code, or 0.
  109. /// </summary>
  110. /// <value>The slave exception code.</value>
  111. public byte SlaveExceptionCode => _slaveExceptionResponse != null ? _slaveExceptionResponse.SlaveExceptionCode : (byte)0;
  112. /// <summary>
  113. /// Gets the slave address, or 0.
  114. /// </summary>
  115. /// <value>The slave address.</value>
  116. public byte SlaveAddress => _slaveExceptionResponse != null ? _slaveExceptionResponse.SlaveAddress : (byte)0;
  117. #if NET46
  118. /// <summary>
  119. /// When overridden in a derived class, sets the <see cref="T:System.Runtime.Serialization.SerializationInfo"></see>
  120. /// with information about the exception.
  121. /// </summary>
  122. /// <param name="info">
  123. /// The <see cref="T:System.Runtime.Serialization.SerializationInfo"></see> that holds the serialized
  124. /// object data about the exception being thrown.
  125. /// </param>
  126. /// <param name="context">
  127. /// The <see cref="T:System.Runtime.Serialization.StreamingContext"></see> that contains contextual
  128. /// information about the source or destination.
  129. /// </param>
  130. /// <exception cref="T:System.ArgumentNullException">The info parameter is a null reference (Nothing in Visual Basic). </exception>
  131. /// <PermissionSet>
  132. /// <IPermission
  133. /// class="System.Security.Permissions.FileIOPermission, mscorlib, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"
  134. /// version="1" Read="*AllFiles*" PathDiscovery="*AllFiles*" />
  135. /// <IPermission
  136. /// class="System.Security.Permissions.SecurityPermission, mscorlib, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"
  137. /// version="1" Flags="SerializationFormatter" />
  138. /// </PermissionSet>
  139. [SecurityPermissionAttribute(SecurityAction.Demand, SerializationFormatter = true)]
  140. [SuppressMessage("Microsoft.Design", "CA1062:ValidateArgumentsOfPublicMethods", Justification = "Argument info is validated, rule does not understand AND condition.")]
  141. public override void GetObjectData(SerializationInfo info, StreamingContext context)
  142. {
  143. base.GetObjectData(info, context);
  144. if (info != null && _slaveExceptionResponse != null)
  145. {
  146. info.AddValue(SlaveAddressPropertyName, _slaveExceptionResponse.SlaveAddress);
  147. info.AddValue(FunctionCodePropertyName, _slaveExceptionResponse.FunctionCode);
  148. info.AddValue(SlaveExceptionCodePropertyName, _slaveExceptionResponse.SlaveExceptionCode);
  149. }
  150. }
  151. #endif
  152. }
  153. }