Questions in the order people ask them on the SWMM forums, answered for StormSewer. Where the answer is the engine's behaviour the manual cites the EPA document; where it is a forum finding the thread is linked and paraphrased, never copied. Engine error numbers are indexed in Appendix C.
The report ends each of Runoff Quantity Continuity, Flow Routing
Continuity, Quality Routing Continuity and Groundwater Continuity with a
Continuity Error (%) line: the mismatch between what came
in and what went out plus what is stored, as a percentage of the inflow.
StormSewer shows the largest absolute value in the run panel as
worst continuity.
A model can run and be wrong. runswmm
exits 0 regardless, and a finished run with a 40 % continuity error is
still a finished run. The forum's own words for this are that SWMM lets
a model silently fail (r/civilengineering).
Always read the number.
Working thresholds from the OpenSWMM threads (4223, 3925): under 1 % is good; under 2 % is usually fine; 5 % needs a reason; anything above that means the routing did not converge somewhere and the results at that place are not trustworthy. Some reviewers ask for 0.5 %. The sign is only which side the imbalance fell on; a negative error is not better than a positive one (11479).
Where it comes from, in the order to check:
ROUTING_STEP, or
set VARIABLE_STEP (0.5–0.75) and a
MINIMUM_STEP.LENGTHENING_STEP (10–30 s is a common setting) or merge
them.SURCHARGE_METHOD EXTRAN (14273,
USEPA
#210); try `SLOT`, and check MIN_SURFAREA.ALLOW_PONDING NO: water
lost to flooding is accounted as Flooding Loss, not an
error — but a huge flooding loss with a small error is its own warning
sign.The engine prints only the five worst nodes in Highest Continuity Errors and the five worst links in Highest Flow Instability Indexes (USEPA #32). The Run Status window (§9.4) shows every entry the report carries, colours each continuity section green below 1 %, amber to 10 % and red above, and selects a listed node or link on click; the Model Report keeps the whole report text.
Check, in order: the ERROR/WARNING lines in
the run panel; the continuity error; the Node Flooding Summary and the
Conduit Surcharge Summary in Tables; then the Profile with Max HGL along
the trunk. A model whose every node floods is telling you about an
offset or a unit, not about drainage.
An oscillating hydrograph, a link with a large instability index, or
a step count that never converges
(% of Steps Not Converging in the Routing Time Step
Summary) is a numerical problem, not a hydraulic one. RM II §3.4 is the
reference. What people report helping, in rough order of effect (2346,
3938,
25086):
ROUTING_STEP, or VARIABLE_STEP
with a MINIMUM_STEP;LENGTHENING_STEP so short links are computed as if
longer;INERTIAL_DAMPING PARTIAL or FULL
(FULL drops the inertial terms as flow approaches critical;
RM II §3.2);NORMAL_FLOW_LIMITED BOTH;MIN_SURFAREA raised on tiny junctions;Kinematic wave is faster and cannot surcharge or back up; if your
model has surcharge, backwater or loops it needs DYNWAVE
(RM II §2.2).
Three words the engine uses with exact meanings (UM §3.3 and the Node Surcharge and Node Flooding summaries):
MaxDepth, plus SurDepth if set) and water left
the system. With ALLOW_PONDING NO that water is gone
(counted as Flooding Loss). The HGL in a profile stops at the rim.ALLOW_PONDING YES
and an Aponded area on the node, flooded water
sits on the node in a pond of that area and drains back in when it can.
The HGL can then rise above the rim (29608,
15558).
Without an Aponded area, ALLOW_PONDING YES
does nothing at that node.SurDepth (surcharge depth) is an extra height above the
rim before flooding is declared — a sealed manhole cover.
ERROR 209: undefined object X at line N means a row
names an object that does not exist. The usual culprits (16685,
13117,
USEPA
#171):
RainGage or Outlet
was deleted or renamed by hand;[INFLOWS], [DWF] or [TAGS]
row for a deleted node;[REPORT] line (NODES J5 J6) that still
lists a deleted object — the engine treats that as fatal.StormSewer's validator catches all of these before the run
(link "…" does not exist,
rain gage "…" does not exist,
outlet "…" is neither a node nor a subcatchment,
to node "…" does not exist) and refuses to run until they
are fixed, and its delete and rename commands keep references in step so
they do not arise from editing here. They arise from files edited
elsewhere. Click the finding to go to the row.
Also fatal at read time: a duplicate name (the engine ignores case,
so J1 and j1 are the same object — the
validator says so), a row with too few fields, a zero or negative length
(ERROR 111) or area (ERROR 211), a REPORT_STEP shorter than
ROUTING_STEP (ERROR 195), an outfall with more than one
link (ERROR 141), an end date before the start (ERROR 191). The
validator checks each of these and names the engine's code.
A link's InOffset and OutOffset are the
heights of its ends above the node inverts when
LINK_OFFSETS DEPTH, or absolute elevations when
ELEVATION (UM §3.3, Appendix D [CONDUITS]).
The forum history says the manual's first definition was unclear and
people still get it backwards (3507,
9489).
Two things the engine does without asking, noted only by a
WARNING line in the report that is easy to miss (swmm5.org):
ELEVATION offset under the invert) is raised to the node
invert — the offset becomes 0;MaxDepth) raises the node's rim to the crown; with
MaxDepth 0 the rim is the highest crown.StormSewer's validator flags a negative offset and an
ELEVATION offset below the node invert before the run; the
profile draws what the engine will use (chapter 11). A drop through a structure is a
pipe entering above the node invert — an InOffset on the
downstream pipe's upstream end is not how to say that; put the offset on
the incoming pipe's OutOffset.
Switching LINK_OFFSETS between DEPTH and ELEVATION is
the same trap in miniature: the keyword alone changes what every offset
in the file means, and every pipe moves. The Options dialog says so
beside the field and offers Convert existing offsets with the node
inverts (same undo step) (§8.2). Take it unless the numbers are
already in the new convention.
Changing FLOW_UNITS changes how every number in the file
is read, and converts none of them (4235,
32845).
The engine does the same: the labels change, the numbers do not. When
you change the keyword in Project → Options…, StormSewer opens the
unit-switch wizard (§8.2): it
lists the groups below with the number of rows each would touch,
converts the ones you tick as one undo step, and can copy its report.
Anything it does not cover you convert by hand or with Replace in
column → Scale (§6.4). The checklist of what a
switch between U.S. and SI touches:
| Section | What must change |
|---|---|
[JUNCTIONS], [OUTFALLS],
[STORAGE], [DIVIDERS] |
elevations and depths: ft ↔︎ m |
[CONDUITS] |
length ft ↔︎ m; offsets; Roughness is Manning's n and is
the same in both systems |
[XSECTIONS] |
every Geom column ft ↔︎ m |
[SUBCATCHMENTS] |
area ac ↔︎ ha; width ft ↔︎ m |
[SUBAREAS] |
depression storage in ↔︎ mm |
[INFILTRATION] |
Horton rates in/hr ↔︎ mm/hr; Green-Ampt suction in ↔︎ mm, conductivity in/hr ↔︎ mm/hr |
[RAINGAGES] and their series |
in/hr ↔︎ mm/hr, or in ↔︎ mm for VOLUME |
[INFLOWS], [DWF] |
baseline flows and any FLOW series in the flow unit |
[PUMPS] curves |
head ft ↔︎ m, flow in the flow unit |
[WEIRS] Qcoeff |
dimensional: 3.33 (U.S.) ↔︎ 1.84 (SI) for a sharp-crested transverse weir; the engine expects the metric form in an SI model (3620) |
[ORIFICES] Qcoeff |
dimensionless — unchanged |
[STORAGE] curves and [CURVES] |
depth ft ↔︎ m; area ft² ↔︎ m²; flows |
[DIVIDERS] cutoff flows, tabular curves |
flow unit |
[OPTIONS] MIN_SURFAREA |
ft² ↔︎ m² |
[LID_CONTROLS], [LID_USAGE] |
thicknesses in ↔︎ mm; areas ft² ↔︎ m² |
[EVAPORATION], [TEMPERATURE],
[SNOWPACKS] |
in/day ↔︎ mm/day, °F ↔︎ °C |
[LOADINGS], pollutant concentrations |
usually unchanged (mg/L) — check |
The storm-sewer design panel refuses metric models rather than convert (§12.2).
Width is the width of the overland flow path:
conceptually the subcatchment's area divided by the length of the
longest overland flow path to the collector (RM I §3.8). It sets the
runoff hydrograph's timing; the same area with half the width peaks
later and lower. Its estimation is the most-asked question on the forums
(3818,
4862,
11520)
and Guo (2012) called it a frequent source of user error. Rules of thumb
people use: area ÷ maximum overland flow length; for a rectangular lot
draining to a gutter along one side, the length of that side; for a
subcatchment draining to a pipe running through it, about twice the pipe
length (flow comes from both sides), with a skew factor when the two
sides are unequal. Flow lengths over about 500 ft of true sheet flow are
rare.
The design mapping uses Area / Width as the flow length
for Kirpich (§15.3), so a wrong width also
moves the design Tc. The validator warns when a width is zero: no runoff
leaves such a subcatchment.
A Type 2 pump (flow versus wet-well depth, stepwise) starts at
Startup and stops at Shutoff depth; with the
two close together and a small wet well it cycles every step and the
continuity error climbs (2773).
Separate the depths, enlarge the wet well, or use a Type 3 or 4
curve.
ERROR 2xx: … clause invalid or out of sequence in
[CONTROLS] is nearly always a second IF inside
one rule: every IF needs its own RULE name
line (9552,
16749).
The syntax is UM Appendix C. StormSewer does not parse rules; it patches
object names in them on rename.
ERROR 363: invalid data in rain gage file (or in a
time-series file) means the engine's reader could not parse a line (r/stormwater).
The file formats are UM §11.5. Common causes: a header line the format
does not allow, a blank line, a date in the wrong order, a station name
over 50 characters in a GHCN download (USEPA
#224), a comment line long enough to overflow the reader's buffer
(USEPA
#165), or an interval that does not match the gage's
Interval. Bring the data into a [TIMESERIES]
instead with Project → Time Series → Import… (§8.5): it detects the delimiter and
date format, reads a GHCN-Daily station csv directly (and cuts the
over-long station name to SWMM's limit, saying so), and can make the
gage with a matching format and interval. The engine's own parser then
reads the series with the model and any problem is reported with a line
number. Export to File… goes the other way for series too long for the
.inp, writing exactly the file format the engine
expects.
WARNING 09: time series interval greater than recording interval
means the gage's Interval is shorter than the series'
spacing; set them equal.
A hotstart file ([FILES] SAVE HOTSTART x.hsf then
USE HOTSTART x.hsf) carries the end state of one run into
the start of another (UM §11.6). It is binary, model-specific, and has
no checker. ERROR 335: error reading hotstart file means
the file was made by a model with a different object count or order —
any add or delete since it was saved (19483,
USEPA
#214). Regenerate it after every structural edit; there is no way to
inspect it. StormSewer does not manage hotstart files; the
[FILES] lines are text in the Options dialog.
The common uses: a warm-up run of a day or two of dry weather to fill the pipes and wet wells before the event, and a tidal outfall's initial condition.
[COORDINATES] row is not drawn; the
validator lists each one
(no [COORDINATES] row, so it cannot be drawn) and the
Project browser still counts it. Add the row in the
[COORDINATES] attribute table, or select the object in the
browser and place it.[BACKDROP] DIMENSIONS,
which View → Backdrop → Load Image… fills from a world file beside the
image and Georeference… edits by hand (§3.9). An image that lands in the wrong
place has a world file in other units or none; fix the extent in the
dialog and Write world file so the next load is right. Rotation
in a world file is ignored (SWMM cannot draw a rotated backdrop).
Lengths are never measured from the picture; Compute Conduit Lengths
measures from the drawn objects.[MAP] DIMENSIONS is the EPA GUI's map extent;
StormSewer's view fits to the objects regardless, but the dialog (View →
Map Dimensions…) sets it from the model or the backdrop so the EPA GUI
opens the file sensibly, and [MAP] Units feeds the length
factor.Different engine versions give different numbers, because bugs were fixed: 5.0 → 5.1 changed evaporation and infiltration accounting; 5.1 → 5.2 fixed elliptical-pipe geometry, changed the inlet handling, and more (4769, USEPA #144; EPA's own change lists are at epa.gov). A calibrated model is calibrated to an engine. Results → Compare Engines… shows the difference object by object, and every StormSewer run and report carries the engine version and binary hash so a number can be tied to the binary that produced it.
The storm-sewer design panel and the SWMM run will not agree on peaks
either, and should not: one is a Rational peak at one intensity, the
other a routed hydrograph under a hyetograph. Typical reasons for a 2×
gap (r/Hydrology):
the Rational Tc floor; a subcatchment width that gives a very different
time to peak; a WET_STEP or rain interval too coarse for a
small catchment; storage or surcharge attenuating the SWMM peak. Use the
design panel to size and check; use the run to see what the sized system
does.
Runtime is the routing step count times the network size. Continuous
models with LID controls are the usual complaint (5464);
`THREADS` in Options uses more cores for the routing;
REPORT_STEP does not change runtime but changes the
.out size; DRY_STEP can be long. The Stop item
cannot interrupt a run in this build, so check the dates before pressing
F5.
The engine runs as a separate process: an engine crash cannot take
the editor down, and the run is reported as failed with the report's
last lines. If StormSewer itself stops, the model on disk is whatever
you last saved, plus the autosave snapshot: while the model is dirty its
text is written every N minutes (Run → Autosave every N min,
default 2) to <model>.inp.autosave beside the file,
or to %APPDATA%\StormSewer\recovery for a model that has no
file yet. On the next open of that file StormSewer asks Recover
unsaved changes? with the file's and the snapshot's timestamps:
Restore autosave or Discard it, keep the file. Saving
or closing the model removes the snapshot. Ctrl+S is still
cheap and lossless.
The stock EPA engine can fail to open a model whose path contains
characters outside ASCII (õ ä ö ü, CJK) — reported against
the Windows build and the Python bindings (swmm-python
#71, #70).
StormSewer sidesteps it: a model on a non-ASCII path is run from a
scratch copy under %TEMP%\StormSewer\run\<hash>\,
with its [FILES] and data files copied beside it so
relative paths still resolve, and the Run Status window says
Ran a scratch copy and names the path the engine read (§9.2). The .rpt and
.out are beside the copy, and the run history, Compare Runs
and the Python terminal use that location. Only the engine sees the
copy; your model stays where it is.
Live, on every edit, shown under the map and in Project → Validate Model. Errors refuse a run; warnings do not.
Errors: a link whose from/to node does not exist; a subcatchment
whose outlet is neither a node nor a subcatchment, or whose rain gage
does not exist; a duplicate name within a section, across the node
sections or across the link sections, including names that differ only
by case; a conduit without an [XSECTIONS] row; a row
shorter than its section allows; [COORDINATES],
[VERTICES], [POLYGONS], [SYMBOLS]
or [XSECTIONS] rows for objects that do not exist; a zero
or negative conduit length or subcatchment area;
REPORT_STEP shorter than ROUTING_STEP; an
outfall with more than one link, or with an outgoing link; a simulation
that ends before it starts.
Warnings: a node without coordinates; more than one coordinate row
for a node; a node no link connects to; a rain gage no subcatchment
uses; a negative offset, or an ELEVATION offset below the
node invert (the engine silently uses 0 and raises the rim if it must —
WARNING 03); a subcatchment width of zero; a curve or series with no
points; a junction whose only outgoing links are weirs or orifices;
DRY_STEP shorter than WET_STEP (the engine
raises it — WARNING 06).
It does not check hydraulics, units, or anything inside
[CONTROLS], [LID_CONTROLS],
[STREETS] or the climate sections.