Thanks to visit codestin.com
Credit goes to github.com

Skip to content

fix(yara): replace prose-colliding webshell strings with family markers (fixes #487) - #488

Open
stefanoamorelli wants to merge 2 commits into
NVIDIA:mainfrom
stefanoamorelli:fix/yara-webshell-prose-fp-487
Open

fix(yara): replace prose-colliding webshell strings with family markers (fixes #487)#488
stefanoamorelli wants to merge 2 commits into
NVIDIA:mainfrom
stefanoamorelli:fix/yara-webshell-prose-fp-487

Conversation

@stefanoamorelli

@stefanoamorelli stefanoamorelli commented Sep 6, 2026

Copy link
Copy Markdown

Skills written in German that include the words "behindert" or "Behinderung" are flagged even if legit, with a CRITICAL php_webshell_known finding, because the rule matched the bare substring "behinder", and "WSO 2 Micro Integrator" hits the same way through "WSO ". I map the two families with Behinder's hardcoded AES key and with WSO's wsoEx(, WSO_VERSION and wsoSecParam respectively, and I added tests for both cases.

fixes #487

`php_webshell_known` matched the bare substrings "behinder" and "WSO "
under `any of them`, so ordinary prose produced a CRITICAL YR2 finding
at 0.9 confidence with a remediation telling the reader to remove a
webshell. The German words "behindert" and "Behinderung" contain the
first string, and the product name "WSO 2 Micro Integrator" contains
the second, as reported in NVIDIA#487.

Behinder is now identified by its hardcoded AES key, md5("rebeyond")
truncated to 16 characters, which its PHP, ASP and JSP shells share and
which signature-base [1] uses for the same purpose. The key is written
as a YARA hex string so the packaged rule file does not carry the
indicator in plaintext, in the spirit of the encoded malware rules. WSO is identified
by the helper names oRb introduced in 2.x: `wsoEx(`, `WSO_VERSION` and
`wsoSecParam`. I checked a WSO 2.5 source against the old and new rule:
the old one hit only the banner and the bare "WSO " string, the new one
hits the banner and all three helpers, so no known sample is lost.

I preferred narrowing the strings over a `fullword` modifier because a
document that names the Behinder family would still have scored
CRITICAL, and "WSO 2" would still have matched.

Fixes NVIDIA#487

[1]: https://github.com/Neo23x0/signature-base

Signed-off-by: Stefano Amorelli <[email protected]>
The benign cases are the two reproductions from NVIDIA#487 plus a document
that names the Behinder and WSO families without shipping them. The
malicious cases are a Behinder PHP shell, a Behinder JSP shell and a
WSO fragment carrying `WSO_VERSION` and `wsoEx(`. All six fail against
the previous rule: the prose cases fired and the samples were missed,
so the tests guard both directions. The samples are base64-encoded like
the existing reverse shell fixture so the indicators do not sit in the
repository in plaintext.

Signed-off-by: Stefano Amorelli <[email protected]>
@stefanoamorelli
stefanoamorelli force-pushed the fix/yara-webshell-prose-fp-487 branch from bdec400 to f465db4 Compare September 9, 2026 14:13
SanHsien added a commit to SanHsien/SkillSpector that referenced this pull request Sep 11, 2026
…VIDIA#524

Raise reviewed_pr_through to 527 and reviewed_issue_through to 524 in
tools/upstream_baseline.json (commit axis unchanged at 69dcdfb). Every
item gets a verdict in docs/DECISIONS.md: NVIDIA#493/NVIDIA#507/NVIDIA#508/NVIDIA#511 verified
via git merge-base --is-ancestor as already included through the
2.11.1/2.11.2 sync (including NVIDIA#521, which merged only into the still-
open NVIDIA#516 stack, not main); the remaining 27 items stay "wait for
upstream merge", none adopted now.

Two items get dedicated comparison notes per docs/DIVERGENCE.md's
static_runner.py and scripts/compare_scan_accuracy.py rows: NVIDIA#522 uses a
different env var name and different default/semantics than this
fork's SKILLSPECTOR_MAX_STATIC_SECONDS, so merging it cannot simply
delete the divergence row and needs a downstream env var migration
first; NVIDIA#490 extends this fork's own upstream PR NVIDIA#486 with a Python
3.14/POSIX edge case the fork's Windows environment does not hit, so
NVIDIA#486 is left untouched pending upstream's own resolution. NVIDIA#501-NVIDIA#505 and
NVIDIA#518 are also flagged as near-verbatim matches to this fork's existing
Windows test divergence rows, worth revisiting for row deletion once
merged.

Co-Authored-By: Claude Opus 5 <[email protected]>
Signed-off-by: SanHsien <[email protected]>

@rng1995 rng1995 left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[SkillSpector Review]

Changes requested at head f465db48b6bda9ccb9dab20a7301acb8a82c9413.

  • src/skillspector/yara_rules/webshells.yar:71: any of them makes every newly added WSO marker and the bare Behinder AES key independently produce a CRITICAL webshell finding. Benign source or documentation that mentions one helper/constant/key still false-positives, and the added tests do not exercise isolated markers. Require corroborating family evidence (for example, two WSO markers and the Behinder key plus a PHP/JSP server tag) and add isolated-marker negative tests. PR #489 implements the needed direction and supersedes this version.

Required CI is green, but the rule precision issue and BEHIND merge state block merge.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

False positive: php_webshell_known fires on the German word "behindert" and on "WSO " in prose

2 participants