T09 · Insecure Skill Coding Practices
- Location
scripts/create_spark.py:20- Finding
Predictable Temporary File Permits Symlink-Based File Overwrite and Concurrent Write Races
- Content
View full analysis
Vulnerability Details
File Location:
scripts/create_spark.py:20-23;scripts/update_spark.py:17-20
Vulnerability Type: Predictable and symlink-following temporary file
Risk Level: MediumVulnerable Code
scripts/create_spark.py:20-23:python tmp_file = DATA_FILE + ".tmp" with open(tmp_file, 'w') as f: json.dump(data, f, ensure_ascii=False, indent=2) os.replace(tmp_file, DATA_FILE)scripts/update_spark.py:17-20:python tmp_file = DATA_FILE + ".tmp" with open(tmp_file, 'w') as f: json.dump(data, f, ensure_ascii=False, indent=2) os.replace(tmp_file, DATA_FILE)Technical Analysis
Both write operations use the fixed pathname
思考火花.json.tmp. The ordinaryopen(..., 'w')operation follows symbolic links and truncates the resolved target before writing. If another local process can create or replace this temporary path, it can point the path at another file writable by the user running the skill.The fixed name also causes all concurrently running create and update operations to use the same temporary file. Because the scripts perform an unlocked read-modify-write sequence, concurrent executions can overwrite each other's temporary data, fail during
os.replace, generate duplicate identifiers, or silently lose updates.Exploitation requires the attacker to have write access to the
~/.openclaw/workspace/collectiondirectory or otherwise control the temporary path. This does not independently cross OS-user privilege boundaries.Attack Path
- The attacker obtains write access to
~/.openclaw/workspace/collection. - The attacker creates
思考火花.json.tmpas a symbolic link to another file writable by the victim account. - The victim invokes
create_spark.pyorupdate_spark.py. open(tmp_file, 'w')follows the symbolic link and truncates the linked target.- The script writes attacker-influenced or application-generated JSON into that targe ...[truncated 1109 chars]
- The attacker obtains write access to
- Remediation
View remediation
Remediation Suggestions
- Create a uniquely named temporary file in the destination directory with
tempfile.NamedTemporaryFile(delete=False, dir=destination_directory). - Open the temporary file with restrictive permissions, ideally mode
0600. - Use protections such as
O_NOFOLLOWandO_EXCLwhere supported to prevent symbolic-link following and pre-existing-file races. - Flush Python buffers and call
os.fsync()before atomically replacing the destination. - Clean up the unique temporary file if serialization or replacement fails.
- Protect the entire load-modify-save operation with an inter-process file lock. Locking only the final write is insufficient to prevent lost updates and duplicate IDs.
- Ensure
~/.openclaw/workspace/collectionis owned by the intended user and is not writable by other accounts.
- Create a uniquely named temporary file in the destination directory with
