Symptoms and Field Observation
When a SIMATIC S7-1200 CPU is wired to a Microscan Ethernet TCP/IP barcode scanner through Open User Communication (OUC) and the receive block is configured in TIA Portal V13 SP1 with TRCV_C block version 4.0, integrators observe the following abnormal behavior on the live system:
- STATUS output of TRCV_C reads
16#7006(decimal 28678) continuously while the TCP connection remains held open. - RCVD_LEN output reads
0for every OB1 cycle, even immediately after the scanner is triggered. - The destination data block - typically declared as
Array[0..N] of ByteorArray[0..N] of Char- is never written by the block. All bytes remain at the configured initial value. - The scanner is proven to be transmitting valid TCP payloads when observed with a PC-based tool such as the Hercules SETUP utility in TCP client mode. No request message is required from the PLC to elicit a payload; the scanner fires on its hardware trigger input and pushes the ASCII data unsolicited.
- Setting the LEN input of TRCV_C to a non-zero value (e.g.
1,100, or65535) changes the symptom to ERROR = TRUE and STATUS =16#8088- "LEN parameter does not correspond to the receive area set at the DATA parameter".
Together, these observations point to a data-flow binding problem between the TRCV_C instruction and the receive buffer tag, not to a physical, network-layer, or scanner-side fault. The fix is a one-time reconfiguration of the DATA pin in TIA Portal.
Affected Environment and Versions
| Component | Configuration |
|---|---|
| PLC | SIMATIC S7-1200 (CPU 1211C, 1212C, 1214C, 1215C, 1217C, 1214FC; tested on 6ES7214-1AG40-0XB0) |
| CPU firmware | V4.0 (TIA Portal V13 SP1 baseline) through V4.6 (TIA Portal V17/V18); TRCV_C is supported on firmware V4.0 and higher |
| TIA Portal | V13 SP1 (reported), V14, V14 SP1, V15, V15.1, V16, V17, V18 |
| Receive instruction | TRCV_C (legacy Open User Communication), block version 4.0 |
| Companion instruction | TSEND_C (for bidirectional traffic on the same connection) |
| Partner device | Microscan Ethernet TCP/IP barcode scanner (MS-2, MS-3, MS-4, ID-20, ID-30, ID-40, V420, V430 families) |
| Protocol | Raw TCP (RFC 793), no application layer encapsulation - no ISO-on-TCP, no Modbus/TCP wrapper |
| Default scanner port | TCP 2001 (Microscan factory default) - configurable via ESP or web UI |
| Default PLC port (passive) | Any unused TCP port above 1024 - typically 2000, 2001, 2002, or 3000 series |
| Max concurrent OUC connections | 8 on CPU 1214C, fewer on 1211C/1212C (see CPU-specific manual) |
Root Cause: The DATA Pin Assignment
The TRCV_C instruction is implemented as a self-contained compound FB that performs both TCP connection management and payload buffering. Per the official Siemens documentation for the SIMATIC S7-1200 manual collection, TRCV_C interprets the DATA input as the absolute start address and length of a contiguous receive buffer within the work memory of the S7-1200. The block then uses the difference between the buffer size and the currently-used offset to decide how many bytes can still be accepted in the current ad-hoc frame.
When a user drops a tag of type Array[0..199] of Byte onto the DATA pin and TIA Portal auto-resolves it to MyArray[0] (the first element only), the block sees the receive buffer as a one-byte area located at the start of the array. Two distinct failure modes follow:
- Ad-hoc mode (LEN = 0): The block is told it has one byte of buffer, so it is willing to accept only a single byte per call. Because barcode payloads are typically 10-60 ASCII characters (and can be up to 255 characters with certain 2D codes), the arriving data is silently truncated to one byte and the rest is held in the internal TCP receive FIFO without ever being written back to the user tag. RCV_LEN may briefly report 1, but if the program reads it before the next OB1 cycle, it shows 0 because the next TRCV_C invocation re-arms the buffer pointer and clears the bookkeeping.
-
Length-specified mode (LEN > 0): The static length at the LEN input disagrees with the dynamic size derived from the 1-byte buffer at the DATA pin, so TRCV_C reports
16#8088(STATUS) with ERROR = TRUE. This is the secondary symptom most often reported together with the empty buffer.
The correct binding is to assign the entire symbolic array tag to the DATA pin. In the TIA Portal variable-selection dialog, this is done by clicking the array name itself rather than expanding the [...] node. Once the full array is bound, the block can compute a buffer size equal to the array length, and the ad-hoc receive works against the entire area.
"DB_Scan".rcvBuf) and not "DB_Scan".rcvBuf[0]. If the tooltip shows an index, the binding is wrong and TRCV_C will silently behave as a one-byte receiver.TRCV_C Parameter Reference
The following table lists every input and output of the TRCV_C block that is relevant to this fix, with the data type, direction, and functional meaning. Reference: Siemens Support - TRCV_C: Establishing a connection and receiving data (S7-1200).
| Parameter | Direction | Type | Meaning |
|---|---|---|---|
REQ |
Input | BOOL | Rising edge starts a new receive job. In ad-hoc mode keep REQ = TRUE and let TRCV_C manage internally. |
CONT |
Input | BOOL | Keep connection open after job completion. Must remain TRUE for sustained scanner traffic. |
LEN |
Input | UINT | Length to receive. 0 = ad-hoc (variable length, controlled by DATA buffer size). 1 - 8192 = fixed length protocol. |
DATA |
InOut | VARIANT | Receive buffer. Must be the whole array (e.g. DB_Scan.rcvBuf), not an indexed element. |
CONNECT |
Input | BOOL |
TRUE = establish / maintain connection, FALSE = tear down. |
ID |
Input | WORD | Connection identifier 1-16 (S7-1200), tied to TCON_IP_v4 / TCON parameters. |
Connection |
InOut | VARIANT | Pointer to the connection description DB (e.g. TCON_IP_V4). |
DONE |
Output | BOOL | One-shot pulse when a frame has been received successfully. |
BUSY |
Output | BOOL |
TRUE while a job is in progress. |
ERROR |
Output | BOOL |
TRUE when the last job terminated with an error (see STATUS). |
STATUS |
Output | WORD | Status / error code. 16#7006 = NO_DATA, no payload available yet. |
RCVD_LEN |
Output | UINT | Number of bytes actually received in the most recent frame. |
Solution: Link the Whole Array to the DATA Pin
Open the TRCV_C instance in the LAD/FBD editor. Re-wire the DATA input as follows:
- In the project tree, open
Program blocks > DB_Scan(your receive data block). - Click directly on the array tag name (e.g.
rcvBuf) - do not expand the[0..199]array node to drill into the first element. - Drag the array tag (or the name itself) onto the DATA input of TRCV_C. The input field will display the symbolic name without any trailing
[n]. - Confirm with the tooltip: hover the DATA pin; the tooltip must show
"DB_Scan".rcvBufonly. - Set LEN to
0for ad-hoc mode. - Compile the project (Project > Compile > Software), download, and STOP/RUN the CPU to force a full reinitialization of the connection.
The block now sees a 200-byte (or whatever the array size is) contiguous buffer in the work memory and is allowed to receive up to that many bytes in a single ad-hoc frame. The DONE bit will pulse for one OB1 cycle when a frame has been written, RCVD_LEN will reflect the actual payload size, and the bytes will be visible in the data block from rcvBuf[0] upward.
STRING tag or a STRUCT tag, but the same rule applies: bind the whole STRING variable or the whole STRUCT variable, not a sub-element. The legacy documentation explicitly notes that TRCV_C will not receive data into Boolean locations.LEN Parameter and Ad-hoc Mode
The LEN input selects between two protocol variants. Both variants rely on the same underlying TCP socket, but they differ in how the length of each receive frame is determined.
| LEN value | Protocol variant | Behavior |
|---|---|---|
0 |
Ad-hoc mode | Length is determined by the number of bytes that arrive from the partner between two OB1 cycles, bounded by the size of the DATA buffer. Recommended for barcode scanners where each scan produces a variable-length payload. |
1 - 8192 |
Length-specified mode | TRCV_C will only return DONE after exactly LEN bytes have been received. Used for fixed-length protocol frames. |
65535 |
Ad-hoc mode (older TIA Portal V11 - V12 convention) | Historical alias for LEN = 0. Replaced by LEN = 0 in V13 and later. Setting LEN = 65535 on V13+ typically produces error 16#80B5 or 16#8088. |
For Microscan scanners that fire a single ASCII string terminated by a CR/LF or by a configurable suffix, ad-hoc mode (LEN = 0) is the right choice. The block will return DONE as soon as the partner closes the write side of the frame or the OS hands off the buffered bytes.
TRUE. This is rarely needed for barcode payload reception.Status and Error Code Reference
The following are the STATUS values most commonly observed when TRCV_C is used as the receive block for an external TCP partner such as a Microscan scanner. Reference: TIA Portal - Legacy TSEND_C and TRCV_C instructions.
| STATUS (hex) | STATUS (dec) | Meaning |
|---|---|---|
| 7000 | 28672 | Block not active, REQ = 0, no connection. |
| 7001 | 28673 | First call, connection establishment started. |
| 7002 | 28674 | Connection establishment in progress, awaiting partner. |
| 7003 | 28675 | Connection established, no receive job active. |
| 7004 | 28676 | Connection terminated cleanly. |
| 7005 | 28677 | Connection established, receive path ready. |
| 7006 | 28678 | NO_DATA - connection established, receive job active, no new payload has been received. This is the value reported in the field symptom; it is not itself an error. |
| 80A1 | 32929 | Connection terminated by partner, no more data available. |
| 80A2 | 32930 | Local connection error, partner did not acknowledge FIN. |
| 80A3 | 32931 | Connection aborted locally or by partner, receive buffer locked. |
| 80A4 | 32932 | IP address of partner not assigned / not reachable. |
| 80A7 | 32935 | Connection terminated by partner, restart required. |
| 80A8 | 32936 | Local connection abort, frame error. |
| 80A9 | 32937 | Remote connection abort, frame error. |
| 80AA | 32938 | Local connection abort, no resources. |
| 80AB | 32939 | Remote connection abort, no resources. |
| 80AC | 32940 | Local connection abort, ARP failure. |
| 80AD | 32941 | Remote connection abort, ARP failure. |
| 80AE | 32942 | Local connection abort, no TCP socket available. |
| 80AF | 32943 | Connection ID already in use by another block. |
| 80B0 | 32944 | Connection establishment in progress, awaiting CONNECT. |
| 80B1 | 32945 | Establishment failed, no free connection resource. |
| 80B2 | 32946 | Establishment failed, parameter assignment error. |
| 80B3 | 32947 | Establishment aborted, no further resources. |
| 80B4 | 32948 | Connection limit reached (max 8 active OUC connections on S7-1200). |
| 80B5 | 32949 | Parameter assignment error in the connection description DB (e.g. invalid LEN, port out of range). |
| 8088 | 32904 | LEN parameter does not correspond to the receive area set at the DATA parameter (e.g. LEN greater than array size, or DATA bound to a sub-element). |
| 80C0 | 32960 | Temporary resource error, retry on next cycle. |
| 80C1 | 32961 | Temporary resource error, retry on next cycle. |
| 80C2 | 32962 | Temporary resource error, retry on next cycle. |
| 80C3 | 32963 | Temporary resource error, retry on next cycle. |
| 80C4 | 32964 | Internal system error, firmware update recommended. |
Microscan Scanner Ethernet Configuration
Before chasing the TRCV_C binding problem, confirm the scanner side is configured to push data unsolicited on TCP. A Microscan scanner is normally configured through the ESP (Easy Setup Program) desktop utility, through the on-board web interface (default 192.168.1.20:80), or through the scanner's serial configuration menu accessed via the configuration bar code. The relevant settings are:
| Setting | Recommended value | Comment |
|---|---|---|
| IP Address |
192.168.1.20 (example) |
Must be on the same subnet as the S7-1200 PN interface. |
| Subnet Mask | 255.255.255.0 |
Match PLC subnet. |
| Default Gateway |
192.168.1.1 or empty |
Required only if the scanner must reach a host outside the local subnet. |
| Protocol | TCP Server (default) or TCP Client (if scanner is to dial out) | For unsolicited push on trigger, set the scanner as TCP Server, then have the S7-1200 issue an active connect via CONNECT = TRUE. |
| Destination IP | PLC IP address (192.168.1.10) |
Only relevant if scanner is TCP Client. |
| Destination Port | PLC port (e.g. 2000) |
Only relevant if scanner is TCP Client. PLC must be in passive (server) mode. |
| Local Port (TCP Server) |
2001 (Microscan factory default) |
PLC must connect to this port from the active side. |
| End of Message Suffix |
CR or CR LF
|
Optional. S7-1200 TRCV_C will deliver everything received as one ad-hoc frame regardless. |
| Data Format | ASCII string (readable) - not binary | Microscan default. |
| Trigger Mode | External edge, level, or serial command | Scanner fires payload on hardware or software trigger. |
If the scanner is left in its factory-default TCP Server mode on port 2001, the S7-1200 program should establish the connection actively by leaving CONNECT = TRUE and populating the TCON_IP_V4 connection parameter DB with ActiveEstablishment = TRUE, RemoteAddress = "192.168.1.20", and RemotePort = 2001. The first TRCV_C call will open the socket; subsequent calls just receive.
Step-by-Step Fix and Verification Procedure
Use this checklist to apply the fix and to prove the receive path is end-to-end functional on the live network.
- Place the CPU in STOP, open the TIA Portal project, and download the project.
- Open the FB / OB that contains TRCV_C in the LAD or FBD editor.
- Click the DATA input of TRCV_C and delete the existing wire.
- From the project tree, expand the receive DB (e.g.
DB_Scan), then drag the array tag (e.g.rcvBuf : Array[0..199] of Byte) - not the elementrcvBuf[0]- onto the DATA input. - Verify with the tooltip that the binding reads
"DB_Scan".rcvBufwithout an index. - Set LEN to
0for ad-hoc mode. - Confirm the connection DB (e.g.
TCON_IP_V4) hasActiveEstablishment = TRUE,RemoteAddress = "192.168.1.20",RemotePort = 2001, and a uniqueID(e.g.1) that matches the ID input of TRCV_C. - Compile the project (Project > Compile > Software).
- Download the new build to the S7-1200 and STOP/RUN the CPU to force a full reinitialization of the connection resource.
- Open an online watch table on the TRCV_C instance. Monitor
STATUS,ERROR,RCVD_LEN, and the first 16 bytes ofrcvBuf. - Trigger the Microscan scanner with a known bar code (e.g.
123456789012). STATUS should remain16#7006between scans, DONE should pulse TRUE for one OB1 cycle on receipt, RCVD_LEN should report the number of bytes in the payload (e.g. 12 for the 12-digit code), and the bytes inrcvBuf[0..11]should be ASCII 0x31, 0x32, 0x33, ... 0x32. - If STATUS remains
16#8088, the LEN/DATA binding is still wrong. Recheck the tooltip and recompile. - If STATUS reports any value from the
80Axor80Bxfamily, consult the Status and Error Code Reference above to isolate the network-layer fault.
Common Pitfalls and Edge Cases
- Indexing the array in the variable selector. The single most common cause of the empty-buffer symptom. The fix is to drop the array itself, not an element.
- Passing a BOOL or a single BYTE tag at DATA. The Siemens manual explicitly states that TRCV_C will not receive data into Boolean locations. Use a non-scalar type (ARRAY of BYTE, ARRAY of CHAR, or STRING).
- Using a STRING with too small a maximum length. A STRING of length 10 cannot hold a 16-character payload; the data is silently truncated. Size the STRING to the maximum scan length plus 2 bytes for the Siemens STRING header.
- Forgetting to leave REQ = TRUE. In ad-hoc mode, REQ must remain TRUE for the block to keep listening. Latching REQ high in OB1 is the correct pattern - one-shot rising-edge calls are for length-specified mode only.
- Calling TRCV_C in a non-cyclic OB. TRCV_C must run in a cyclic class of OB (OB1, OB3x, OB8x). Calling it in OB100 (startup) or OB121 (error) will not deliver ongoing data.
- Not performing a STOP/RUN transition after download. TIA Portal V13 SP1 sometimes retains stale connection state in the S7-1200 firmware; a power cycle or STOP → RUN transition is required to reinitialize the connection description DB.
-
Multiple blocks competing for the same connection ID. The S7-1200 supports up to 8 open OUC connections (depending on CPU type). Each TSEND_C / TRCV_C pair must use a unique ID; otherwise STATUS reports
16#80AF"Connection ID already in use". -
Scanner configured as TCP Client with no active listener on the PLC. If the scanner is set to TCP Client and the PLC side is configured passively, the PLC must already be in LISTEN before the scanner dials. Use TRCV_C with
ActiveEstablishment = FALSEin the TCON_IP_V4 structure. - Firewall or managed switch blocking TCP traffic on port 2001. On a plant network, ensure the path between the PLC and the scanner has no ACL dropping the port.
- VLAN mismatch. The S7-1200 PN interface is single-VLAN-aware; if the scanner is on a different VLAN, the PROFINET interface must be configured for that VLAN ID in the device properties.
- Symbolic access disabled on the receive DB. The DATA input of TRCV_C requires symbolic access on the destination DB. If the DB property "Optimized block access" is set incorrectly, or "Accessible from HMI/OPC UA" interferes, the bind may fail silently. Verify under DB > Properties > Attributes.
- Retain attribute interfering with the buffer. If the receive DB has "Retain" enabled, the previous payload survives a power cycle and may look like a working receive even when the new one is not arriving. Disable Retain on the buffer DB or zero the array in startup.
Migrating to Newer TIA Portal Versions
TRCV_C is the legacy "compound" block (connect + send/receive in one call) and remains the recommended entry point for simple scanner integration on TIA Portal V13 - V18. For users on V15.1 or later, Siemens additionally offers the pair TCON + TRCV (split into separate connection management and receive blocks) which expose the same parameters but allow the connection to be shared with TSEND on the same ID. The behavior at the DATA pin is identical: bind the whole ARRAY tag, set LEN = 0 for ad-hoc, and verify with the tooltip.
When migrating an existing project from V13 SP1 to V17 / V18, pay attention to the following points:
- Connection parameter DBs (TCON_IP_V4) created in V13 SP1 are forward-compatible; no recreation is needed unless the firmware of the S7-1200 was also upgraded to V4.5 or higher.
- TRCV_C block version 4.0 is replaced by 4.1 / 4.2 in newer TIA Portal versions but the call interface is identical - no code change is required.
- TSAP / port-handling changed in V14: the LocalPort and RemotePort fields in the TCON_IP_V4 structure now accept both decimal and hexadecimal string values; older projects stored them as decimal strings, which can be silently misinterpreted after migration.
- If the project is converted to a V17/V18 PC-based WinCC Runtime or to a PLCSIM instance, verify that the simulation profile includes the PROFINET interface and that the firewall on the engineering PC allows the loopback TCP port.
For full reference of the V13 SP1 - V18 block interface, consult the official TIA Portal manual collection: Legacy TSEND_C and TRCV_C instructions and the Siemens support entry for TRCV_C on the S7-1200.
Frequently Asked Questions
What does STATUS 16#7006 mean on TRCV_C, and is it an error?
STATUS 16#7006 (decimal 28678) is the NO_DATA state. The TCP connection is open and the receive job is armed, but no new payload has arrived from the partner since the last call. It is not an error; it is a steady-state value you will see most of the time on a quiet scanner. Only when the scanner triggers and DONE does not pulse should you treat the symptom as a fault.
Why does ERROR 16#8088 appear when I set LEN to a non-zero value?
ERROR 16#8088 means the LEN input does not match the size of the buffer at the DATA pin. With a whole ARRAY bound at DATA, LEN must be between 0 and the size of the array (e.g. 0 - 200 for Array[0..199] of Byte). Any LEN greater than the array size triggers the error. Use LEN = 0 for ad-hoc mode when the payload length varies from scan to scan.
Can I use a STRING tag instead of an ARRAY at the DATA pin?
Yes. TRCV_C accepts a STRING tag. The block writes the incoming bytes into the STRING's character area (after the two-byte Siemens header). The same rule applies: bind the whole STRING tag at DATA, not a sub-element, and use a STRING with a maximum length greater than the longest expected payload.
Does this same fix apply to the newer TRCV instruction (TCON + TRCV)?
Yes. The TCON / TRCV pair follows identical rules. Bind the whole ARRAY or STRING at the DATA input, set LEN = 0 for ad-hoc mode, and verify the tooltip shows the full symbolic tag name without an index.
Why does RCV_LEN read 0 even though STATUS is 7006?
RCVD_LEN is a one-shot output: it shows the number of bytes received in the last completed frame. Between frames it holds the last value (which can be 0 if no frame has yet been completed) until the next DONE pulse updates it. To catch a frame, monitor the rising edge of DONE and snapshot RCVD_LEN in the same OB1 cycle.