T09 · Insecure Skill Coding Practices
- Location
scripts/openseti.py:301- Finding
Coordinator-Controlled Arbitrary URL Fetch Enables SSRF and Resource Exhaustion
- Content
View full analysis
Vulnerability Details
File Location:
scripts/openseti.py:301-311, called fromscripts/openseti.py:407
Vulnerability Type: Server-Side Request Forgery from the client host, unrestricted outbound request, and unbounded download
Risk Level: HighVulnerable Code
python def download_work_unit(download_url): """Download work unit data""" try: # Handle relative URLs if download_url.startswith('/'): url = f"{COORDINATOR_URL}{download_url}" else: url = download_url res = requests.get(url, timeout=60) res.raise_for_status() return res.content except Exception as e: print(f"❌ Error downloading: {e}") return NoneThe function is reached using a URL supplied in the coordinator response:
python data = download_work_unit(work['download_url'])Technical Analysis
The coordinator controls
work['download_url']. Absolute URLs are accepted without validating their scheme, hostname, resolved IP address, port, or destination network. Therequestslibrary also follows HTTP redirects by default, so validating only the initial string would not be sufficient.A malicious or compromised coordinator could instruct the scanner to request:
- Loopback services such as
http://127.0.0.1:... - Private-network services on RFC1918 addresses
- Link-local services, including cloud instance metadata endpoints
- Unexpected non-coordinator Internet hosts
- Extremely large responses intended to consume memory or bandwidth
The function uses
res.content, which buffers the entire response in memory. The 60-second timeout limits request duration but does not impose a response-size limit. The downloaded content is not executed, which reduces the risk of remote code execution, but it is subsequently parsed and processed with NumPy.This network authority exceeds the minimum privilege required to download radio-telescope work units from ...[truncated 1382 chars]
- Loopback services such as
- Remediation
View remediation
Remediation Suggestions
- Permit downloads only from an explicit allowlist of trusted HTTPS hostnames.
- Reject URLs containing credentials, non-HTTPS schemes, unexpected ports, or malformed hostnames.
- Resolve the hostname and reject loopback, private, link-local, multicast, reserved, and cloud metadata address ranges for both IPv4 and IPv6.
- Disable redirects with
allow_redirects=False, or validate the destination after every redirect. - Stream responses using
stream=Trueand enforce a strict maximum size before buffering or analysis. - Validate
Content-Lengthwhen available, while still enforcing the limit during streaming. - Apply separate connection and read timeouts.
- Prefer coordinator-relative, cryptographically authenticated work-unit identifiers rather than arbitrary URLs.
- Verify downloaded work units using a coordinator-provided hash and expected size.
Example defensive design:
python res = requests.get( validated_url, timeout=(10, 30), allow_redirects=False, stream=True, ) maximum_size = 2 * 1024 * 1024 data = bytearray() for chunk in res.iter_content(chunk_size=65536): data.extend(chunk) if len(data) > maximum_size: raise ValueError("Work unit exceeds the permitted size")
