T05 · Unauthorized Access and Privilege Escalation
- Location
scripts/smyx_elderly_nightmare_startle_detect_analysis.py:45- Finding
Caller-Controlled Identity Can Be Exchanged for Account Access Tokens
- Content
View full analysis
Vulnerability Details
File Location:
scripts/smyx_elderly_nightmare_startle_detect_analysis.py:45-60;skills/smyx_common/scripts/util.py:458-471, 548-612
Vulnerability Type: Authentication and account impersonation flaw
Risk Level: HighVulnerable Code
The command-line entry point accepts a hidden identity argument and passes it directly into the identity resolver:
python parser.add_argument("--open-id", required=False, help=argparse.SUPPRESS)python # Initialize the internal user identity. OpenIdUtil.resolve_current_open_id(args.open_id, use_current=bool(args.open_id))The resolver accepts the supplied value without authenticating its ownership:
python @classmethod def resolve_current_open_id(cls, open_id=None, use_current=True): """Resolve and initialize the current open-id.""" resolved_open_id = (open_id or "").strip() if isinstance(open_id, str) else open_id if not resolved_open_id and use_current: resolved_open_id = ConstantEnum.CURRENT__OPEN_ID or ConstantEnum.CURRENT__USER_NAME if not resolved_open_id: resolved_open_id = cls.get_api_key_file_open_id() if not resolved_open_id: resolved_open_id = cls.get_or_create_default_open_id() ConstantEnum.CURRENT__OPEN_ID = resolved_open_id if not ConstantEnum.CURRENT__USER_NAME: ConstantEnum.CURRENT__USER_NAME = resolved_open_id return resolved_open_idThe resulting identity is then submitted to a silent login or registration endpoint:
python def _get_or_create_user(username): _url = ApiEnum.BASE_URL_HEALTH + "/sys/phoneLogin" open_id = username _data = { "silent": 1, "register": 1, "openId": open_id, "mobile": username, "source": ConstantEnum.DEFAULT__SKILL_HUB_NAME } try: _response = requests.post(_url, json=_data) if _response.status_code == 200: _response_json = _response.json() if _response_json ...[truncated 3786 chars]- Remediation
View remediation
Remediation Suggestions
- Remove
--open-idfrom all caller-accessible command-line interfaces. Hiding it withargparse.SUPPRESSis not an access control. - Obtain the current identity exclusively from an authenticated platform context rather than from command-line input, content extracted from a user request, or a mutable local file.
- Require a server-issued, signed identity assertion that binds the account identifier to the authenticated caller, intended Skill, and current session.
- Change the login API so that possession of an
openIdor username alone can never produce account credentials. Require an established authenticated session, signed platform token, or explicit ownership challenge. - Disable automatic silent registration when accessing existing accounts. Account creation and account login should use separate endpoints and authorization policies.
- On the server, derive report ownership from the validated access token rather than accepting client-selected usernames or identity fields as authorization inputs.
- Reject requests when the identity from the trusted platform context conflicts with any identity supplied by the client.
- Do not persist returned tokens until identity ownership and token scope have been verified. Store necessary credentials using operating-system-protected secret storage and restrictive file permissions.
- Revoke tokens previously created through identifier-only silent login and review access logs for requests that switched among unrelated identities.
- Add security tests proving that supplying another user’s identifier cannot obtain tokens, list reports, retrieve export links, or create analysis records for that user.
- Remove
