{
 "manufacturer": "Eastron",
 "manufacturer_slug": "eastron",
 "model": "SDM120CT-40mA",
 "model_slug": "sdm120ct-40ma",
 "short_model": "SDM120CT-40mA",
 "aliases": [
  "SDM120CT-M-40mA",
  "SDM120CT-M 40mA"
 ],
 "equipment_type": "Energy meter",
 "applies_to": "Eastron SDM120CT-40mA single-phase CT-connected DIN-rail meter with RS485 Modbus RTU, user manual V1.0 (2026-07-16).",
 "summary": "The SDM120CT-40mA is a single-phase two-wire DIN-rail meter that measures through external current transformers and reports over RS485 Modbus RTU. Readings are IEEE floats in input registers (function 04) covering voltage, current, powers, power factor, frequency, demand and import/export energy. Holding registers (function 03/16) hold the RS485 settings, CT primary, pulse outputs and demand period.",
 "transport": [
  "RTU"
 ],
 "defaults": {
  "unit_id": 1,
  "baud": 9600,
  "parity": "None",
  "data_bits": null,
  "stop_bits": 1,
  "tcp_port": null
 },
 "addressing": {
  "convention": "Modicon",
  "note": "Tables print Modicon numbers (30001, 40003, six-digit 461457...) beside the hex start address used on the wire. Wire address = printed number minus 30001 / 40001 / 400001; the manual's example reads 30001 at start address 0x0000."
 },
 "default_word_order": "ABCD",
 "firmware": null,
 "source": {
  "title": "SDM120CT-40mA user manual",
  "doc_number": "V1.0",
  "revision_date": "2026-07-16",
  "url": "https://www.eastrongroup.com/eastrongroup/2026/07/17/EastronSDM120CT-M40mAUsermanualV10.pdf",
  "pages": "Chapter 4, PDF pages 17-23"
 },
 "notes": [
  "Word order: the manual states floats are sent big-endian with the high 16 bits in the first register, and its example decodes 43 66 00 00 as 230 V. All floats here are ABCD.",
  "Left out: metering mode (printed 463779 but with hex start address F9 20, which corresponds to 463777). The printed number and the hex address disagree, so the register is omitted until confirmed.",
  "Left out: scroll display time (463745), stored as BCD, which this schema cannot represent.",
  "Left out: serial number (464513), an unsigned 32-bit value with no stated word order.",
  "This map is for the SDM120CT-40mA only. The SDM120-M (direct connect) user manual on eastrongroup.com has no register table, so it is not covered here.",
  "The front-panel CT1 menu offers fixed primaries (5 to 600 A) while register 40051 accepts 5 to 9999; values outside the menu list have not been checked on a meter."
 ],
 "registers": [
  {
   "table": "input_register",
   "address": 0,
   "documented": "30001",
   "name": "Voltage",
   "description": "Line-to-neutral RMS voltage.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "V",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 6,
   "documented": "30007",
   "name": "Current",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "A",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 12,
   "documented": "30013",
   "name": "Active power",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "W",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 18,
   "documented": "30019",
   "name": "Apparent power",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "VA",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 24,
   "documented": "30025",
   "name": "Reactive power",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "VAr",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 30,
   "documented": "30031",
   "name": "Power factor",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 70,
   "documented": "30071",
   "name": "Frequency",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "Hz",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 72,
   "documented": "30073",
   "name": "Import active energy",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "kWh",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 74,
   "documented": "30075",
   "name": "Export active energy",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "kWh",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 76,
   "documented": "30077",
   "name": "Import reactive energy",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "kVArh",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 78,
   "documented": "30079",
   "name": "Export reactive energy",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "kVArh",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 84,
   "documented": "30085",
   "name": "Total active power demand",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "W",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 86,
   "documented": "30087",
   "name": "Max total active power demand",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "W",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 88,
   "documented": "30089",
   "name": "Import active power demand",
   "description": "Printed as 'import active energy demand' but given in W.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "W",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 90,
   "documented": "30091",
   "name": "Max import active power demand",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "W",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 92,
   "documented": "30093",
   "name": "Export active power demand",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "W",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 94,
   "documented": "30095",
   "name": "Max export active power demand",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "W",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 258,
   "documented": "30259",
   "name": "Current demand",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "A",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 264,
   "documented": "30265",
   "name": "Max current demand",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "A",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 342,
   "documented": "30343",
   "name": "Total kWh",
   "description": "What 'total' includes depends on the metering-mode setting (not mapped; see notes).",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "kWh",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "input_register",
   "address": 344,
   "documented": "30345",
   "name": "Total kVArh",
   "description": "",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "kVArh",
   "access": "R",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 2,
   "documented": "40003",
   "name": "Demand period",
   "description": "0 to 60 minutes; 0 updates demand every second. Default 60.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "min",
   "access": "RW",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 12,
   "documented": "40013",
   "name": "Relay pulse width",
   "description": "Pulse on-time: 60, 100 or 200 ms. Default 60.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "ms",
   "access": "RW",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 18,
   "documented": "40019",
   "name": "Parity and stop bit",
   "description": "RS485 framing. Default one stop bit, no parity.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "",
   "access": "RW",
   "values": {
    "0": "1 stop bit, no parity",
    "1": "1 stop bit, even parity",
    "2": "1 stop bit, odd parity",
    "3": "2 stop bits, no parity"
   },
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 20,
   "documented": "40021",
   "name": "Modbus address",
   "description": "Node address 1 to 247. Default 1.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "",
   "access": "RW",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 28,
   "documented": "40029",
   "name": "Baud rate",
   "description": "Default 9600.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "",
   "access": "RW",
   "values": {
    "0": "2400",
    "1": "4800",
    "2": "9600",
    "5": "1200"
   },
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 50,
   "documented": "40051",
   "name": "CT1",
   "description": "CT primary current, 5 to 9999. Default 5.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "A",
   "access": "RW",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 60,
   "documented": "40061",
   "name": "Backlit time",
   "description": "0 to 121; 0 keeps backlight on, 121 keeps it off. Default 60.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "min",
   "access": "RW",
   "values": null,
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 86,
   "documented": "40087",
   "name": "Pulse 1 output mode",
   "description": "Energy quantity driving pulse output 1. Default export active.",
   "data_type": "FLOAT32",
   "length": 2,
   "word_order": "ABCD",
   "scale": 1,
   "units": "",
   "access": "RW",
   "values": {
    "1": "Import active energy",
    "2": "Import + export active energy",
    "4": "Export active energy",
    "5": "Import reactive energy",
    "6": "Import + export reactive energy",
    "8": "Export reactive energy"
   },
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 61456,
   "documented": "461457",
   "name": "Reset",
   "description": "Write 0000 to clear maximum demand.",
   "data_type": "UINT16",
   "length": 1,
   "word_order": null,
   "scale": 1,
   "units": "",
   "access": "W",
   "values": {
    "0": "Reset maximum demand"
   },
   "bits": null,
   "offset": 0
  },
  {
   "table": "holding_register",
   "address": 63760,
   "documented": "463761",
   "name": "Pulse 1 output constant",
   "description": "Energy per pulse on output 1. Default 0.001 kWh/imp.",
   "data_type": "UINT16",
   "length": 1,
   "word_order": null,
   "scale": 1,
   "units": "",
   "access": "RW",
   "values": {
    "0": "0.001 kWh/imp",
    "1": "0.01 kWh/imp",
    "2": "0.1 kWh/imp",
    "3": "1 kWh/imp"
   },
   "bits": null,
   "offset": 0
  }
 ],
 "integration": {
  "summary": "Read two-register floats with function 04 from 0x0000 (voltage) through 0x0158; import/export kWh are at 0x0048/0x004A. Set the CT primary (40051) to match the installed CTs before trusting current, power and energy.",
  "minimum_registers": [
   {
    "table": "input_register",
    "address": 0,
    "why": "Voltage"
   },
   {
    "table": "input_register",
    "address": 6,
    "why": "Current"
   },
   {
    "table": "input_register",
    "address": 12,
    "why": "Active power"
   },
   {
    "table": "input_register",
    "address": 72,
    "why": "Import kWh"
   },
   {
    "table": "input_register",
    "address": 74,
    "why": "Export kWh"
   },
   {
    "table": "holding_register",
    "address": 50,
    "why": "CT primary setting"
   }
  ],
  "enable": "Modbus RTU is always active on the RS485 port. Settings are written with function 16; the front-panel setup mode also sets the address and CT1.",
  "watchdog": null,
  "quirks": [
   "Most settings, including baud code and address, are floats spanning two registers; the pulse constant and reset registers are 16-bit hex values.",
   "Six-digit register numbers (461457, 463761) map to wire addresses 0xF010 and 0xF910."
  ],
  "setup": [
   "Defaults: address 1, 9600 bps, no parity, 1 stop bit (data bits are not stated in the manual).",
   "Baud options are 1200, 2400, 4800 and 9600 bps only.",
   "Enter the CT primary current (5-9999 A) in 40051."
  ],
  "gotchas": [
   "Current, power and energy are only correct once the CT primary in 40051 matches the installed CTs; this variant takes CTs with a 40 mA secondary."
  ]
 },
 "page": "https://easymodbus.com/modbus-register-maps/eastron/sdm120ct-40ma",
 "address_note": "address = 0-based Modbus wire (PDU) address; documented = as printed in the source.",
 "note": "Re-typed from the manufacturer's public documentation (see source) and verified against it. Registers vary by firmware and options; verify against the live device before writing."
}
