Configuring Variable S5T# Timers in Siemens STL: ITB Method

David Krause14 min read
HMI ProgrammingSiemensTutorial / How-to
Licensed PE Working through this on a live machine? A Maine-licensed engineer can take it from here — included with IMD hardware, by the hour for everything else. Book an engineer

Overview

Siemens SIMATIC S7-300, S7-400, S7-1200, and S7-1500 controllers expose two distinct time-data families. The modern IEC 61131-3 TIME type is a 32-bit signed DINT in milliseconds, accepts any variable tag as input, and is consumed by the TON, TOF, TP, and TONR IEC timer instructions. The legacy S5TIME (printed as S5T#) is a 16-bit word that combines a 2-bit time-base selector with a 3-digit BCD value; it is consumed by the legacy timer instructions SD, SS, SP, SE, SA, and SF.

The S5T# syntax is a literal: the compiler parses the token after the hash as a fixed time constant at edit time, then emits a 16-bit word constant. The compiler does not interpret S5T#MW300 as "the value currently held in MW300" — that source line fails to compile, because the lexical analyzer expects a literal duration (for example S5T#5m or S5T#1h30m).

The standard remedy is to construct the S5TIME word at runtime. The procedure is to load a SCADA-supplied DINT (typically in minutes), scale it into the chosen time-base units, convert the integer to BCD with the ITB instruction, OR in the time-base mask with OW, and feed the resulting word to SD. This article documents the procedure for the 1–60 minute range, the time-base choices, edge cases, and verification steps for S7-300/S7-400 and S7-1500 STL programs.

S5TIME Bit Layout and Encoding

S5TIME occupies a single 16-bit word. Bits 15 and 14 select one of four time bases; bit 13 is reserved and must be zero; bits 12–0 carry a BCD value in the range 0–999. The structure is shown below.

15..14 13..0 Time base BCD value (0..999)

The four time-base codes are summarized below.

Bit 15 Bit 14 Time Base Resolution Minimum Maximum (BCD 999) Mask Word
0 0 10 ms 0.01 s 10 ms 9.99 s W#16#0000
0 1 100 ms 0.1 s 100 ms 99.9 s (1 m 39.9 s) W#16#4000
1 0 1 s 1 s 1 s 999 s (16 m 39 s) W#16#8000
1 1 10 s 10 s 10 s 9990 s (2 h 46 m 30 s) W#16#C000

The mask words listed in the right column are used with OW to set the time-base bits while leaving the BCD field untouched.

BCD Encoding Rules

Each decimal digit occupies four bits. The value 360 is encoded as 0011 0110 0000 (3, 6, 0 — twelve bits, occupying bits 11–0 of the S5TIME word). Any attempt to write hex digits A through F into the BCD field is illegal and is rejected by the SD/SS/SP/SE/SA/SF instructions at runtime, or produces a value that decays as garbage.

Why S5T# Cannot Reference a Variable Tag

The S5T# syntax is a literal token in STL. The compiler's lexical analyzer reads the characters after S5T# as a fixed time specification (number plus optional unit suffix). Examples accepted by the compiler:

S5T#2s // 2 seconds: base 1s, BCD 2 -> W#16#2002
S5T#500ms // 500 ms: base 100 ms, BCD 5 -> W#16#4005
S5T#1h30m // 90 min: base 10s, BCD 540 -> W#16#C540

The compiler does not resolve S5T#MW300, S5T#"scadaValue", or any other tag reference. Even at runtime, the SD/SS/SP/SE/SA/SF timer instructions read the time value from the low word of ACCU1 — they do not support tag indirection at the syntax level.

The solution is to construct the word explicitly using ITB, OW, and L/T operations as documented below.

Prerequisites

  • STEP 7 (TIA Portal) V13 SP1 or later; procedure verified against V17 and V20.
  • PLC: S7-300, S7-400, S7-1200 (with S5 timers enabled in CPU properties), or S7-1500 CPU.
  • STL editor enabled in TIA Portal: Options → Settings → PLC programming → STL/FBD/LAD.
  • SCADA or HMI tag supplying a DINT in minutes (1–60). Typical sources: WinCC, TIA Portal HMI, or third-party SCADA via OPC UA or Modbus TCP.
  • Free timer cell (e.g., T1) and a free memory word (e.g., MW100) for the constructed S5TIME word.
  • PLC and HMI connected via PROFINET, PROFIBUS, or MPI.

ITB and SD Instruction Reference

ITB — Integer to BCD

The ITB instruction converts the 32-bit signed integer in ACCU1 into its Binary-Coded-Decimal equivalent and writes the result back to ACCU1. For positive values up to 9 999 999, the BCD representation fits in the low 28 bits. For our use case (values up to 360), the BCD value occupies only the low 16 bits of ACCU1.

Behavior:

  • Sets OV (overflow) and OS (overflow latched) if the integer magnitude exceeds ±99 999 999 (beyond BCD capacity).
  • Does not modify ACCU2.
  • ENO is not relevant in STL context.

Examples:

L 50 // ACCU1-L = 0x0032 (hex) = 50 (dec)
ITB // ACCU1-L = 0x0050 (BCD representation of 50)

L 360 // ACCU1-L = 0x0168 (hex)
ITB // ACCU1-L = 0x0360 (BCD of 360)

SD — Start On-Delay Timer

Per the Siemens TIA Portal V20 STL documentation for S7-1500, the SD instruction starts the addressed timer when a "1" is detected at the start input. The time value is read from the low word of ACCU1 and interpreted as S5TIME (time base + BCD value). The current timer value can be read in BCD format from the corresponding timer word (TW); for example, MW10 for T1 on many S7-300 CPUs.

Timer word readback in S5TIME format:

  • MW contains bits 15–14 = current time base, bits 12–0 = current value in BCD.
  • The value decreases as the timer runs, in units of the selected time base.
  • When the value reaches zero, the timer output Q becomes "1".

Step-by-Step: DINT Minutes (1–60) to S5TIME

The 1–60 minute range requires the 10-second time base (bit pattern 11, mask W#16#C000). The 1-second base caps at 999 seconds (16 min 39 s), which is insufficient for the full range. The conversion procedure scales the minute count by 6 (to convert minutes into 10-second units), then encodes with ITB and OW.

  1. Load the minute DINT from the SCADA tag into ACCU1.
  2. Load the multiplier 6 into ACCU1 (shifts previous value to ACCU2).
  3. Multiply integers with *I: ACCU2-L × ACCU1-L → ACCU1-L.
  4. Convert ACCU1-L to BCD with ITB.
  5. Load the time-base mask W#16#C000.
  6. OR the low word with OW.
  7. Transfer the constructed S5TIME word to a memory location (e.g., MW100).
  8. Load the start input condition (e.g., A "timerRun").
  9. Load MW100 and start the timer with SD T1.
Important: If the OW step is omitted, the timer word retains time-base bits 00 (10 ms). A value of 5 in the low word would then yield a 50 ms pulse, not a 5-minute delay. This is the most common mistake when porting S5TIME code from a constant to a variable tag.

Complete STL Code Example

// Title: Variable S5TIME for SD T1 (1..60 min from SCADA)
// Inputs:
// "scadaMinutes" : DINT (1..60)
// "timerRun"     : BOOL start trigger
// Outputs:
// T1.Q = 1 when "scadaMinutes" worth of 10-s ticks elapse
// MW100 holds the constructed S5TIME word (debug visibility)
// Requires a tag table with "scadaMinutes" and "timerRun"

// 1. Build the S5TIME word
L "scadaMinutes" // load SCADA-supplied minutes (DINT)
L 6 // multiplier: minutes -> 10-second units
*I // ACCU1 = minutes × 6 (must be <= 999)
ITB // ACCU1 = BCD value
L W#16#C000 // 10-second time-base mask
OW // OR the low word with the time-base bits
T MW 100 // store constructed S5TIME for monitoring

// 2. Drive the timer
A "timerRun" // start input condition
L MW 100 // load S5TIME word
SD T 1 // start on-delay timer T1

// 3. Optional: read current timer value as DINT (ms)
L T 1 // load T1's binary time value (DINT, ms)
T MW 104 // store for HMI display in milliseconds

The commented block demonstrates the standard procedure. The optional readback at the end places the current value in milliseconds (DINT) into MW104 for HMI display, avoiding BCD interpretation overhead on the SCADA side.

Working Examples by Minute Value

scadaMinutes (DINT) × 6 (10-s units) BCD Mask OR MW100 (HEX) Real Time
1 6 0x006 0xC000 W#16#C006 60 s (1 min)
5 30 0x030 0xC000 W#16#C030 300 s (5 min)
10 60 0x060 0xC000 W#16#C060 600 s (10 min)
15 90 0x090 0xC000 W#16#C090 900 s (15 min)
30 180 0x180 0xC000 W#16#C180 1800 s (30 min)
45 270 0x270 0xC000 W#16#C270 2700 s (45 min)
60 360 0x360 0xC000 W#16#C360 3600 s (60 min)

Time Base Selection Guide

Select the smallest time base that covers the full dynamic range with acceptable resolution. The trade-off is precision versus maximum range:

Application Range Time Base Resolution Mask Scaling from Minutes
0–9.99 s 10 ms 10 ms W#16#0000 min × 6000
0–99.9 s 100 ms 100 ms W#16#4000 min × 600
0–999 s (16.65 min) 1 s 1 s W#16#8000 min × 60
0–9990 s (166.5 min) 10 s 10 s W#16#C000 min × 6

For the 1–60 minute range, the 10-s base (mask W#16#C000) is the only choice that fits the full range without BCD overflow.

Alternative: SCADA Pre-Scaled Value

If the HMI/SCADA can deliver the value already scaled to 10-second units, the *I step is unnecessary. Configure the SCADA tag to transmit the minute value multiplied by 6, or use a separate scaling tag with a linear conversion on the HMI side.

// "scadaTenths" = DINT in 10-second units (6..360)
L "scadaTenths"
ITB
L W#16#C000
OW
T MW 100
A "timerRun"
L MW 100
SD T 1

The advantage is fewer CPU instructions per scan. The disadvantage is that the SCADA tag no longer represents a human-readable quantity, which complicates diagnostics.

Alternative: Pre-Built Lookup Table

If the time selection is from a fixed list (for example, user picks 5/15/30/60 minutes from a drop-down), the S5TIME word can be selected by index from a data block — no ITB required.

// DB50 layout: 4 WORD entries (W#16#C030, W#16#C090, W#16#C180, W#16#C360)
OPN DB 50 // open lookup DB
L "timeIndex" // INT 0..3
SLD 3 // multiply by 8 (bytes per DBW) — adjust to entry size
LAR1 // pointer to DBW in AR1
L DBW [AR1,P#0.0] // load pre-built S5TIME word from DB
T MW 100
A "timerRun"
L MW 100
SD T 1

This approach avoids the ITB step entirely and centralizes the time word constants in a data block, making them easy to audit and modify.

Edge Cases and Limits

BCD Overflow

Values producing BCD > 999 cannot be encoded in S5TIME. With the 10-s base, the limit is 9990 s = 166 min 30 s. A SCADA value of 167 minutes × 6 = 1002 overflows the BCD field. Mitigation: clamp the input at 166 minutes, use cascaded SD calls for longer durations, or switch to an IEC timer (TP/TON/TOF) with the TIME type (32-bit DINT in milliseconds, range up to 24 d 20 h 31 m 23 s 647 ms).

Negative or Zero Input

S5TIME accepts only positive BCD values. A SCADA input of 0 results in immediate timer expiry (output Q becomes "1" on the next scan). A negative input (possible from a faulty SCADA calculation) is treated as a very large unsigned value and produces unpredictable behavior. Mitigation: validate the SCADA tag with a limit check before ITB.

// Validate before scaling
L "scadaMinutes"
L 1
<I // ACCU2-L < ACCU1-L?
JC errTooSmall // jump to error handler if scadaMinutes < 1
L 60
>I // ACCU2-L > ACCU1-L?
JC errTooLarge // jump to error handler if scadaMinutes > 60

CPU-Specific Timer Cell Count

The number of available SD timer cells is CPU-dependent:

CPU Family Typical Timer Count
S7-312 128
S7-315-2 PN/DP 256
S7-317 / S7-319 512
S7-1511 / S7-1513 2048
S7-1516 / S7-1518 2048

For applications requiring more than the available timer cells, use the IEC TP/TON/TOF instructions which share the same internal pool but have a more flexible memory footprint.

S7-1200 Restrictions

The S7-1200 in TIA Portal V13–V16 does not expose legacy S5 timer instructions (SD/SS/SP/SE/SA/SF) by default. In V17 and later, the legacy timers may be enabled via the CPU properties, but the recommended approach on S7-1200 remains the IEC timer family.

Modern Alternative: IEC Timers (TP, TON, TOF)

For new development on S7-1200 and S7-1500, prefer the IEC 61131-3 timer family. The TIME data type is a 32-bit signed DINT in milliseconds and accepts a variable tag directly without BCD manipulation. A 60-minute value is simply T#60m or a variable DINT of 3 600 000.

// IEC TON (on-delay timer) on S7-1500 with variable DINT
A "timerRun"
TON "myTimer", "scadaTimeMS" // tag "scadaTimeMS" = DINT milliseconds
// "scadaTimeMS" = scadaMinutes × 60000 (scaling done once in SCADA or in cycled FB)

Reserve S5TIME/SD for legacy migration and existing code paths. Conversion of legacy SD code to TON is typically a one-line change plus the data-type swap.

Verification Procedure

  1. Compile and download the STL program to the PLC (or PLCSIM instance).
  2. Open a Watch Table in TIA Portal and add the following tags:
    • "scadaMinutes" (DINT) — modify = 5 for initial test.
    • "timerRun" (BOOL) — modify = TRUE.
    • MW100 (WORD) — display in HEX format.
    • T1 (TIMER) — status and current value.
    • MW10 (WORD) — T1's timer word, display in HEX.
  3. Set "scadaMinutes" = 5 and "timerRun" = TRUE. Observe MW100 in HEX; confirm the value matches W#16#C030 (base 10s, BCD 30, equal to 300 s = 5 min).
  4. Monitor T1.Q transitions; it should rise to TRUE after approximately 300 seconds.
  5. Read MW10 (timer word) during the run; the BCD value should decrement from 30 to 0 in 10-second steps.
  6. Repeat for scadaMinutes = 1, 30, and 60; verify against the table in the "Working Examples" section.
  7. Test the edge cases: scadaMinutes = 0 (immediate fire), scadaMinutes = 1000 (BCD overflow — should be clamped or rejected).

Troubleshooting Matrix

Symptom Root Cause Correction
Compile error: "S5T#MW300 invalid syntax" S5T# accepts only literals, not tag references Build the word at runtime using ITB/OW as shown
Timer fires after 50 ms instead of 5 min Time-base bits = 00 (10 ms) because OW was skipped Always OR with W#16#C000 (or the appropriate base mask)
Timer never reaches Q=1 BCD overflow from value > 999 (OV bit set) Clamp the SCADA input; verify scaling factor
Timer fires after wrong duration (e.g., 6 s instead of 1 min) Forgot to multiply minutes by 6 before ITB Insert L 6 *I before ITB, or pre-scale the SCADA value
Watch table shows MW100 as decimal 9999 instead of W#16#C006 Watch table set to DEC instead of HEX Right-click the column header, select HEX
BCD digit 0xA–0xF appears in MW10 SCADA sent a value exceeding BCD range Add a limit check before ITB; reject values > 166 min
Time drifts by ±1 s per cycle 10-s resolution rounding inherent to S5TIME base 11 Acceptable per spec; switch to IEC TON with TIME for finer resolution
OV/BR flags set after ITB Input value outside ±99 999 999 Verify SCADA scaling; check for sign-extension errors
S7-1200 does not show SD in instruction list Legacy S5 timers disabled in CPU properties Enable in CPU properties → Timer, or switch to IEC TON
SCADA value updated but timer duration unchanged Word MW100 not reloaded before SD; old timer still running Reset T1 with RA before reloading, or use a fresh timer cell

Frequently Asked Questions

Why does the compiler reject S5T#MW300 in STL?

S5T# is a literal token parsed by the compiler at edit time; only fixed time values like S5T#5m are accepted. Variable timing requires runtime construction of the 16-bit word using ITB, OW, and L/T operations.

Which time base do I need for a 1–60 minute timer?

The 10-second time base (bits 15-14 = 11, mask W#16#C000) is required because the 1-second base caps at 999 seconds (16 min 39 s). The 10-s base covers up to 9990 seconds (166.5 min).

Can the multiply-by-6 step be avoided?

Yes. Configure the SCADA tag to deliver the value already scaled to 10-second units (minutes × 6), or use a lookup DB with pre-built S5TIME words selected by index.

Does SD still work on S7-1500 in TIA Portal V20?

Yes. SD (Start on-delay timer) is part of the legacy timer operations supported in STL on S7-1500 per official Siemens documentation. New development should still prefer IEC TON/TP/TOF with the TIME data type.

What is the maximum S5TIME duration on any CPU?

The hard maximum is 9990 seconds (2 h 46 min 30 s) using the 10-s base with BCD value 999. For longer durations, cascade SD calls, use multiple timers, or switch to an IEC timer with TIME (DINT ms), which supports durations up to 24 d 20 h 31 min 23 s 647 ms.

How do I monitor the S5TIME word during runtime?

Open a Watch Table in TIA Portal, add the timer word MW (e.g., MW10 for T1), and switch the display format to HEX. The high nibble of the high byte shows the time base (0xC = 10 s); the low 12 bits show the BCD value.

Back to blog