T09 · Insecure Skill Coding Practices
- Location
scripts/build_swmm_inp.py:720- Finding
Unescaped Input Allows SWMM INP Directive and Section Injection
- Content
View full analysis
str: if value is None: raise ValueError(f"{context} missing required field '{field}'") text = str(value).strip() if not text: raise ValueError(f"{context} field '{field}' must be a non-blank string") return text ``` The configuration title is also accepted without output-safety validation and emitted directly into the INP document: ```python def title_from_config(config: dict[str, Any]) -> str: return str(config.get("title") or "SWMM model generated by swmm-builder") ``` ```python def emit_title(title: str) -> list[str]: return ["[TITLE]", title] ``` Other attacker-controlled textual fields are similarly interpolated directly into structured SWMM rows: ```python def emit_subcatchments( subcatchments: dict[str, dict[str, Any]], params_subcatchments: dict[str, dict[str, Any]], *, default_gage_id: str, ) -> list[str]: lines = [ "[SUBCATCHMENTS]", ";;Name Rain Gage Outlet Area %Imperv Width %Slope CurbLen SnowPack", ] for subcatchment_id in sorted(subcatchments): sc = subcatchments[subcatchment_id] p = params_subcatchments[subcatchment_id] rain_gage = sc.get("rain_gage") or default_gage_id lines.append( f"{subcatchment_id:<18} {rain_gage:<18} {sc['outlet']:<18} " f"{format_num(sc['area_ha'] ...[truncated 3683 chars]- Remediation
View remediation
