Problem Description
A SIMATIC S7-200 CPU 224XP (order number 6ES7 214-1HG31-0XB0) configured as a Modbus master never exchanges data with a Modbus server simulator. The MB_Client instruction output BUSY remains latched at TRUE, DONE never pulses, ERROR never pulses, and STATUS never advances past an early hex code such as 0x0001 or 0x0010. Online watch tables on the buffer area (for example, MW100, 16 words) read back all zeros. The PLC is configured with IP 192.168.1.1 and the workstation running the simulator is on the same /24 subnet.
This pattern is the classic signature of a Modbus master that transmits a request but receives either no reply or a malformed reply. Because the BUSY bit clears only when the master times out waiting for a response or when a valid response is processed, a permanently high BUSY tells you the master's transmit side has executed, but the receive side has not produced a valid reply within the configured timeout window.
Before changing any code, confirm which Siemens library is actually loaded. The instruction name MB_Client belongs to the SIMATIC S7-200 SMART platform (CPU ST/SR series) running in STEP 7 Micro/WIN SMART. The classic S7-200 CPU 224XP, by contrast, uses the Modbus RTU Master library (MBUS_CTRL and MBUS_MSG) for serial communication and the CP 243-1 Ethernet module with the ETHx_CTRL/MB_CLIENT pair for Modbus TCP. Mixing the wrong instruction with the wrong firmware is one of the most common reasons a MB_Client call appears in an S7-200 classic project but never executes - in that case the CPU silently treats the call as an undefined operation and the BUSY bit is left at whatever it was last written to.
Hardware Identification: 6ES7 214-1HG31-0XB0
The order number 6ES7 214-1HG31-0XB0 decodes as follows:
| Field | Value | Meaning |
|---|---|---|
| 6ES7 | Siemens SIMATIC | Family prefix |
| 214 | CPU 224 class | S7-200 product group |
| 1 | DC power supply | 24 V DC nominal input |
| H | DC inputs / relay outputs | 14 DI 24 V DC / 10 DO relay 2 A |
| G | Two RS-485 ports | Port 0 + Port 1 |
| 31 | Function level | CPU 224XP hardware revision |
| 0XB0 | Release identifier | Final hardware release |
Key technical data, drawn from the SIMATIC S7-200 system manual:
- Program memory: 16,384 bytes; data memory: 10,240 bytes
- Retentive area: 256 bytes (V memory); bit memory (M): 256 bits
- Digital inputs: 14 x 24 V DC; digital outputs: 10 x relays 2 A
- Analog inputs: 2 (12-bit); analog output: 1 (12-bit voltage)
- High-speed counters: 6 (up to 200 kHz on phases A/B)
- Pulse outputs: 2 (up to 100 kHz, PTO/PWM)
- Communication ports: 2 x RS-485 supporting PPI, MPI, USS, Freeport, and Modbus RTU master/slave
- Real-time clock retention: 100 hours typical, 70 hours minimum at 25 °C
- Dimensions: 80 x 62 x 140 mm (W x H x D); mounting on DIN 35 mm rail
- Current draw 24 V backplane: 500 mA typical with full I/O load
Instruction Selection: MB_Client vs MB_CLIENT vs MBUS_MSG
Siemens ships three different Modbus master constructs for the S7-200 platform, and choosing the wrong one is the first failure point. Each lives in a different library, each requires a different programming tool, and each runs on different physical hardware.
1. Modbus RTU Master on S7-200 Classic (RS-485)
Lives in the Modbus Master RTU library under STEP 7 Micro/WIN. Used on Port 0 or Port 1 of the CPU 224XP. Instruction names: MBUS_CTRL (init) and MBUS_MSG (single request). Baud 1.2-115.2 kbps, parity none/even/odd, slave IDs 1-247, function codes 01, 02, 03, 04, 05, 06, 15, 16. The library is provided by Siemens and ships as a .mwl file that must be added to the Libraries tree before use. Reference: Siemens FAQ: S7-200 Modbus RTU Master library.
2. Modbus TCP Master on S7-200 Classic via CP 243-1
The CP 243-1 runs an internal web-configuration wizard in Micro/WIN that exports a UDT-based data block plus two FBs: ETHx_CTRL (handles the connection pool) and MB_CLIENT (handles a single Modbus TCP transaction at a time). MB_CLIENT here is written exactly as MB_CLIENT with no underscore, lives in the CP 243-1 Ethernet sublibrary, and is the closest analog to MB_Client on classic S7-200. Reference: CP 243-1 manual.
3. Modbus TCP Client on S7-200 SMART
S7-200 SMART (CPU ST20, SR40, SR60, etc.) uses the instruction named MB_Client (mixed case, with underscore) inside STEP 7 Micro/WIN SMART. The instruction is a single FB, no separate init block, and supports up to 8 active client connections. The 6ES7 214-1HG31-0XB0 is not an S7-200 SMART part; the S7-200 SMART equivalent would be 6ES7 288-1SR40-0AA0 (SR40) or similar. Reference: S7-200 SMART System Manual.
Root Cause Analysis: Why BUSY Stays True
The Modbus master/client instruction sets BUSY=TRUE at the start of every transaction and clears it when the response is received and validated or when a timeout fires. A stuck BUSY with no DONE pulse therefore means one of three things:
- The master transmitted a frame but the slave (or simulator) never replied within the timeout.
- The master transmitted and received a frame, but the response failed CRC, length, transaction-ID, function-code, or unit-ID validation.
- The master has not actually transmitted, because the EN or REQ condition has not pulsed; the apparent BUSY is latched state from a previous call or from an uninitialised instance.
For the symptom described (BUSY always TRUE, 0 returned for any watched word), the most common causes, ranked by field frequency:
| Rank | Cause | How to detect |
|---|---|---|
| 1 | Slave register not initialised - server returns zeros for every read because holding register 0 is empty | Write a non-zero value to register 0 from the simulator before triggering the read |
| 2 | Wrong IP / subnet / no route to server | Ping the server from the engineering PC; open the CP 243-1 diagnostic web page |
| 3 | Firewall on the simulator workstation blocking TCP port 502 | netstat -an | findstr 502 ; review Windows Defender firewall log |
| 4 | Wrong function code or wrong starting address (Modbus addresses are 0-based on the wire but 1-based in many simulators) | Cross-check simulator config; toggle between FC03 and FC04 |
| 5 | PLC is the master but the project loaded is actually a slave, or vice versa | Inspect MBUS_MSG Mode input; 1 = read, 0 = write |
| 6 | Pending Windows restart blocks the simulator service after a previous software install | Check for a Restart required overlay; reboot the server PC - per Microsoft KB 7365340 |
| 7 | Client instruction never gets a rising edge on REQ because the trigger logic runs in a sub-routine that is never called | Cross-reference the call site; verify the subroutine is in the main OB1 scan |
| 8 | Wrong instruction compiled against wrong firmware (MB_Client on classic CPU 224XP) | Open project in Micro/WIN, attempt compile; observe error |
Prerequisites
Before changing any code, confirm the following on the bench:
- STEP 7 Micro/WIN V4.0 SP9 (or Micro/WIN SMART V2.7 if the CPU is actually a SMART series) installed and matching the target CPU firmware.
- PC Ethernet adapter set to a static address in the 192.168.1.x subnet (for example 192.168.1.10) with mask 255.255.255.0.
- PPI/MPI programming cable (USB-to-RS-485, 6ES7 901-3DB30-0XA0) or Ethernet-to-PPI bridge for download.
- Modbus server simulator - Modbus Poll, Modbus Tools, or qModMaster - configured to listen on TCP port 502.
- Wireshark or tcpdump for sniffing the actual frames on the wire.
- User rights on the simulator host to disable the Windows firewall temporarily for testing.
- Known non-zero register values pre-loaded in the simulator so that an empty response can be ruled out.
Step-by-Step Diagnostic Procedure
Follow this sequence; do not skip steps. Each step assumes the previous has been verified and produces a green check before continuing.
Step 1: Verify instruction name and library
Open the program and read the instruction block symbol. If the symbol is MB_Client on a 6ES7 214-1HG31-0XB0, you are either running on the CP 243-1 sublibrary (in which case the project must contain the CP 243-1 wizard data block DB1) or you have a Micro/WIN SMART project loaded against classic S7-200 firmware. The CPU 224XP will not execute an instruction it does not recognise - in that case the call runs as a no-op and BUSY stays latched from a previous call site, which produces exactly the observed symptom. Press F1 over the instruction name to confirm the library source.
Step 2: Verify physical and IP layer
From the engineering PC, ping the simulator host:
ping 192.168.1.50
If ping fails, the issue is below Modbus; resolve L2/L3 first. Confirm link LEDs on the switch, the PLC IP using the Find CPU tool in Micro/WIN, and the simulator IP using ipconfig on the host. The PLC IP is reported back to Micro/WIN via the CP 243-1 diagnostic web page, not from the CPU directly.
Step 3: Verify TCP port 502 reachability
Use a generic TCP client such as nc or PuTTY to open a raw TCP session to port 502 of the simulator and send a known-good Modbus request manually:
echo -n -e '\x00\x01\x00\x00\x00\x06\x01\x03\x00\x00\x00\x0a' | nc 192.168.1.50 502
The first six bytes are the MBAP header (transaction ID 0x0001, protocol 0x0000, length 0x0006). The next byte is unit ID 0x01, followed by function code 0x03 (Read Holding Registers), starting address 0x0000, quantity 0x000a (10 registers). A working simulator returns a frame beginning with the same transaction ID and function code 0x03, with 20 bytes of register data following. If nc produces no response or an immediate disconnect, the server is not listening on 502 or the firewall is intercepting.
Step 4: Verify register content
Most PLC-side complaints of "all zeros in MW100" are caused by a simulator that is responding correctly with all-zero holding registers because no one wrote anything to the simulator yet. Open the simulator UI and write a known pattern (for example 0xAAAA at holding register 0 and 0x5555 at register 1) before triggering the read from the PLC. The PLC buffer will then reflect the pattern on the next successful transaction.
Step 5: Inspect STATUS, ERROR, and DONE outputs in the program
Code a contact that latches every rising edge of DONE, every pulse of ERROR, and every transition of STATUS, into dedicated M bits. Do not rely on online charts alone; the chart update rate is decoupled from the PLC scan and you can miss a one-scan pulse. A persistent STATUS of 0x0001 indicates no response from slave; 0x0002 is a CRC or length error; 0x0003 is an exception response from the slave; 0x0010 means the TCP connection has not been established. Reference the Modbus Master RTU library FAQ for the full code table on the classic RTU library.
Step 6: Capture the wire
Run Wireshark on the engineering PC with the capture filter tcp port 502 and host 192.168.1.50. Confirm:
- TCP three-way handshake completes (SYN, SYN-ACK, ACK) - if not, the client is sending to a closed port.
- The PLC sends exactly one MBAP + PDU frame per REQ pulse - if not, the trigger logic is over-pulsing.
- The server replies within the configured response timeout (default 1000 ms for Modbus RTU master, configurable to 1-32767 ms).
- The transaction ID in the request matches the transaction ID in the response - mismatched IDs mean another master is interleaving.
Step 7: Validate the timeout
The Modbus RTU Master MBUS_MSG block has a Timeout input in milliseconds. If Timeout is left at zero or below the latency of the simulator (which on Windows often takes 50-200 ms to wake up), the master will time out before the response arrives and STATUS will read 0x0001 even though the server eventually replies. Recommended starting value: 1000 ms for bench work, 300-500 ms for production. The CP 243-1 MB_CLIENT uses a fixed response timeout of 2 seconds per transaction, configurable through the wizard.
Wiring, Electrical, and Network Topology
If the actual intent is Modbus RTU on the RS-485 port of the CPU 224XP (which is the most common path on a 224XP given the lack of onboard Ethernet), pin the connector per Siemens specification. The S7-200 Port 0 and Port 1 share the same 9-pin sub-D female pinout:
| Pin | Signal | Direction | Notes |
|---|---|---|---|
| 1 | Shield | Chassis | Ground shield at one end only to avoid ground loops |
| 2 | 24 V common / logic ground | Bidirectional | Same reference as CPU 24 V DC |
| 3 | Data B (D1) | Bidirectional | Inverting line |
| 4 | RTS (TTL) | Output | Used for direction control on half-duplex transceivers |
| 5 | Data A (D0) | Bidirectional | Non-inverting line |
| 6 | +5 V (via 390 ohm) | Output | Termination bias; do not load externally |
| 7 | +24 V (via 390 ohm) | Output | Bias for fail-safe idle state |
| 8 | NC | - | No connection |
| 9 | NC | - | No connection |
For multi-drop RS-485, terminate the two ends of the bus with 120 ohms between pins 3 and 5. Do not place termination in the middle of the bus. Maximum recommended cable length is 1200 m at 9600 baud; drop lengths from the trunk should be under 0.3 m. Use shielded twisted pair with characteristic impedance 100-120 ohms.
The topology below applies when Modbus TCP is used through a CP 243-1:
Network Configuration and IP Addressing
The CPU 224XP does not own an IP address; the CP 243-1 does. Configuration is performed with the CP 243-1 wizard in Micro/WIN, which writes a data block (default DB1) containing the IP, subnet, gateway, and connection table. A common failure mode is to set the IP in the wizard but forget to download the project after the wizard ran - the CPU keeps the previous IP from its flash and the new value is ignored. Force a power cycle after every CP 243-1 parameter change.
| Parameter | Typical bench value | Common error |
|---|---|---|
| PLC IP | 192.168.1.1 | Same address as the server - silent ARP conflict |
| Subnet mask | 255.255.255.0 | /16 mask forces traffic through a gateway that does not exist |
| Server IP | 192.168.1.50 | PC on Wi-Fi (192.168.0.x) while PLC on wired (192.168.1.x) |
| Server TCP port | 502 | Simulator listens on 5020; client sends to 502; connection refused |
| Connection count | 1 | Wizard configured for 0 active connections - no MB_CLIENT can ever fire |
| Keep-alive interval | 30 s | Set to 0 disables keep-alive; intermediate switch clears idle TCP after 60 s |
Modbus Server Simulator Verification
Before pointing the PLC at the simulator, sanity-check the simulator standalone. From the same PC running the simulator, open a second instance of any Modbus master (Modbus Poll, qModMaster, or any reference Modbus TCP client) and read holding registers 0-9. If the second master also sees zeros, the simulator is the problem, not the PLC. If the second master sees the configured values, the simulator is good and the focus shifts to the PLC side.
On Windows, the simulator must be allowed through the firewall. The first time a user runs a service that listens on TCP 502, Windows Defender prompts for permission; if the user dismisses the prompt or selects Cancel, the listener is registered but blocks inbound. Re-enable via wf.msc - Inbound Rules - find the simulator entry - Properties - Allow the connection. Also verify the simulator is not bound to a specific interface (127.0.0.1 only) instead of 0.0.0.0.
If the workstation recently had any Siemens or other software installed that left the system in a restart-pending state, the Winsock catalog may be partially updated and TCP binds will fail or succeed but never accept. Per Microsoft KB 7365340, reboot the host before continuing. The error message "Cannot connect the computer to the server" is the same Winsock-class symptom and is often the only clue that the host, not the PLC, is the failing component.
Parameter and Error Code Reference
For the CP 243-1 MB_CLIENT block, the working parameter set on the bench is:
| Parameter | Value | Notes |
|---|---|---|
| REQ | BOOL, single-shot pulse per scan | Use rising-edge contact; holding REQ high causes a single transaction then idle |
| Connect | BOOL, level | TRUE while the client connection is established; pulses FALSE on error |
| IP1..IP4 | 192, 168, 1, 50 | Modbus server IP, four separate byte inputs |
| RW | 0 = read, 1 = write | Read for diagnostics, write for setpoint |
| Addr | VW100 or MW100 | PLC-side data buffer start; ensure range does not overlap other DBs |
| Count | 1-125 | Word count for FC03/FC04, coil count for FC01/FC02 |
| DataPtr | Pointer to V or M area | Use &VW100 syntax in Micro/WIN |
| Done | BOOL output | One-scan TRUE on success |
| Busy | BOOL output | TRUE while transaction in flight |
| Error | BOOL output | One-scan TRUE on failure |
| Status | WORD output | Hex error code, see table below |
The CP 243-1 MB_CLIENT STATUS word carries the following common codes. Refer to the CP 243-1 manual for the exhaustive list.
| STATUS (hex) | Meaning | Likely cause |
|---|---|---|
| 0x0000 | No error, last transaction OK | Done bit already cleared |
| 0x0001 | Illegal function code | Server does not support FC03; try FC04 |
| 0x0002 | Illegal data address | Starting address outside simulator range |
| 0x0003 | Illegal data value | Count too large or write value out of range |
| 0x0006 | Slave device busy | Server still processing previous request |
| 0x000D | CP 243-1 not configured | Wizard was never run; DB1 missing or not downloaded |
| 0x0010 | Connection not established | TCP handshake failed; check IP / port |
| 0x0020 | Response timeout | Increase Timeout input; check firewall |
| 0x0030 | Invalid response | Length or transaction ID mismatch; another master interfering |
| 0x00FF | General CP fault | Power-cycle CP 243-1; reflash firmware |
Modbus Address Off-by-One
Modbus PDUs address registers 0-65535. Most HMI and SCADA tools display addresses 1-65536. If the simulator is configured to show address 40001 for holding register 0, the client must still send starting address 0 on the wire. A common bench error is to put 40001 into the PLC's MB_CLIENT Addr input, expecting it to map to holding register 1, when in fact the value goes through the TCP stack unmodified and the simulator rejects 40001 as out of range. Always send the protocol-level address, not the user-facing label.
Verification and Commissioning Checks
After every change, validate with this ordered list:
- Trigger a single read from the PLC and capture the Wireshark session. Confirm one MBAP+PDU request, one matching reply, transaction ID identical, function code echoed.
- In Micro/WIN Status Chart, set up MW100 as 16 consecutive words and force the simulator to write 0x1234, 0x5678, 0x9ABC, 0xDEF0 to the first four registers. Confirm those exact values appear in MW100-MW106 after the next DONE pulse.
- Force a write from the PLC (RW=1) of value 0xAA55 to register 0 of the simulator and confirm the simulator UI shows the new value. This proves bidirectional path symmetry.
- Disconnect the Ethernet cable mid-run and confirm the client transitions Connect from TRUE to FALSE within the response timeout window. Reconnect and confirm Connect re-establishes without a project download.
- Power-cycle the PLC and CP 243-1. The client must re-establish the TCP session within 30 seconds without manual intervention. If it does not, the wizard-generated connection table is incomplete.
- Force the simulator offline for 5 minutes, then bring it back. The client should log a single ERROR pulse with STATUS 0x0020 during the outage, then resume normal operation on the first valid response. If BUSY latches permanently after the outage, the MB_CLIENT instance is not being re-triggered after error recovery.
- Run the test loop for 1 hour with at least one transaction per second and confirm DONE pulse count equals request count. Any drift indicates intermittent timeouts or lost responses.
Troubleshooting Matrix
| Symptom | Most likely root cause | First action |
|---|---|---|
| BUSY always TRUE, DONE never pulses | No response from server | Ping server; nc port 502 test; Wireshark |
| DONE pulses, but buffer is always zero | Simulator register empty | Pre-load registers from simulator UI before triggering read |
| ERROR pulses with STATUS 0x0002 | Address out of range | Cross-check starting address with simulator; remember 0-based wire offset |
| ERROR pulses with STATUS 0x0010 | TCP not connected | Verify wizard connection table; force CP restart; check cable |
| ERROR pulses with STATUS 0x0020 | Timeout too short | Increase Timeout to 1000 ms in MBUS_MSG or check CP 243-1 keep-alive |
| Connect bit never goes TRUE | CP 243-1 not configured | Run wizard, regenerate DB, redownload, power-cycle |
| Compiler error "MB_Client unknown" | Project in wrong tool | Open in Micro/WIN SMART only if CPU is SMART; otherwise use CP 243-1 wizard MB_CLIENT |
| Works once after download, fails after power cycle | Wizard DB not in retentive area | Mark DB1 as retentive in System Block |
| All-zero buffer but DONE pulses after REQ | Reading wrong FC - simulator does not support FC04 for input registers | Switch to FC03 for holding registers |
| Occasional DONE followed by zero buffer | Another master on the bus returning stale responses | Capture with Wireshark; assign unique unit ID per master |
| Wireshark shows SYN but no SYN-ACK | Firewall or wrong port | Disable Windows Firewall briefly; confirm port 502 with netstat -an |
| Connection drops every 60 seconds | Intermediate switch idle timer; keep-alive disabled | Enable keep-alive in CP 243-1 wizard; reduce polling interval |
Safety and EMC Considerations
The CP 243-1 must be mounted on the same backplane as the CPU 224XP with a stable 24 V DC supply. Voltage tolerance is 20.4-28.8 V DC; dips below 19.2 V will reset the module and force a re-handshake with the server. In electrically noisy cabinets, route the Ethernet cable along grounded cable trays and avoid running parallel to VFD output cables closer than 200 mm. Use shielded CAT5e or better, with the shield bonded to chassis ground at one end only. Reference the CP 243-1 manual EMC installation guidelines for cabinet layout.
For RS-485 Modbus RTU on Port 0/1, the 24 V common of the CPU must share the same ground reference as the slave device, otherwise the differential signal is referenced to a floating common and the receiver cannot decode bits reliably. Use a single-point ground at the master end of the bus and avoid ground loops through multiple chassis.
Frequently Asked Questions
Does the CPU 224XP support Modbus TCP natively?
No. The 6ES7 214-1HG31-0XB0 has only RS-485 ports. Modbus TCP requires the CP 243-1 (6GK7 243-1EX01-0XE0) communication processor, configured through the Ethernet wizard in Micro/WIN. Reference the CP 243-1 manual.
Why does my MB_Client instruction not compile in Micro/WIN?
Because MB_Client belongs to the S7-200 SMART library, not classic S7-200. The classic CPU 224XP uses the CP 243-1 sublibrary block named MB_CLIENT (no underscore) for Modbus TCP, or MBUS_MSG for Modbus RTU on the onboard RS-485 port. Reference the S7-200 SMART system manual for SMART-side differences.
My BUSY bit stays high forever - what does STATUS 0x0010 mean?
STATUS 0x0010 from the CP 243-1 MB_CLIENT means the TCP connection has not been established. Verify the server IP, port 502 reachability, firewall rules, and that the CP 243-1 wizard connection table has at least one entry pointing at the server. Re-download the project and power-cycle the CP after any wizard change.
The buffer reads back all zeros even though DONE pulses - is the server broken?
Not necessarily. Most simulators return 0x0000 for any holding register that has never been written. Write a known non-zero pattern (for example 0xAAAA at register 0) from the simulator UI before triggering the read; if the pattern then appears in the PLC buffer, the path is healthy and the all-zero result was simply empty registers.
After installing TIA Portal or another Siemens tool the simulator stops accepting connections. Why?
Some installers leave the Windows network stack in a pending-restart state, which prevents Winsock listeners from binding cleanly. Reboot the simulator host to clear the pending state. See Microsoft KB 7365340 for background on the symptom.
How do I switch from Modbus RTU on Port 0 to Modbus TCP on a CP 243-1?
Stop the program, open the Ethernet wizard in Micro/WIN, run it against the CP 243-1 at slot 1, regenerate DB1, then replace the MBUS_CTRL / MBUS_MSG pair with the wizard-generated MB_CLIENT FB instances (one per connection). Set the IP bytes, RW mode, count, and data pointer to the same V/M area. Download, then power-cycle the PLC once so the CP 243-1 boots with the new configuration.