modbus.go 2.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293
  1. // Copyright 2014 Quoc-Viet Nguyen. All rights reserved.
  2. // This software may be modified and distributed under the terms
  3. // of the BSD license. See the LICENSE file for details.
  4. /*
  5. Package modbus provides a client for MODBUS TCP and RTU/ASCII.
  6. */
  7. package modbus
  8. import (
  9. "fmt"
  10. )
  11. const (
  12. // Bit access
  13. FuncCodeReadDiscreteInputs = 2
  14. FuncCodeReadCoils = 1
  15. FuncCodeWriteSingleCoil = 5
  16. FuncCodeWriteMultipleCoils = 15
  17. // 16-bit access
  18. FuncCodeReadInputRegisters = 4
  19. FuncCodeReadHoldingRegisters = 3
  20. FuncCodeWriteSingleRegister = 6
  21. FuncCodeWriteMultipleRegisters = 16
  22. FuncCodeReadWriteMultipleRegisters = 23
  23. FuncCodeMaskWriteRegister = 22
  24. FuncCodeReadFIFOQueue = 24
  25. )
  26. const (
  27. ExceptionCodeIllegalFunction = 1
  28. ExceptionCodeIllegalDataAddress = 2
  29. ExceptionCodeIllegalDataValue = 3
  30. ExceptionCodeServerDeviceFailure = 4
  31. ExceptionCodeAcknowledge = 5
  32. ExceptionCodeServerDeviceBusy = 6
  33. ExceptionCodeMemoryParityError = 8
  34. ExceptionCodeGatewayPathUnavailable = 10
  35. ExceptionCodeGatewayTargetDeviceFailedToRespond = 11
  36. )
  37. // ModbusError implements error interface.
  38. type ModbusError struct {
  39. FunctionCode byte
  40. ExceptionCode byte
  41. }
  42. // Error converts known modbus exception code to error message.
  43. func (e *ModbusError) Error() string {
  44. var name string
  45. switch e.ExceptionCode {
  46. case ExceptionCodeIllegalFunction:
  47. name = "illegal function"
  48. case ExceptionCodeIllegalDataAddress:
  49. name = "illegal data address"
  50. case ExceptionCodeIllegalDataValue:
  51. name = "illegal data value"
  52. case ExceptionCodeServerDeviceFailure:
  53. name = "server device failure"
  54. case ExceptionCodeAcknowledge:
  55. name = "acknowledge"
  56. case ExceptionCodeServerDeviceBusy:
  57. name = "server device busy"
  58. case ExceptionCodeMemoryParityError:
  59. name = "memory parity error"
  60. case ExceptionCodeGatewayPathUnavailable:
  61. name = "gateway path unavailable"
  62. case ExceptionCodeGatewayTargetDeviceFailedToRespond:
  63. name = "gateway target device failed to respond"
  64. default:
  65. name = "unknown"
  66. }
  67. return fmt.Sprintf("modbus: exception '%v' (%s), function '%v'", e.ExceptionCode, name, e.FunctionCode)
  68. }
  69. // ProtocolDataUnit (PDU) is independent of underlying communication layers.
  70. type ProtocolDataUnit struct {
  71. FunctionCode byte
  72. Data []byte
  73. }
  74. // Packager specifies the communication layer.
  75. type Packager interface {
  76. Encode(pdu *ProtocolDataUnit) (adu []byte, err error)
  77. Decode(adu []byte) (pdu *ProtocolDataUnit, err error)
  78. Verify(aduRequest []byte, aduResponse []byte) (err error)
  79. }
  80. // Transporter specifies the transport layer.
  81. type Transporter interface {
  82. Send(aduRequest []byte) (aduResponse []byte, err error)
  83. }