Back to skill

Security audit

lab-unit-harmonization

Security checks for vulnerabilities and agentic risk

Overview

This skill is not malware, but it should be reviewed because its lab-cleaning instructions can silently drop or alter clinical measurements.

Review this skill carefully before using it on real patient or research data. It should require explicit source units or trusted source mappings, preserve original values, log every conversion or dropped record, keep full-precision numeric canonical data, and treat range checks as validation warnings rather than automatic conversion or clamping rules.

Vulnerability Patterns
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (3)

T09 · Insecure Skill Coding Practices

Warning
Location
SKILL.md:119
Finding
Ambiguous comma parsing can silently corrupt clinical measurements<![CDATA[ ## Vulnerability Details **File Location**: `SKILL.md`, lines 119-130 **Vulnerability Type**: Ambiguous numeric parsing and fail-open data handling **Risk Level**: Medium ### Vulnerable Code ```python # Handle European decimals (comma as decimal separator) # In this dataset, comma is used as decimal separator, not thousands if ',' in s: s = s.replace(',', '.') # Parse as float try: return float(s) except ValueError: return np.nan ``` ### Technical Analysis The parser unconditionally interprets every comma as a decimal separator, even though the Skill also claims to handle values containing thousands separators. This creates two failure modes: - A value such as `1,234` is parsed as `1.234`, changing its magnitude by a factor of 1,000. - A value such as `1,234.5` becomes `1.234.5`, fails parsing, and is silently converted to `NaN`. Returning `NaN` without raising an error, preserving the original value, or recording a validation event makes the corruption difficult to detect. The result can subsequently be treated as missing data or omitted from downstream analysis. ### Attack Path 1. A clinical data source supplies a value containing a comma, such as `1,234` or `1,234.5`. 2. `parse_value` replaces every comma with a period. 3. The value is either interpreted at the wrong magnitude or becomes syntactically invalid. 4. Invalid values are silently replaced with `NaN`. 5. The corrupted or missing value propagates into unit conversion, record filtering, research datasets, or analytical models without an explicit failure. An attacker able to influence imported laboratory values could deliberately use ambiguous separators to cause selected values to be altered or discarded. ### Impact Assessment This issue does not grant operating-system privileges, code execution, or access to additional resources. Its impact is limited to the integrity and availability of data processed according to the Skill. Potential consequences include: - Si ...[truncated 206 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Require explicit source-locale or schema metadata instead of inferring separator meaning from the string alone. - Use a locale-aware numeric parser with separately configured decimal and grouping separators. - Reject values containing both comma and period unless their format matches a known source convention. - Do not silently convert parsing failures to `NaN`; emit a validation error containing the row, column, original value, and source. - Preserve the original unmodified value in an audit column. - Add tests for at least `1,234`, `1,234.5`, `12,34`, `1.234,5`, scientific notation, whitespace, and malformed input. ]]>

T09 · Insecure Skill Coding Practices

Error
Location
SKILL.md:140
Finding
Range-based unit inference can silently apply an incorrect conversion<![CDATA[ ## Vulnerability Details **File Location**: `SKILL.md`, lines 140-181 **Vulnerability Type**: Unsafe unit inference based on physiological ranges **Risk Level**: High ### Vulnerable Code ```python def convert_unit_if_needed(value, column, reference_ranges, conversion_factors): """ If value is outside expected range, try conversion factors. Logic: 1. If value is within range [min, max], return as-is 2. If outside range, try each conversion factor 3. Return first converted value that falls within range 4. If no conversion works, return original (NO CLAMPING!) """ if pd.isna(value): return value if column not in reference_ranges: return value min_val, max_val = reference_ranges[column] # If already in range, no conversion needed if min_val <= value <= max_val: return value # Get conversion factors for this column factors = conversion_factors.get(column, []) # Try each factor for factor in factors: converted = value * factor if min_val <= converted <= max_val: return converted # No conversion worked - return original (NO CLAMPING!) return value ``` ### Technical Analysis The algorithm infers a measurement's unit solely from whether its numeric value falls within a broad expected physiological range. This is not a reliable unit discriminator. A value expressed in an alternative unit may already fall within the target range and therefore remain unconverted. Conversely, a legitimate extreme or anomalous value in the target unit may be multiplied by a conversion factor merely because the converted result appears plausible. The function also returns the first conversion factor that produces an in-range result. For analytes supporting multiple alternative units, more than one conversion can produce a plausible result. The order of `conversion_factors` then determines the output rather than verified unit metadata. Physiol ...[truncated 1610 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Require an explicit unit for each value or a verified source-level unit mapping. - Normalize units through a validated implementation of UCUM or an equivalent controlled unit system. - Reject unknown, missing, or incompatible units instead of inferring them from physiological ranges. - Use expected ranges only as post-conversion validation warnings. - Preserve the original value, original unit, converted value, target unit, conversion formula, and source identifier. - Require explicit disambiguation when multiple conversion formulas could produce plausible values. - Record every conversion in an auditable log. - Add tests covering target-unit outliers, alternative-unit values that overlap target ranges, boundary values, and analytes with three supported units. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
SKILL.md:202
Finding
Uniform two-decimal formatting causes clinically significant precision loss<![CDATA[ ## Vulnerability Details **File Location**: `SKILL.md`, lines 202-208 **Vulnerability Type**: Destructive fixed-precision formatting **Risk Level**: Medium ### Vulnerable Code ```python # Format all numeric columns to X.XX format for col in numeric_cols: df[col] = df[col].apply(lambda x: f"{x:.2f}" if pd.notna(x) else '') ``` ### Technical Analysis The Skill applies exactly two decimal places to every laboratory feature, regardless of the analyte's required precision, reporting limit, or clinical interpretation. This is destructive when formatting replaces the canonical numeric representation. Low-concentration markers can be rounded to zero, while values requiring three or more decimal places can become indistinguishable. For example, a low troponin value may become `0.00`, and a urine-specific-gravity value such as `1.005` may become `1.00`. The code also converts numeric columns to strings, which can complicate later numeric validation and encourage consumers to treat the rounded representation as the authoritative value. ### Attack Path 1. A valid high-precision laboratory result enters the formatting stage. 2. The same two-decimal format is applied regardless of analyte type. 3. Clinically relevant digits are rounded away. 4. The rounded string replaces the more precise numeric value. 5. A downstream consumer performs threshold checks, aggregation, modeling, or reporting using the altered value. An attacker who controls input values could select measurements near rounding boundaries so that the formatted output crosses a decision threshold or collapses to zero. ### Impact Assessment This issue does not provide additional privileges, code execution, or unauthorized system access. Its impact concerns data integrity across every formatted numeric column. Potential consequences include: - Loss of low-level biomarker measurements - Threshold misclassification - Collapse of distinct measurements into identical outputs - Reduced reprod ...[truncated 145 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Retain full numeric precision in the canonical dataset. - Apply rounding only to a separate presentation or export layer. - Define analyte-specific precision, significant-figure rules, and reporting limits. - Preserve laboratory qualifiers such as `<`, `>`, and below-detection-limit indicators. - Store both the original source value and any display-formatted value. - Keep analytical columns numeric rather than replacing them with strings. - Add boundary tests for troponins, urine specific gravity, pH, and other precision-sensitive measurements. ]]>
Vulnerability Patterns
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
Findings (2)

Intent-Code Divergence

Medium
Confidence
95% confidence
Finding
The skill instructs users to drop any row containing missing numeric values before harmonization, which is a destructive data-processing step not required for unit normalization. In healthcare analytics, this can silently remove large portions of patient data, bias cohorts, distort downstream models or clinical summaries, and potentially exclude vulnerable patients with partial lab panels.

Intent-Code Divergence

Medium
Confidence
98% confidence
Finding
The documentation first states that out-of-range values should be returned unchanged and explicitly says not to clamp, but later permits tolerance-based clamping near boundaries. This inconsistency can lead implementers to silently alter clinical measurements at decision thresholds, masking true abnormalities and producing non-reproducible transformations across systems.

Static analysis

No suspicious patterns detected.