Overview: From S7-200 Subroutines to S7-300 Modular Blocks
Engineers moving from a S7-200 to a S7-300 typically experience a structural shift in how program logic is organized. On a S7-200 with STEP 7 Micro/WIN, every program module is a SUB routine inside a single POU tree; the CPU scans OB1 once, calls SUBs as required, and persists state in V-memory or data blocks. On a S7-300 with STEP 7 (V5.x) or TIA Portal, the CPU instead supports a rich block architecture: Organization Blocks (OB), Function Blocks (FB), Functions (FC), Data Blocks (DB), and System Blocks (SFB/SFC/SDB). Each plant area (a conveyor, a stopper, a lifting device, a transfer chain) maps cleanly onto one FB with its own instance DB, called from OB1 (slow logic) or OB35 (deterministic cyclic logic).
This reference walks through the structure of a S7-300 STEP 7 program on a CPU 315-2DP (MLFB 6ES7315-2AH14-0AB0, firmware V3.x), with focus on the block model and the practical mapping required to organize a multi-area material-handling plant. The same principles apply to CPU 312, CPU 314, CPU 316, CPU 317, and CPU 319 variants; the differences are capacity (number of blocks, work memory, address ranges) rather than the structural concepts.
STEP 7 Block Type Reference
STEP 7 programs are built from the following block types. The S7-300 and S7-400 share the same model; S7-1200 and S7-1500 extend it slightly (with optimized blocks and newer block types) but the conceptual mapping is identical.
| Block | Purpose | Memory | Typical Use |
|---|---|---|---|
| OB (Organization Block) | Interface between CPU OS and user program | Local stack only | Cyclic scan, interrupts, startup, error handling |
| FB (Function Block) | Reusable code with persistent state | Own instance DB | Plant-area encapsulation (conveyor, stopper, lifter) |
| FC (Function) | Reusable stateless code | No memory | Calculations, conversions, shared logic |
| DB (Data Block) | Data container | Work memory / load memory | Instance data, recipes, global setpoints |
| SFB / SFC (System FB / FC) | Built-in functions embedded in CPU firmware | Internal | RTC read, PID, communication handlers |
| SDB (System Data Block) | Configuration storage | Load memory | HW configuration, networking parameters |
The instance DB is the key to the S7-300 programming model. When you create an FB and call it from OB1, you assign a DB to that call: the DB stores the FB's STAT (static) variables between scans. Without the instance DB, the FB behaves like an FC. With multiple instances of the same FB, each call receives its own DB and therefore its own independent state.
Capacity for CPU 315-2DP
| Resource | CPU 315-2DP (typical) | Verification |
|---|---|---|
| Work memory (code + data) | 256-384 KB depending on MLFB / FW | PLC → Module Information |
| Load memory (with MMC) | up to 8 MB | PLC → Module Information |
| Maximum FB / FC count | up to 2048 each (block numbers 0-2047) | HW Config → CPU → Properties |
| Maximum DB count | up to 2048 (block numbers 1-2047) | HW Config → CPU → Properties |
| Maximum block size (FB/FC/DB) | 64 KB | Compiler error on exceed |
| Bit memory (M) | 2048 bytes | HW Config |
| Timers / Counters | 256 / 256 | HW Config |
Organization Blocks (OB) for the CPU 315-2DP
OBs are the only blocks the CPU operating system calls directly. Every OB has a fixed priority and a fixed trigger; you can configure some, others are fixed by the firmware.
| OB | Name | Priority | Trigger | Use in a material-handling plant |
|---|---|---|---|---|
| OB1 | Main cyclic program | 1 | End of previous scan | Sequencing, HMI request handling, slow I/O |
| OB10 | Time-of-day interrupt | 2 | Absolute time / periodic | Shift handover, end-of-shift reporting |
| OB35 | Cyclic interrupt | 12 | Configurable period (default 100 ms) | Closed-loop control, fast I/O, anti-bounce |
| OB40 | Hardware interrupt | 16 | DI module rising/falling edge | Encoder pulse capture, light-curtain trip |
| OB82 | Diagnostic interrupt | 26 | DI/DO/AI module fault | Wire-break, overload, channel diagnostics |
| OB100 | Warm restart | 27 | STOP → RUN, mode selector | Initialize non-retentive M and DB tags |
| OB101 | Hot restart | 27 | Power restore with backup | Resume state after power dip |
| OB102 | Cold restart | 27 | MRES or initial download | Full re-initialization |
| OB121 | Programming error OB | = calling OB | OB1 / OB35 / etc. error | Trap divide-by-zero, BCD conversion error |
| OB122 | I/O access error OB | = calling OB | Missing or faulty I/O module | Trap "Peripheriefehler", log and continue |
The default S7-300 project template contains OB1 and OB35. OBs 10, 40, 82, 100, 121, and 122 must be inserted manually via SIMATIC Manager → S7 Program → Blocks → Insert New Object → Organization Block, then assigned their fixed number.
Configuring OB35 phase time
The OB35 period is set in HW Config → CPU 315-2DP → Properties → Cyclic Interrupts. Default 100 ms is the conservative choice for a multi-area conveyor line; reduce to 50 ms or 20 ms when you need faster response on a closed-loop or fast counting task.
Sample STL in OB35 for a 20 ms anti-bounce filter on a digital input stored in DB20:
// OB35 - 100 ms cyclic interrupt
CALL FB 100, DB20 // FB100 = anti-bounce filter, instance DB20
IN := I 0.7 // raw input from light curtain
T_MS := 30 // 30 ms debounce
OUT := M 50.3 // debounced output
ERR := M 50.4 // error flag (e.g. cycle overrun)
Function Blocks (FB) for Plant Area Encapsulation
The FB is the right tool for each plant area: Conveyor 1, Conveyor 2, Stopper 3, Lifter 4, Transfer Chain 5, and so on. The FB holds the area's logic and the area's state in its instance DB.
A typical FB for a conveyor might expose the following interface (IN / OUT / IN_OUT / STAT / TEMP):
| Section | Name | Type | Meaning |
|---|---|---|---|
| INPUT | I_START | BOOL | Start command from upstream |
| INPUT | I_STOP | BOOL | Stop command (E-Stop / HMI) |
| INPUT | I_MOTOR_OK | BOOL | Drive healthy feedback |
| INPUT | I_OL_OK | BOOL | Overload contact from motor protector |
| INPUT | IW_SPEED | INT | Actual speed (0-27648 for ±10 V) |
| INPUT | SP_SPEED | INT | Setpoint speed |
| OUTPUT | Q_RUN | BOOL | Run signal to VFD / contactor |
| OUTPUT | Q_RUNNING | BOOL | Running feedback to HMI |
| OUTPUT | QW_SPEED | INT | Setpoint to VFD |
| IN_OUT | FAULT | BOOL | Aggregated fault |
| STAT | s_state | INT | Sequencer step (0=Idle, 1=Start, 2=Run, 3=Fault) |
| STAT | s_run_timer | S5TIME | Run-time accumulator |
| STAT | s_fault_latch | BOOL | Latched fault |
| STAT | s_first_scan | BOOL | One-shot on first call |
OB1 then becomes a short, readable list of FB calls:
// OB1 - main cyclic program
CALL FB 10, DB100 // Conveyor 1
I_START := I 10.0
I_STOP := I 10.1
I_MOTOR_OK := I 10.2
I_OL_OK := I 10.3
IW_SPEED := IW 12
SP_SPEED := DB200.SP_CONV1
Q_RUN := Q 8.0
Q_RUNNING := M 100.0
QW_SPEED := QW 12
FAULT := M 110.0
CALL FB 10, DB101 // Conveyor 2
...
CALL FB 20, DB110 // Stopper 3
...
CALL FB 30, DB120 // Lifter 4
...
CALL FB 40, DB130 // Transfer Chain 5
...
Each call site is only 12-20 lines, and adding Conveyor 6 means inserting one more CALL — the rest of the program is unaffected.
Conv1_Start in the Symbol Table (S7 Program → Symbols) so that OB1 reads as English-language logic and not numeric addresses. Renaming a signal becomes a Symbol Table edit rather than a program rewrite.Functions (FC) for Shared Reusable Logic
FCs are stateless. Use them for calculations, conversions, and shared logic that does not need to remember anything between scans. Examples:
- FC100 — Scale raw analog input (0-27648) to engineering units (0.0-100.0 %)
- FC101 — Convert BOOL edge to a one-shot pulse
- FC102 — Two-out-of-three voter for redundant sensors
- FC103 — Linear interpolation for a recipe curve
- FC104 — Pack five BOOL alarms into a BYTE for HMI
An FC can be called from any block: from OB1, from OB35, from inside an FB, or even from another FC. Because the FC has no instance DB, the call is cheap in work memory.
// FC100 - scale 0-27648 INT to 0.0-100.0 REAL (% engineering units)
FUNCTION FC 100 : VOID
VAR_INPUT
RAW : INT; // 0-27648
END_VAR
VAR_OUTPUT
PCT : REAL; // 0.0-100.0
END_VAR
BEGIN
IF RAW > 27648 THEN
PCT := 100.0;
ELSIF RAW < 0 THEN
PCT := 0.0;
ELSE
PCT := INT_TO_REAL(RAW) / 276.48;
END_IF;
END_FUNCTION
Note the difference between FB and FC: the FC has no STAT section, no instance DB, and no persistent variables. If you call FC100 twice in the same scan, both calls share no state; if you call FB10 twice, each call has its own DB with independent STATs.
Data Blocks: Instance DBs and Global DBs
There are two distinct uses of DB in S7-300 programming:
| DB type | Created when | Contents | Example |
|---|---|---|---|
| Instance DB | You assign a DB to an FB call | STAT and TEMP variables of the FB | DB100 = data for Conveyor 1 FB |
| Global DB | You insert a DB object directly | Recipe data, setpoints, shared tags | DB200 = line-wide setpoints for HMI |
Instance DB example
DB100, generated automatically when FB10 is first compiled and assigned to a call, looks like this in the declaration view:
DATA_BLOCK DB 100
// Conveyor 1 instance data, mirrored from FB10
STRUCT
s_state : INT; // FB10 STAT
s_run_timer : S5TIME;
s_fault_latch: BOOL;
s_first_scan : BOOL;
END_STRUCT;
BEGIN
END_DATA_BLOCK
Global DB example
DB200 — line-wide setpoints written by HMI and read by all conveyor FBs:
DATA_BLOCK DB 200
// Line-wide setpoints
STRUCT
SP_CONV1 : INT; // Conveyor 1 speed (RPM)
SP_CONV2 : INT;
SP_LIFTER_POS : INT; // 0=down, 1=up
MODE_AUTO : BOOL;
RECIPE_ID : INT;
SHIFT_CODE : INT;
END_STRUCT;
BEGIN
SP_CONV1 := 1500;
SP_CONV2 := 1500;
SP_LIFTER_POS := 0;
MODE_AUTO := FALSE;
RECIPE_ID := 0;
SHIFT_CODE := 0;
END_DATA_BLOCK
Avoid the temptation to put all setpoints in one giant DB; that produces hidden coupling between FBs. Prefer one DB per FB (instance) plus a small number of shared DBs (recipe, mode, line-wide fault).
Multi-Instance Pattern for Compact Memory Use
On smaller S7-300 CPUs (CPU 312, CPU 314) the number of available DB numbers can be a constraint. The multi-instance pattern solves this by calling FBs inside other FBs and storing all child FBs in a single parent instance DB.
Consider a master FB "Line_1" that owns Conveyor 1, Stopper 1, and Lifter 1:
FUNCTION_BLOCK FB 1 // Line_1 master
VAR
conv1 : FB 10; // Conveyor instance, no DB assigned here
stop1 : FB 20; // Stopper instance, no DB assigned here
lift1 : FB 30; // Lifter instance, no DB assigned here
END_VAR
BEGIN
// Calling FB10 inside FB1 with "conv1" as the instance identifier
conv1(I_START := I 10.0,
I_STOP := I 10.1,
Q_RUN := Q 8.0,
...);
stop1(...);
lift1(...);
END_FUNCTION_BLOCK
When you call FB1 from OB1 with a single instance DB (DB1), the instance DB contains the STAT data for conv1, stop1, and lift1 in named structures. This cuts DB count from 3 to 1 for the entire line and keeps the variable namespace tidy.
Mapping Plant Areas: Conveyors, Stoppers, Lifting Devices, Transfer Chains
For a typical material-handling line, the FBs fall into a small library:
| FB | Plant area | Inputs (typical) | Outputs (typical) | State (STAT) |
|---|---|---|---|---|
| FB10 — Conveyor | Belt, motor, VFD, photo-eye | Start, Stop, OL_OK, VFD_OK, IW_Speed | Q_Run, Q_Running, QW_Speed | state, run_timer, fault_latch |
| FB20 — Stopper | Pneumatic arm, dual-solenoid valve | Up_OK, Down_OK, Pressure_OK | Q_Up, Q_Down | position, last_command |
| FB30 — Lifter | Vertical axis with brake and limit switches | Upper_LS, Lower_LS, Brake_OK | Q_Up, Q_Down, Q_Brake | position, homed, target_pos |
| FB40 — Transfer Chain | Slat conveyor with indexing | Index_OK, Pos_1..Pos_8 | Q_Index, QW_Speed | index_count, step |
| FB50 — Turntable | Rotary indexing table | Pos_feedback, CW_LS, CCW_LS | Q_CW, Q_CCW | actual_pos, target_pos |
| FB60 — Stack Light | 3-color tower (R/A/G) | Fault, Warning, Run | Q_Red, Q_Amber, Q_Green | — |
Two engineering conventions keep the program maintainable:
- One FB per area, one DB per area. Conveyor 1 is FB10 + DB100. Conveyor 2 is FB10 + DB101. The Symbol Table ties the same FB type to different physical I/O.
- FB numbers in the 10s for equipment class, instance DBs in the 100s. FB10..FB19 = conveyors, FB20..FB29 = stoppers, FB30..FB39 = lifters, FB40..FB49 = transfer chains. DB100..DB199 = conveyor instances, etc. The convention is not enforced by STEP 7 but makes cross-references readable.
Sample Symbol Table excerpt:
// Symbol Table - selected entries
Symbol Address DataType Comment
Conv1_Start I 10.0 BOOL Conveyor 1 start pushbutton
Conv1_Stop I 10.1 BOOL Conveyor 1 stop pushbutton
Conv1_OL_OK I 10.3 BOOL Conveyor 1 overload contact
Conv1_Speed_AI IW 12 INT Conveyor 1 VFD speed feedback
Conv1_Run Q 8.0 BOOL Conveyor 1 run command
Conv1_Speed_AO QW 12 INT Conveyor 1 VFD speed setpoint
Stopper3_Up_OK I 30.0 BOOL Stopper 3 raised feedback
Stopper3_Down_OK I 30.1 BOOL Stopper 3 lowered feedback
Stopper3_Up_Cmd Q 28.0 BOOL Stopper 3 raise solenoid
Stopper3_Dn_Cmd Q 28.1 BOOL Stopper 3 lower solenoid
Lifter4_Upper_LS I 40.0 BOOL Lifter 4 upper limit switch
Lifter4_Lower_LS I 40.1 BOOL Lifter 4 lower limit switch
Lifter4_Up_Cmd Q 38.0 BOOL Lifter 4 raise command
Lifter4_Dn_Cmd Q 38.1 BOOL Lifter 4 lower command
Line_Mode_Auto DB200.DBX0.3 BOOL Line automatic mode from HMI
Line_Recipe_ID DB200.DBW4 INT Active recipe number
Symbolic Addressing and the Symbol Table
The Symbol Table (in S7 Program → Symbols in SIMATIC Manager, or PLC Tags in TIA Portal) is the single source of truth for naming. Use symbolic addressing throughout; never use absolute addresses inside FBs unless absolutely necessary.
Three engineering rules:
- Every input, output, flag, and DB tag that crosses a block boundary gets a symbol. Internal scratch variables can remain absolute.
- Symbols follow a noun-first convention:
Conv1_Run, notRun_Conv1. Group sort orders the table by area, which matches the FB grouping. - Symbols are uppercase with underscores; comments explain the physical source (e.g., "Conveyor 1 VFD speed feedback from 4-20 mA on AI4").
In TIA Portal V18 and later, the PLC tag table can be exported to CSV for review with maintenance teams. The cross-reference tool (Options → Cross-Reference) then shows every block access to a tag, which is invaluable during commissioning and fault-finding.
Project Layout in STEP 7 V5.x (Classic) and TIA Portal
Two project structures coexist for S7-300 today: the SIMATIC Manager / STEP 7 V5.x structure (still supported on STEP 7 V5.7) and the TIA Portal structure (V13 onward, currently V18/V19/V20). The block model is identical; only the project container differs.
| Layer | STEP 7 V5.x (SIMATIC Manager) | TIA Portal |
|---|---|---|
| Project root | Plantname.S7P | Plantname.ap18 |
| Station | SIMATIC 300 Station | Device (CPU 315-2DP) |
| Program | S7 Program (under station) | Program blocks (under device) |
| Blocks folder | OBs, FBs, FCs, DBs | Same, in "Program blocks" |
| Source folder | STL sources, SCL sources | External sources |
| HW configuration | HW Config (separate tool) | Device view (integrated) |
Recommended folder layout inside the S7 Program / Program blocks folder:
-
OB— OB1, OB35, OB82, OB100, OB121, OB122 -
FB_Conveyor— FB10 master type -
FB_Stopper— FB20 master type -
FB_Lifter— FB30 master type -
FB_Transfer— FB40 master type -
FB_Drive— FB5 motor/VFD wrapper -
FC_Utility— FC100..FC109 scaling and conversion -
DB_Instance— DB100..DB139 instance data -
DB_Global— DB200 recipes, DB210 line faults, DB220 HMI mirror -
DB_System— DB250 shift log, DB260 alarm buffer
In TIA Portal the same hierarchy is created as subfolders inside Program blocks. Drag and drop preserves cross-references.
Commissioning, Cross-Reference, and Verification
After download, the following checks verify the program structure is correct and complete.
Step 1 — Block consistency
In SIMATIC Manager, right-click the Blocks folder → Check Block Consistency. The compiler flags FBs that are called with mismatched interfaces (parameter added or removed in the FB but not propagated to all call sites). The result should be "No errors".
Step 2 — Cross-reference
Options → Cross-Reference (Ctrl+Alt+F7) lists every access to a tag or block. Confirm that:
- Every FB has exactly one instance DB assigned.
- Every FB is called from OB1, OB35, or another FB (no orphan FBs).
- Every input tag has a single source (no double-write from two FBs).
Step 3 — Reference data
Options → Reference Data → Display produces a program structure tree, a cross-reference list, and a memory map. The program structure tree should show a clean pyramid: OB1 → master FBs → equipment FBs → FC utilities, with no circular calls.
Step 4 — Online scan
Connect online to the CPU (PLC → Online → Accessible Nodes) and open the diagnostic buffer (PLC → Diagnose/Set → Diagnostic Buffer). Confirm the absence of "OB not loaded" or "Block inconsistency" events. If OB82 has fired on a missing module, the diagnostic buffer lists the slot.
Step 5 — OB priority verification
Open HW Config → CPU 315-2DP → Properties → Cyclic Interrupts. Confirm OB35 period matches the design intent (e.g., 100 ms for a conveyor line, 20 ms if closed-loop control is involved). Watch OB1 scan time in PLC → Monitor/Modify; if scan time exceeds the OB35 period, OB35 will queue and the program will report "OB35 queue overflow" in the diagnostic buffer.
Step 6 — Symbol completeness
Options → Symbol Table → Sort and look for entries with empty Comment columns. A symbol without a comment is a maintenance liability; require comments on every I/O symbol and every DB tag that crosses a block boundary.
Migration Path to S7-1500 and TIA Portal
The CPU 315-2DP and the rest of the S7-300 line are in the phase-out lifecycle stage as of TIA Portal V17 (product announcement 2017, phase-out announced for many regions). New projects should target the S7-1500 family (CPU 1511, CPU 1515, CPU 1516, CPU 1518).
The block model carries over with two important differences:
| Concept | S7-300 / 400 | S7-1500 |
|---|---|---|
| Block type | OB / FB / FC / DB | Same, plus "optimized block" |
| Instance DB | Fixed layout, indexed access | Optimized by default, symbolic only |
| Programming languages | LAD / FBD / STL / SCL / GRAPH | LAD / FBD / SCL / GRAPH (STL deprecated) |
| Multi-instance | Supported | Supported; recommended pattern |
| Access to instance data | DB10.DBD0 (absolute) | "Conv1".speed (symbolic only) |
| Error OBs | OB121 / OB122 | Same, plus more granular diagnostics |
The STEP 7 V5.x → TIA Portal migration tool (TIA Portal V18 and later) converts a V5 project to a TIA Portal project automatically, preserving FBs, FCs, DBs, and the symbol table. The conversion flags absolute accesses inside optimized blocks; engineers can choose to keep classic DB layout for compatibility or convert to optimized blocks for the S7-1500 symbolic-only model. The STEP 7 product page documents the supported source versions.
FAQ
What is the difference between OB1 and OB35 on a S7-300?
OB1 is the main cyclic program: the CPU executes it from top to bottom, then immediately restarts. OB35 is a cyclic interrupt with a configurable period (default 100 ms) and higher priority (12). Use OB1 for sequencing, HMI handling, and slow logic; use OB35 for closed-loop control, anti-bounce filtering, and any I/O that must run at a deterministic rate regardless of OB1 scan time.
When should I use FB versus FC in STEP 7?
Use an FB when the logic must remember state between scans (motor run timer, sequencer step, fault latch). The FB stores its STAT variables in an instance DB that the engineer assigns at call time. Use an FC for calculations and conversions that have no memory: scaling, conversion, voter, edge detection. Calling FC10 ten times in one scan is cheap; calling FB10 ten times creates ten independent states via ten instance DBs.
How many FBs and DBs can a CPU 315-2DP hold?
The CPU 315-2DP (MLFB 6ES7315-2AH14-0AB0, FW V3.x) supports up to 2048 FBs, 2048 FCs, and 2048 DBs, each up to 64 KB. Work memory is in the 256-384 KB range shared between code and data. For typical multi-area material-handling projects (8-15 plant areas) this is more than sufficient without resorting to multi-instance. Confirm exact values against HW Config for the specific MLFB.
Why does my CPU report "OB not loaded" after download?
The error appears when OB1, OB35, or another OB that the firmware needs at startup is missing from the project. Insert OB1 and OB35 from the right-click menu in the Blocks folder, then re-download. The same message appears if a called FB or FC is missing — STEP 7 lists the missing block in the diagnostic buffer under event ID 0x35FE.
How do I move a STEP 7 V5.x project to TIA Portal without rewriting it?
Open the V5.x project in TIA Portal V18 or later; the migration wizard converts the project automatically. FBs, FCs, DBs, the symbol table, and the HW configuration are translated. You will need to manually address absolute accesses inside instance DBs because TIA Portal's optimized blocks disallow DB10.DBD0 syntax. Plan for a half-day to two-day review pass after automatic conversion.