1. Problem Summary
The "Maximum Nesting Depth Exceeded" / "Nesting Depth Exceeded" system error is raised by the WinCC Flexible 2004 / 2005 / 2008 SP1-SP3 runtime when an HMI project is transferred to a Siemens SIMATIC MP 270 Multi Panel (order number 6AV6 545-0BA15-2AX0, 10.4" TFT and 6AV6 545-0BB15-2AX0 variants). The runtime accepts the project but logs the error and then executes the script chain very slowly because the interpreter falls back to a guarded evaluation path on every cycle. The error is independent of pure VBScript nesting; it is triggered by the cumulative tag-handle resolution cost inside the script body, especially when a large number of power tags (HMI tags connected to a PLC) are referenced within one compiled script unit.
2. Affected Hardware and Software Versions
| Component | Identifier | Notes |
|---|---|---|
| Panel | SIMATIC MP 270 Multi Panel | 6AV6 545-0BA15-2AX0 / 6AV6 545-0BB15-2AX0 |
| Runtime firmware | WinCC Flexible RT V1.3 / V1.4 | CE 5.0 image, ARM/XScale CPU |
| Configuration software | WinCC Flexible 2004 / 2005 / 2008 | SP1, SP2, SP3, SP4 |
| Script engine | VBScript-compatible parser | Limited stack; per-script tag-handle pool |
| PC interface | Serial (RS-232) / Ethernet / MPI / PROFIBUS | Transfer mode required for compile validation |
3. MP 270 System Limits Relevant to the Fault
The MP 270 is a class-2 multi-panel (256-color / 16-bit color TFT) and has tight compiler-imposed limits. The two ceilings most often involved in the nesting-depth fault are:
| Parameter | Limit | Comment |
|---|---|---|
| Total HMI tags (power + internal) | 2 048 | Hard ceiling on the panel; configurable in Project > Properties |
| Local / internal tags | 1 000 | Volatile tags held in panel RAM only |
| Power tags | 1 048 maximum (theoretical) | Limited by remaining tag budget after internal tags |
| Tag-handles per compiled script | Approx. 64 unique resolved pointers | Undocumented internal threshold |
| Script size (VBScript) | ~16 KB compiled IL | Drives nesting-depth validation |
| Nesting depth (IF / FOR / WHILE) | 8 levels | Documented; this is NOT the trigger here |
The MP 270 tag budget is consumed by every SmartTags("PHYSICAL_TAG_xx") reference inside a script. Unlike PLC FBs, the panel allocates a runtime handle per tag per script compile unit. When the handle pool exceeds the internal cap, the compiler flags a synthetic "nesting depth exceeded" condition even though no statement is syntactically nested.
4. Root Cause Analysis
During project regeneration, the WinCC Flexible compiler builds an intermediate symbol table for every script. Each unique SmartTags("PHYSICAL_TAG_xx") read or SmartTag("TAG_xx") write requires:
- An entry in the per-script tag-resolution cache.
- A PLC-side buffer reservation, even if the value is later discarded.
- An export entry in the runtime image, consuming IDB (image database) slots.
When the cumulative handle count exceeds the panel-class compile threshold, the post-linker returns error class 0x8004xxxx, which WinCC Flexible maps to the user-visible message "Maximum Nesting Depth Exceeded". The mapping is historical: the same code path was originally used for true VBScript block-nesting overflows in earlier WinCC versions (2004 SP1) and was never relabeled.
5. Reproduction Pattern
The fault is reproducible with a single script of the form:
' VBScript - WinCC Flexible Advanced
Dim i
For i = 1 To 52
If SmartTags("cond_" & i) Then
SmartTags("PHYSICAL_TAG_1") = SmartTags("SRC_TAG_1")
SmartTags("PHYSICAL_TAG_2") = SmartTags("SRC_TAG_2")
SmartTags("PHYSICAL_TAG_3") = SmartTags("SRC_TAG_3")
SmartTags("PHYSICAL_TAG_4") = SmartTags("SRC_TAG_4")
End If
Next i
Field observations confirm the following markers:
| Symptom | Observation |
|---|---|
| Tag count threshold | Fault appears at approximately 18–22 unique power tags per script |
| Internal-tag substitution | Replacing SmartTags("PHYSICAL_TAG_3") with a literal (e.g. 0 or 1) eliminates the error |
| Script splitting | Splitting one large script into 4–10 smaller scripts does NOT eliminate the error (per-script pool is recompiled) |
| Runtime speed | Project still loads but executes 5×–10× slower due to guarded re-evaluation |
| Compile log location | Output window of WinCC Flexible after > Project > Compile > Start Runtime with Debugging |
6. Diagnostic Procedure
Use the following sequence to isolate the fault to the tag-handle pool rather than a syntactic nesting problem:
- Open the project in WinCC Flexible Advanced.
- Select Project > Compiler > Check Syntax for every script. Capture any reported errors.
- Open each script editor and select the menu Script > Check Syntax. Inspect the Output window for line-level diagnostics.
- Count unique tag references inside the longest script using Edit > Find / Replace with regex
SmartTags?\([^)]+\). - Open Project > Properties > Tags and verify the total tag count is below 2 048 (power + internal).
- Start the runtime in debug mode: Project > Compile > Start Runtime with Debugging. Recompile, then transfer to the MP 270. Note the exact error class displayed on the panel.
- If the fault clears when 2/3 of the physical-tag references are removed, the cause is confirmed as a tag-handle pool overflow.
7. Resolution Path A — Reduce Per-Script Tag References
The first-line mitigation is to keep each script below the per-compile-unit threshold. Practical rule of thumb derived from MP 270 deployments:
| Tag Type in Script | Safe Count per Script | Marginal Count | Fault Zone |
|---|---|---|---|
| Power tags only | 0–14 | 15–20 | > 21 |
| Mixed power + internal | 0–30 | 31–50 | > 51 |
| Internal tags only | 0–80 | 81–120 | > 121 |
Refactor the example by hoisting common tags out of conditional branches:
' Refactored - VBScript
' Hoist common reads
Dim v1, v2, v3, v4
v1 = SmartTags("SRC_TAG_1")
v2 = SmartTags("SRC_TAG_2")
v3 = SmartTags("SRC_TAG_3")
v4 = SmartTags("SRC_TAG_4")
If SmartTags("cond_any") Then
SmartTags("PHYSICAL_TAG_1") = v1
SmartTags("PHYSICAL_TAG_2") = v2
End If
8. Resolution Path B — Indirect Tag Access via Tag Multiplexing
WinCC Flexible Advanced supports tag multiplexing (multiplex tag / index tag pattern), which lets one tag selector choose one of N physical tags at runtime. This reduces the static handle pool dramatically:
- Define an internal
INTtag, e.g.TagIndex. - Configure Multiplex on the source PLC tag set: assign up to 256 physical tags to a single multiplexed access point.
- In the script, set
TagIndexthen readSmartTags("MuxSource"). The runtime resolves the actual power tag on the fly without allocating a per-script handle.
' Multiplexed access
SmartTags("TagIndex") = 7
Dim val
val = SmartTags("MuxSource")
SmartTags("PHYSICAL_OUT") = val
MultiplexTag runtime function. MP 270 RT V1.3 and later is compatible. Reference: Siemens Support Entry 18798452 — WinCC Flexible Tag Multiplexing.
9. Resolution Path C — Move Heavy Logic to the PLC
When the customer requirements force a large power-tag fan-in, the cleanest fix is to move the conditional mapping from the HMI script to a PLC FB (e.g. a Siemens S7-300 / S7-400 / S7-1200 function block). The HMI then exchanges one or two aggregated tags instead of dozens of atomic tags:
| Approach | PLC Load | Panel Load | Maintainability | Risk |
|---|---|---|---|---|
| All logic in HMI script | Low | High — fault zone | Low | Compile error |
| PLC FB + 1 mux tag | Medium | Low | High | Cycletime increase |
| PLC DB + status word | Low | Low | High | Coordination required |
10. Resolution Path D — Buffer Through Local Tags
If the power-tag references cannot be reduced, buffer them into a local tag array and write back only the active one:
' Buffer pattern
Dim localBuf(4)
localBuf(0) = SmartTags("PHYSICAL_TAG_1")
localBuf(1) = SmartTags("PHYSICAL_TAG_2")
localBuf(2) = SmartTags("PHYSICAL_TAG_3")
localBuf(3) = SmartTags("PHYSICAL_TAG_4")
Dim k
For k = 0 To 3
If SmartTags("cond_" & (k+1)) Then
SmartTags("OUTPUT_TAG") = localBuf(k)
Exit For
End If
Next k
Local tag reads inside a script do not consume the per-script power-tag handle pool. This pattern reduces the power-tag footprint to a single write per loop iteration.
11. Step-by-Step Resolution Workflow
- Back up the project using Project > Archive before any change.
- Inventory tag usage with the regex search described in §6 step 4. Record the count per script.
- Apply Path A: refactor each script whose power-tag count exceeds 14.
- Apply Path D: buffer remaining unavoidable reads into local tag arrays.
- Recompile: Project > Compiler > Check Syntax, then Project > Compiler > Compile.
- Re-test in Start Runtime with Debugging mode. Confirm no error popup.
- Transfer to the MP 270 over MPI/PROFIBUS or Ethernet. Observe first 30 s of runtime for the error popup.
- Tag-budget audit: confirm total HMI tags < 2 048 and power tags < 1 048.
12. Verification Procedure
| Check | Method | Expected Result |
|---|---|---|
| Compile clean | Project > Compiler > Compile (Rebuild All) | 0 errors, 0 warnings about nesting |
| Tag budget | Project > Properties > Tags | Power + internal ≤ 2 048 |
| Runtime debug | Project > Compile > Start Runtime with Debugging | No popup on first 60 s |
| Panel transfer | Transfer > Panel | Successful without System Error popup |
| Cycle performance | Trace script invocation time | ≤ 50 ms per script cycle |
| Functional regression | Operator-driven test of all 52 conditional paths | All branches produce correct values |
13. Performance Optimization Notes
The MP 270's 32-bit RISC CPU evaluates each script invocation with a per-call overhead of 8–15 ms plus ~0.4 ms per unique power-tag reference. A script with 50 power tags therefore adds ~20–35 ms to the cycle, which is consistent with the "slow execution" symptom reported in the field. The recommended target ceiling for time-critical screens is:
ScriptCycleBudget_ms = 50
UniquePowerTagRefs <= 14
NestingDepth_IF_FOR <= 4
TotalScriptsActive <= 3
If more complex logic is required, prefer Scheduled Tasks at a lower priority (Project > Scheduled Tasks) and avoid running them on screen-change events.
14. Best Practices for Future Development on MP 270 / MP 277 / MP 370
- Tag hygiene: declare only the tags the screen actually needs; avoid wildcard-style tag arrays of 200+ entries.
- One responsibility per script: keep tag-handle pools small; split logic into multiple short scripts invoked from one scheduler.
- Prefer multiplex tags for index-driven lookup tables.
- Avoid literal-tag spamming: do not declare 50+ power tags for one mapping task — derive the value in the PLC instead.
- Compile before transfer: always run Project > Compiler > Check Syntax on every script before the panel transfer; the panel-side error is far more costly to diagnose than a compile-time warning.
-
Version documentation: record the panel firmware version (e.g.
RT V1.4.0.12) and the WinCC Flexible build (e.g.2008 SP3 HF7) in the project README; the per-script tag-handle cap varies slightly between builds.
15. Troubleshooting Matrix
| Observed Symptom | Likely Cause | Action |
|---|---|---|
| Error appears during transfer, project never starts | Tag-handle pool overflow in largest script | Apply Path A (refactor) + Path D (buffer) |
| Error appears only at runtime, project loads | Scheduled task script exceeds threshold | Lower cycle rate; refactor task script |
| Error cleared after reducing 2/3 of tags | Confirmed pool-overflow fault | Apply Path B or C for permanent fix |
| Error persists after splitting into 10 scripts | Per-script pool is per-script, but cumulative IL still inflates | Refactor logic into PLC FB (Path C) |
| Error only when physical tags are referenced | Compiler routes power tags to dedicated handle pool | Replace reads with local tag copies |
| Error appears in MP 277 but not in MP 270 | Different internal pool size per panel class | Consult Siemens Support — Panel Class Comparison |
16. Migration Considerations
If a project is being migrated from WinCC Flexible to TIA Portal / WinCC Comfort, the per-script tag-handle pool behavior is different and the error code changes to a structured compile diagnostic in the "Compile > Messages" window. Reference for the TIA Portal / WinCC Engineering replacement of MP 270 (recommended successor: SIMATIC HMI TP700 Comfort or MTP700 Unified) is the Siemens Support Entry 68118683 — Migration from MP 270 to Comfort Panels. The architectural refactors described in §7–§10 carry forward unchanged because they reduce tag-handle pressure on the panel class regardless of platform.
Why does the MP 270 report "Nesting Depth Exceeded" when there is no real script nesting?
The error string is reused from an older WinCC Flexible build where the same code path also handled VBScript block-nesting overflows. On the MP 270 the compiler triggers the same message when the per-script tag-handle pool is exhausted, typically above ~21 unique power-tag references. The message is therefore misleading and should be interpreted as a tag-pool fault.
How many power tags can one script reference on the MP 270?
Empirically 0–14 unique power tags per script is the safe zone, 15–20 is marginal, and above 21 the compiler raises the nesting-depth error. The exact threshold varies by WinCC Flexible build (2004 SP1, 2005 SP1, 2008 SP1-SP4) and panel firmware revision (RT V1.3 through V1.4).
Will splitting one large script into many small scripts fix the error?
Usually no. Each script is compiled into its own IL unit with its own tag-handle pool, but the cumulative footprint across many scripts can still exceed the panel's overall tag-resolver budget. The reliable fix is refactoring (Path A), buffering (Path D), or moving logic into the PLC (Path C).
Can the project still run when the error popup appears?
Yes, the MP 270 runtime loads the project despite the error, but the affected scripts run inside a guarded re-evaluation path that can be 5×–10× slower than normal. This is acceptable for commissioning tests but should not be left in production because of the cycle-time penalty.
What are the hard tag limits for the MP 270?
The MP 270 supports up to 2 048 total HMI tags (power tags plus internal tags combined) and up to 1 000 internal/local tags. The remaining budget of up to 1 048 may be allocated to power tags. These limits are documented in the WinCC Flexible Engineering manual and the SIMATIC HMI device manual for the MP 270 (6AV6 545-0BA15-2AX0).