S7-1200 Programming Languages: What STEP 7 Officially Supports
The SIMATIC S7-1200 compact controller is programmed exclusively through the Totally Integrated Automation (TIA) Portal. According to the official SIMATIC S7-1200 manual collection (entry ID 109759862) on Siemens Industry Online Support, STEP 7 provides a defined set of standard programming languages for the S7-1200, with LAD (Ladder Logic) defined as a graphical programming language. The same manual collection is mirrored on the TIA Siemens Cloud documentation portal.
The standard language set engineers can deploy on an S7-1200 today includes:
| Language | Type | Notation | Typical Use Case |
|---|---|---|---|
| LAD (Ladder Logic) | Graphical | Contacts / coils | Boolean logic, interlocks, motor start/stop |
| FBD (Function Block Diagram) | Graphical | Function boxes with EN/ENO | Arithmetic, signal processing |
| SCL (Structured Control Language) | Textual, high-level | Pascal-like syntax | Data handling, loops, math, string operations |
| STL (Statement List) | Textual, low-level | Mnemonic | Bit-level manipulation (STEP 7 Professional only, FW 4.2+) |
GRAPH (sequential function chart) targets the S7-1500 family by default; it is not the recommended path on the S7-1200. C is not part of this language set. There is no C compiler, no C runtime, and no native C execution environment shipped on any S7-1200 CPU firmware image.
Why Direct C Execution Is Not Available on the S7-1200
The S7-1200 executes a compiled, cyclic, IEC 61131-3 firmware image. The CPU boots into a Siemens-proprietary runtime that interprets or executes pre-compiled STEP 7 blocks (OB, FB, FC, DB). The firmware is closed; the controller has no loader that would accept an arbitrary ELF, COFF, or PE object produced by gcc, clang, or IAR. There is no JTAG, no bootloader entry, and no engineering pathway to substitute user-supplied machine code.
Three architectural constraints make native C execution infeasible on the S7-1200:
- No memory model for a C heap. The work memory is partitioned into code, data, and retentive areas with fixed boundaries enforced at download time. There is no malloc/free subsystem exposed to user code.
- No standard C library linkage. libc, libm, and POSIX headers are not present. printf() must be replaced with Siemens-supplied system functions, HMI blocks, or serial-write blocks.
- No deterministic interrupt model for arbitrary C handlers. The S7-1200 OB priority model (OB1 cyclic, OB35 cyclic interrupt, OB82 diagnostic, OB121 programming error) is the only legal entry point for user code.
SCL: The Closest High-Level Alternative to C
SCL (Structured Control Language) is the textual, Pascal-like language that ships with STEP 7 Professional and is the closest analog to C on the S7-1200. The syntax differs in three important ways C developers should understand:
| Concept | C | SCL |
|---|---|---|
| Block delimiter | { } curly braces | BEGIN ... END_FUNCTION or END_IF |
| Assignment | = | := (Pascal assignment operator) |
| Equality test | == | = |
| Variable declaration | type name = value; | name : type := value; |
| Function block | struct + function pointers | FB with VAR_INPUT / VAR_OUTPUT / STAT |
| Loop constructs | while / for / do-while | WHILE / FOR / REPEAT ... UNTIL |
| Conditional | if (cond) {} else {} | IF cond THEN ... ELSIF ... ELSE ... END_IF; |
| CASE / switch | switch/case/default | CASE ... OF ... ELSE ... END_CASE; |
| Comment | // or /* */ | // single line only |
A complete SCL function block that emulates a typical C state machine ported to ladder-style sequencing:
FUNCTION_BLOCK "FB_StateMachine"
VAR
iState : INT := 0;
iDelay : INT;
END_VAR
BEGIN
CASE iState OF
0: // Idle
IF "iStartCmd" = TRUE THEN
iState := 1;
iDelay := 0;
END_IF;
1: // Ramp up
"qMotorSpeed" := "qMotorSpeed" + 10;
iDelay := iDelay + 1;
IF iDelay >= 50 THEN
iState := 2;
END_IF;
2: // Run
IF "iStopCmd" = TRUE THEN
iState := 3;
END_IF;
3: // Ramp down
"qMotorSpeed" := "qMotorSpeed" - 10;
IF "qMotorSpeed" <= 0 THEN
"qMotorSpeed" := 0;
iState := 0;
END_IF;
ELSE
iState := 0;
END_CASE;
END_FUNCTION_BLOCK
Compile-time errors that SCL catches which pure LAD hides include type mismatches at I/O boundaries, uninitialized variable access, and array bound violations. This is the engineering reason to prefer SCL over LAD for any non-trivial data handling.
WinAC RTX: When You Need Real C Execution
For applications where genuine C execution is non-negotiable, Siemens offers the SIMATIC WinAC RTX product line. WinAC RTX is a software PLC that runs on a Windows PC (typically an industrial PC such as the SIMATIC IPC family) and combines the WinAC RTX real-time extension with the ability to load and execute C/C++ code via the SIMATIC ODK (Open Development Kit) interface.
Key engineering constraints when sizing a WinAC RTX solution:
- Hardware: SIMATIC IPC227G, IPC427G, IPC627, or equivalent industrial PC with deterministic Ethernet.
- RTX layer: IntervalZero RTX extension handles the hard real-time partition; Windows handles HMI, logging, OPC UA.
- ODK version: SIMATIC ODK supports C/C++ function calls from STEP 7 blocks; the DLL must be signed and loaded by the WinAC RTX service.
- Latency budget: Typical PROFINET IRT cycle on a WinAC RTX system is 1 ms; the C DLL executes in a deterministic slot within the same cycle.
C-to-LAD Conversion Tools: What Exists vs. What Does Not
The premise of automated C-to-LAD translation has been investigated by both Siemens and third parties, but no production-grade converter exists for the S7-1200 as of TIA Portal V19. The reasons are fundamental:
- Semantic gap: C permits pointer arithmetic, recursion, dynamic memory, and goto. LAD has no representation for any of these. Every C construct must be re-expressed as a state machine or call-tree, which is itself a manual engineering task.
- Type system gap: C's signed/unsigned, float/double, struct/union map poorly to the S7-1200's IEC 61131-3 type system (BOOL, INT, DINT, REAL, STRING, ARRAY, STRUCT).
- Library gap: printf, malloc, file I/O have no direct IEC equivalent; manual block libraries must be created.
- Verification gap: A translated LAD program would inherit the bugs of the C source. The compiler/translator cannot prove equivalence of two different language semantics.
Academic converters and IEC 61131-3 code-generation frameworks (such as those built around Eclipse 4DIAC) target FBD/ST export from IEC 61131-3 but do not advertise reliable C-to-LAD translation for the S7-1200 platform. Siemens does not provide a C-to-LAD converter in any current TIA Portal release.
Migration Strategy: From C Source to S7-1200 Logic
The recommended engineering workflow when porting C code to the S7-1200 is structured in five phases:
- Decompose the C application into a function call tree. List every C function, its inputs, outputs, side effects, and call frequency.
- Classify each function as one of: pure boolean (map to LAD), arithmetic / data handling (map to SCL), state machine (split into OB1 logic + FB instances), time-critical closed loop (consider S7-1500 or WinAC RTX).
- Define a tag dictionary that mirrors the C global variables and structs. Each C struct becomes an S7-1200 DB (data block) of type STRUCT; each scalar becomes a tag in the default tag table or a DB.
- Translate each C function block-by-block. Boolean-heavy functions become LAD networks; arithmetic becomes SCL functions; reuse becomes FBs with instance DBs.
- Commission and verify. Mirror the C unit tests as PLC watch tables and force tables. Trigger each input combination and confirm output parity with the C reference build.
LAD Programming Quick Reference for C Developers
LAD is read left-to-right, top-to-bottom, with power flow representing logical TRUE. The basic primitives map to C control flow as follows:
| LAD Element | C Equivalent | Notes |
|---|---|---|
| NO contact (—| |—) | if (var == TRUE) | Passes power if the tag is TRUE |
| NC contact (—|/|—) | if (var == FALSE) | Passes power if the tag is FALSE |
| Coil (—( )—) | out = TRUE; | Sets the tag to TRUE while energized |
| Negated coil (—(/)—) | out = FALSE; | Sets the tag to FALSE while energized |
| Set coil (—(S)—) | out = TRUE; (latched) | Set/Reset pair forms an SR flip-flop |
| Reset coil (—(R)—) | out = FALSE; (latched) | Reset dominates Set |
| TON timer | delay(T, t) | On-delay, PT in ms |
| TOF timer | off-delay | Off-delay, PT in ms |
| CTU counter | ++counter; if >= PV... | Up counter |
| CTD counter | --counter; if <= 0... | Down counter |
A typical motor start/stop rung with overload protection in LAD notation:
Network 1: Motor seal-in
[ StopPB_NC ] [ Overload_OK ] [ SealIn_NO ] ----( Motor_Run )----[/Fault_Latch/]
Network 2: Fault latch (set/reset flip-flop)
[ Overload_Trip ] ------------------------------( S Fault_Latch )--
[ Fault_Ack ] ---------------------------------( R Fault_Latch )--
SCL Programming Quick Reference for C Developers
The most common SCL block types engineers porting from C will create are:
- FB (Function Block) - C struct with attached methods; instances are reusable via instance DBs.
- FC (Function) - C pure function; multiple return values via VAR_OUTPUT.
- OB (Organization Block) - C main(); cyclic OB1 is the default entry point.
- DB (Data Block) - C global or struct; instance DBs are auto-created per FB instance.
Sample SCL function that ports a typical C clamping macro:
FUNCTION "FC_Clamp" : INT
VAR_INPUT
iValue : INT;
iMin : INT;
iMax : INT;
END_VAR
VAR_TEMP
iResult : INT;
END_VAR
BEGIN
IF iValue < iMin THEN
iResult := iMin;
ELSIF iValue > iMax THEN
iResult := iMax;
ELSE
iResult := iValue;
END_IF;
"FC_Clamp" := iResult;
END_FUNCTION
Called from LAD as a box: EN input wired, ENO passed through, iValue/iMin/iMax wired from tag names. SCL supports RETURN for early exit, similar to a C return statement.
Data Type Mapping: C Types to S7-1200 Types
The type-system translation between C and the S7-1200 IEC 61131-3 type set is a frequent source of porting bugs. Use this table as the canonical mapping:
| C Type | S7-1200 Type | Size (bytes) | Notes |
|---|---|---|---|
| bool / _Bool | BOOL | 1 | Single bit when in optimized block; byte in non-optimized |
| char (signed/unsigned) | CHAR / BYTE | 1 | BYTE = unsigned 0..255; CHAR = ASCII printable |
| unsigned char | BYTE | 1 | Use WORD for 16-bit unsigned |
| short | INT | 2 | Signed -32768..32767 |
| unsigned short | WORD | 2 | Bit-level operations: AND, OR, XOR |
| int (typically 32-bit) | DINT | 4 | Signed -2^31..2^31-1 |
| unsigned int | DWORD | 4 | 0..2^32-1 |
| long long | LINT | 8 | Signed 64-bit |
| float | REAL | 4 | IEEE 754 single precision |
| double | LREAL | 8 | IEEE 754 double precision |
| char[N] | STRING[N+2] | N+2 | Each STRING has 2-byte header |
| struct | STRUCT in DB | Sum of members | STRICT alignment; no padding |
| enum | INT + named constants | 2 or 4 | No native enum; use named integer constants |
| union | Not supported | n/a | Use separate DBs or bit-level access via AT overlay |
The AT overlay construct is the S7-1200 mechanism for viewing the same memory region as different types, similar in spirit to a C union. Example: declaring a DWORD and overlaying four BOOLs to access individual bits.
TIA Portal Version and Firmware Requirements
The S7-1200 firmware family evolved significantly across TIA Portal versions. The mapping below covers the production-relevant combinations:
| TIA Portal Version | S7-1200 FW Range | STEP 7 Edition Required |
|---|---|---|
| V13 / V13 SP1 | FW 4.0 - 4.1 | STEP 7 Basic V13 |
| V14 / V14 SP1 | FW 4.2 | STEP 7 Basic V14 or Professional V14 |
| V15 / V15.1 | FW 4.3 - 4.4 | STEP 7 Basic V15 or Professional V15 |
| V16 | FW 4.5 | STEP 7 Basic V16 or Professional V16 |
| V17 | FW 4.6 | STEP 7 Basic V17 or Professional V17 |
| V18 | FW 4.7 | STEP 7 Basic V18 or Professional V18 |
| V19 | FW 4.7 (latest) | STEP 7 Basic V19 or Professional V19 |
For SCL on the S7-1200, the minimum combination is TIA Portal V14 SP1 with FW 4.2 on the CPU. Earlier combinations allow LAD/FBD only. STL support requires STEP 7 Professional and FW 4.2 or higher.
Performance and Memory Constraints When Porting from C
The S7-1200 CPU family has fixed memory budgets. Engineers porting C code must respect these limits or the download fails:
| CPU | Work Memory (Code) | Work Memory (Data) | Retentive Memory | Bit Memory |
|---|---|---|---|---|
| CPU 1211C | 30 KB | 50 KB | 10 KB | 4096 bytes |
| CPU 1212C | 50 KB | 75 KB | 10 KB | 4096 bytes |
| CPU 1214C | 100 KB | 150 KB | 10 KB | 8192 bytes |
| CPU 1215C | 150 KB | 250 KB | 10 KB | 8192 bytes |
| CPU 1217C | 250 KB | 400 KB | 10 KB | 8192 bytes |
C porting caveats driven by these limits:
- String handling: C char[] maps to S7-1200 STRING type. Each STRING consumes (max_len + 2) bytes. Concatenation in SCL is more expensive than C strcat(); pre-allocate.
- Recursive functions: Not supported. Convert to iterative form using WHILE/FOR.
- Pointer arithmetic: Replace with indexed ARRAY access; out-of-bounds triggers OB121 and CPU stop if not caught.
- Floating point: REAL is 32-bit IEEE 754 single precision, matching C float. LREAL is 64-bit double. Mixing requires explicit ROUND/TRUNC.
- 64-bit integers: Use DINT (32-bit) or LINT (64-bit signed) explicitly; do not assume int == 32 bits as in C.
- Stack depth: OB1 + nested FB calls must fit in the cyclic time budget. Default OB1 cycle on a CPU 1214C is 1-10 ms; long call chains exceed this and trigger OB80 time error.
OB Execution Model vs. C main() / Interrupt Service Routines
C engineers porting to the S7-1200 must internalize the Organization Block (OB) execution model, which replaces both the C main() function and the interrupt service routine (ISR) concept:
| S7-1200 OB | Priority | C Analog | Use |
|---|---|---|---|
| OB1 (Main cyclic) | 1 | while(1) main loop | All cyclic user logic |
| OB10 (Time-of-day) | 2 | RTC alarm ISR | Scheduled daily/weekly triggers |
| OB35 (Cyclic interrupt) | 12 | Timer ISR | Deterministic 1-1000 ms period tasks |
| OB40 (Hardware interrupt) | 16 | Edge-triggered ISR | Fast reaction to digital input edges |
| OB82 (Diagnostic interrupt) | 26 | Error ISR | I/O module fault detection |
| OB121 (Programming error) | Same as OB1 | SIGFPE/SIGSEGV handler | Recover from bad index access |
The key behavioral difference: when OB35 fires, OB1 is interrupted. State held in instance DBs remains consistent because the S7-1200 runtime serializes access. Do not assume atomic multi-variable updates across OBs without explicit synchronization patterns.
Libraries: Reusable Code Containers
C developers commonly organize reusable code into static or shared libraries. The S7-1200 equivalent is the TIA Portal Library:
- Type DB (UDT) - C typedef equivalent. Define once, reuse as a template for instance DBs.
- FB with multi-instance capability - C class with member functions; instance DBs are the C objects.
- Global Library (.al14 file) - Shared archive between projects. Reusable across stations.
- Project Library - In-project reusable components, automatically versioned.
Master copies in a global library behave like static libraries; changes propagate to all consumers and may require recompilation of dependent blocks. Type changes in UDTs cascade through every instance DB in the project.
Commissioning and Verification Procedure
After translating the C source, follow this verification procedure to catch porting defects before deployment:
- Compile the project in TIA Portal (Project > Compile > All). Resolve all warnings before continuing.
- Download to the target CPU 1211C/1212C/1214C/1215C/1217C and switch to RUN mode.
- Open a watch table covering all I/O and intermediate tags from the migrated code.
- Run the original C build on a PC with a test harness that emits the same input stimulus sequence.
- Force inputs and capture outputs in the watch table; compare against the C reference output on a per-cycle basis.
- Use trace functionality (CPU 1214C FW 4.2+ and higher) to record cyclic values at sub-millisecond resolution.
- Stress-test edge cases: overflow, empty arrays, divide-by-zero, simultaneous interrupts from OB35 and OB40.
Troubleshooting Matrix
| Symptom | Likely Cause | Diagnostic | Fix |
|---|---|---|---|
| Download rejected: "Not enough memory" | C port produced oversized blocks | TIA Portal > Project tree > Program blocks > right-click > Resources | Split into smaller FBs, enable block optimization, upgrade CPU |
| SCL compiler error: "Identifier already declared" | Variable name collision across DBs | Cross-reference tool (Ctrl+Shift+F) | Rename to fully qualified tag-qualified form |
| OB121 programming error during scan | Array index out of bounds | Online > Diagnostics > Buffer | Add limit check before index access |
| STL editor unavailable in TIA Portal | STEP 7 Basic only; STL requires Professional | Help > About > Installed products | Upgrade license to STEP 7 Professional |
| SCL block download fails on CPU 1211C/1212C | SCL not enabled or insufficient work memory | CPU properties > Programming > SCL support | Enable SCL or use CPU 1214C or higher |
| C-like ternary operator (cond ? a : b) unavailable | SCL has no ternary; only IF/ELSIF | Source review | Refactor to IF ... THEN ... ELSE ... END_IF; |
| Watch table value does not update | Tag in optimized DB; absolute addressing disabled | DB properties > Attributes > Optimized block access | Disable optimization or use symbolic name in watch table |
| Timer/dialog FB counts twice per cycle | FB called from OB1 and from interrupt OB | Cross-reference call hierarchy | Move logic to single OB or use instance DB partitioning |
| REAL value differs from C float output | Implicit DINT-to-REAL conversion dropped precision | Watch table on both representations | Use explicit REAL casts in SCL |
| STRING concatenation exceeds max length | C strcat unbounded; SCL STRING is fixed | Diagnostic buffer OB121 | Pre-allocate STRING with sufficient length; truncate manually |
FAQ
Can I program the Siemens S7-1200 directly in C?
No. The S7-1200 firmware executes STEP 7 blocks (LAD, FBD, SCL, STL) only. There is no C compiler, no C runtime, and no loader for C object files on any S7-1200 CPU. To execute native C code on Siemens hardware, use a SIMATIC WinAC RTX software PLC on an industrial PC with the SIMATIC ODK.
Is there an automatic C-to-LAD converter for the S7-1200?
No production-grade converter exists. The semantic gap between C (pointers, recursion, dynamic memory) and LAD (graphical, no recursion, fixed memory) makes reliable automated translation infeasible. Engineers porting C must manually re-express logic in LAD, FBD, or SCL within TIA Portal.
What is the closest Siemens high-level language to C on the S7-1200?
SCL (Structured Control Language) is the closest. It uses Pascal-style syntax with := for assignment, BEGIN/END block delimiters, and supports IF, CASE, WHILE, FOR, and REPEAT. SCL requires STEP 7 Professional and a CPU with firmware V4.2 or higher (such as CPU 1214C, 1215C, or 1217C).
Which TIA Portal version do I need to program an S7-1200?
STEP 7 Basic V13 or higher is required for any S7-1200 programming. For SCL and advanced language features, use STEP 7 Professional V14 SP1 or higher paired with CPU firmware V4.2 or higher. Always match the TIA Portal version to the installed CPU firmware before downloading to avoid incompatibility errors.
How do I port an existing C application to the S7-1200?
Decompose the C program into a function tree, classify each function (boolean into LAD, arithmetic into SCL, state machine into FB), build a tag dictionary that mirrors C globals/structs as DBs, translate block-by-block, then commission using watch tables and force tables to verify parity with the C reference build on a per-input basis.