npx claudepluginhub jygzyc/decx --plugin decxThis skill uses the workspace's default tool permissions.
Use this skill for APK app-layer vulnerability hunting.
assets/coverage-template.jsonassets/findings-template.jsonassets/poc-handoff-template.jsonassets/recon-template.jsonassets/report-target-vuln-en.mdassets/report-target-vuln-zh.mdassets/report-template-en.mdassets/report-template-zh.mdassets/report-template.mdassets/resume-template.jsonreferences/app-activity-clickjacking.mdreferences/app-activity-exported-access.mdreferences/app-activity-fragment-injection.mdreferences/app-activity-intent-redirect.mdreferences/app-activity-lifecycle.mdreferences/app-activity-path-traversal.mdreferences/app-activity-pendingintent-abuse.mdreferences/app-activity-setresult-leak.mdreferences/app-activity-task-hijack.mdreferences/app-activity.mdHunts Android framework vulnerabilities in processed bundles, system_server, Binder services, AIDL implementations, vendor services, and OEM code using DECX CLI.
Performs static analysis of Android APK/AAB files with MobSF to detect hardcoded secrets, insecure permissions, vulnerable components, and crypto flaws. For pentesting, CI/CD gates, and APK reviews.
Performs automated static analysis of Android APK/AAB files using MobSF to detect hardcoded secrets, insecure permissions, vulnerable components, and weak cryptography. For pre-deployment scans, pentesting, or CI/CD security gates.
Share bugs, ideas, or general feedback.
Use this skill for APK app-layer vulnerability hunting.
Scope:
decxcli-framework-vulnhuntdecxcli-pocCeiling:
statically-supportedpoc-validated, runtime-validated, or equivalentdecx code and decx ard command must include -P <port>system-services, perm-info, and framework collect/process do not use -P <port>"package.Class.method(paramType):returnType"... in signatures--help command before retryingDefault filter options for commands that support them (classes, app-receivers, get-aidl, exported-components, search-global, search-class):
--limit <n> return at most N results
--include-package <pattern> only include matching items (repeatable)
--exclude-package <pattern> exclude matching items (repeatable)
--no-regex treat filter values as literal text
Filters use regex by default. Always exclude SDK packages unless the target is a framework or SDK-interaction bug:
--exclude-package "androidx\\..*" --exclude-package "android\\.support\\..*" --exclude-package "kotlin\\..*" --exclude-package "java\\.lang\\..*"
system_server, framework jars, vendor services, Binder service implementations, AIDL service families, or OEM framework logic, switch to decxcli-framework-vulnhuntRecommended work dir:
.decx-analysis/<target-name>/
Recommended artifacts:
recon.jsoncoverage.jsonfindings.jsonreport.mdresume.jsonpoc-handoff.jsonTemplates:
assets/recon-template.jsonassets/coverage-template.jsonassets/findings-template.jsonassets/resume-template.jsonassets/poc-handoff-template.json| State | Meaning | Allowed |
|---|---|---|
candidate | suspicious path, evidence incomplete | Yes |
statically-supported | static evidence proves reachability, control, bypassability, and visible impact | Yes |
rejected | explicit blocking evidence or no real impact | Yes |
poc-validated | PoC-confirmed | No |
runtime-validated | runtime-confirmed | No |
State rules:
candidaterejectedreferences/risk-rating.md: do not reportPendingIntent chain, and scan-driven entrypoint must appear in coverage.jsonrejected requires explicit evidence-backed blocking reasoncandidate and record the exact missing proofEvery reported finding must answer:
reachablecontrollablebypassConditionsimpactEvidenceratingRationaleApp VulnHunt Progress
- [ ] Phase 1: Prepare target and confirm session
- [ ] Phase 2: Build full attack-surface inventory
- [ ] Phase 3: Write first-pass coverage verdicts for every target
- [ ] Phase 4: Deep trace every non-rejected target
- [ ] Phase 5: Finalize exploitability and residual risk set
- [ ] Phase 6: Generate final report
- [ ] Handoff: Pass minimal finding set to decxcli-poc
Goal: open the APK and confirm DECX is healthy.
decx process open "<apk-path>" -P <port>
decx process status -P <port>
Do not close the session automatically. If needed, tell the user:
decx process close "<name>"
Goal: produce a complete external-surface inventory in recon.json.
Execution model:
decx commandsRecon commands:
decx ard exported-components --type <pattern> --exclude-type <pattern> -P <port>
decx ard app-deeplinks -P <port>
decx ard app-receivers --exclude-package "androidx\\..*" --exclude-package "android\\.support\\..*" -P <port>
decx ard app-manifest -P <port>
decx ard get-aidl --exclude-package "androidx\\..*" --exclude-package "android\\.support\\..*" -P <port>
decx ard strings -P <port>
Recon requirements:
<permission><uses-permission>android:permission, readPermission, writePermissionprotectionLevel, owner, and usagesignature and signatureOrSystem as protected by default, but keep tracing when the app forwards, proxies, re-grants, reuses victim identity, exposes a weaker alternate path, or ownership is uncertainPendingIntent, and URI-grant chaintargetIdcandidateMust-consider surfaces:
PendingIntentClipData and URI grantsintent://, custom schemes, postMessage, message ports, file chooser callbacks, QR/scan result handlers, browser-to-native bridgesActivityResultLauncher and legacy onActivityResult()call(), applyBatch(), bulkInsert(), openTypedAssetFile(), FileProvider grantsOutput rules:
recon.json before Phase 3recon.json is inventory, not a filter resultGoal: write one evidence-backed coverage row for every targetId, centered on the traced source component, likely issue type, chain progress, and next follow-up targets.
Required row fields:
targetIdtargetTypeentryPointentryPermissionsourceComponentpossibleIssueTypesanalysisDepthstatusreasonnextActionneedsCrossComponentTraceevidenceRefsanalyzedAttackChainsnextCandidateTargetsFirst-pass rules:
rejected only if blocking evidence is explicit:
candidate if:
PendingIntent, URI grants, results, Binder handles, or WebView/browser handoffstatically-supported only if the full static chain is already completeCoverage rules:
coverage.jsoncoverage.json.targets must follow one stable schemacoverage.json must exhaustively cover recon.json.targetInventoryOverview mapping:
| Target type | Overview file | Common entrypoints |
|---|---|---|
| Activity | references/app-activity.md | onCreate, onNewIntent, result callbacks |
| Service | references/app-service.md | onBind, onStartCommand, handleMessage |
| Provider | references/app-provider.md | query, insert, update, delete, openFile, call, applyBatch, bulkInsert |
| Receiver | references/app-broadcast.md | onReceive |
| Intent flow | references/app-intent.md | forwarding, parcel, grant, result-return paths |
| WebView host | references/app-webview.md | host init, URL loaders, bridge registration, result handlers |
Subagents:
Coverage steward contract:
recon.json.targetInventory, coverage.json.targetstargetId appears exactly oncesourceComponent, possibleIssueTypes, status, reason, analysisDepth, nextAction, and evidenceRefsrejected row names the blocking conditioncandidate row names the missing proofinventorySummary.fullyAccountedFor = true only if all checks passtraceSummary and inventorySummaryTracing command:
decx code method-context "<currentMethod>" -P <port>
Use method-source only when you need the full body; prefer method-context to see callers and callees in one call.
Method labels:
SOURCESINKSAFEPASS_THROUGHDEAD_ENDCommon sources:
getIntent().get*Extra()getIntent().getData()ClipDataMessenger.handleMessage() dataCommon sinks:
startActivity(), startService(), sendBroadcast()PendingIntent.send()Runtime.exec(), ProcessBuildersetResult()WebView.loadUrl(), loadDataWithBaseURL(), evaluateJavascript()CookieManager.setCookie()execSQL()Common hard guards:
checkSignatures, enforceCallingPermission, checkCallingPermissionTrace only tainted-data-relevant calls. Skip logging, pure UI, and obvious dead ends.
Minimum finding fields:
vulnTyperiskstatusentryPointsourcesinkcallChaintraceSummaryreachablecontrollableguardsCheckedbypassConditionsimpactEvidenceratingRationaleGoal: fully trace every non-rejected target that still lacks a complete chain.
Mandatory deep-trace conditions:
PendingIntent, URI grants, results, or scan flows cross trust boundariescandidateRules:
nextMethodschaincoverage.json after each deep tracerejected target is either:
statically-supportedcandidate with explicit missing proofrejected with explicit blocking evidencePersistence:
coverage.json before and during deep tracingfindings.json incrementallyrecon.json, coverage.json, findings.json, and resume.json firstThis phase is exploitability triage based on the traced chain, not exploitation proof.
Quick rejection checks:
| Condition | Check |
|---|---|
signature / signatureOrSystem permission | manifest protectionLevel |
| exact signature enforcement | checkSignatures, signature compare |
| hard package / UID allowlist | immutable trusted allowlist |
| root / system-only path | privileged-only API or environment |
| non-bypassable guard | integrity, cryptographic, or strict type guard |
Three-factor gate:
Decision rules:
statically-supportedrejectedcandidateResidual-risk rules:
candidatecoverage.json and the reportcandidate targetsGoal: generate the final Markdown report using only statically-supported findings, while still surfacing residual candidate targets in the coverage summary section.
Execution model:
Reporting steps:
assets/report-template.mdreferences/risk-rating.mdzh -> assets/report-template-zh.mden -> assets/report-template-en.mdboth -> Chinese first, then Englishdecx code method-source "<method>" -P <port>Mandatory report content:
Bypass Conditions / UncertaintiesVisible ImpactRating Rationalecandidate targetsReport rules:
Full Call Chain, start from the victim app's externally reachable component entrypoint or Binder-exposed method, not from attacker actionsFull Call Chain with AttackerApp.*, bindService, startActivity, sendBroadcast, ContentResolver.*, adb steps, or PoC driver actionsAttack Path -> Exploitation StepsVictimService.onBind(Intent):IBinder -> I*.Stub.method(...) -> guarded or vulnerable internal methodFull Call Chain node must be backed by fetched code evidence; if the exact bridge from entrypoint to sink is not proven, keep the target as candidate instead of inventing a stepAttack PathCode AnalysisAt 60% context usage, hand off immediately:
{
"handoff": true,
"phase": "<current phase>",
"component": "<current component or null during recon>",
"traceSummary": {
"sourceComponent": "<current victim entry component or Binder bridge>",
"possibleIssueTypes": ["<current likely issue types>"],
"analyzedAttackChains": ["<chains already traced>"],
"nextCandidateTargets": ["<next targets to analyze>"]
},
"port": 31234,
"done": "<completed work>",
"next": "<entry instruction for the next subagent>",
"context": "<minimum context needed to continue>"
}
If file-backed continuation is enabled, persist the same state to resume.json.
Phase context:
coverageDone, coveragePending, current source component, likely issue types, and proven rejection reasonsResume:
resume.jsontarget, artifactPath, sessionName, and portrecon.json, coverage.json, and findings.jsondecx process status -P <port>lastCompletedPhase and nextActiondecxcli-pocPass only the minimal finding packet plus the current trace focus.
poc-handoff.json from assets/poc-handoff-template.jsonNever pass:
statically-supportedreferences/app-activity.mdreferences/app-intent.mdreferences/app-broadcast.mdreferences/app-provider.mdreferences/app-service.mdreferences/app-webview.mdreferences/risk-rating.md