Threat Overview
Google Threat Intelligence Group and Mandiant reported on September 25, 2026 that UNC6240, associated with ShinyHunters, resumed mass exploitation of CVE-2026-35273 against Oracle PeopleSoft. The actor bypassed literal-path WAF rules by encoding the leading P in /PSEMHUB/ as /%50SEMHUB/, then abused Java deserialization in the Environment Management Hub servlet for unauthenticated remote code execution. Observed outcomes include fileless command execution, JSP/JSPX web shells, a trojanized signed installer delivering the SIDEEYE backdoor, Neo-reGeorg tunneling, MeshCentral persistence, credential access, lateral movement, and data-theft extortion. Oracle confirms that PeopleTools 8.61 and 8.62 are affected and that exploitation does not require authentication.
References
- Google Threat Intelligence Group / Mandiant, September 25, 2026: https://cloud.google.com/blog/topics/threat-intelligence/shinyhunters-renewed-mass-exploitation-campaign-targeting-oracle-peoplesoft/
- Oracle Security Alert for CVE-2026-35273: https://www.oracle.com/security-alerts/alert-cve-2026-35273.html
- The Hacker News, September 26, 2026: https://thehackernews.com/2026/09/attackers-bypass-wafs-to-exploit-oracle.html
Impacted Systems
- Vendor/product: Oracle PeopleSoft Enterprise PeopleTools 8.61 and 8.62; PeopleSoft Enterprise Applications using affected PeopleTools may also be exposed.
- Platform: PeopleSoft Internet Architecture hosted on Oracle WebLogic on Windows or Linux.
- Component: Environment Management Hub (
PSEMHUB) servlet/application. - Deployment: On-premises or self-managed PeopleSoft environments; Internet-reachable PIA/EMHub endpoints are highest risk.
- Prerequisite: No authentication is required. Exploitation uses crafted serialized Java objects sent to the PSEMHUB hub servlet.
- Exposure:
/PSEMHUB/or encoded/non-normalized variants reachable through a WAF, reverse proxy, load balancer, or directly. - Fixed state: Apply Oracle’s out-of-band Security Alert patch and mitigation guidance. Earlier unsupported releases were not tested and Oracle says they are likely affected.
- Useful unaffected distinction: Standard PIA user sessions do not require public exposure of EMHub or the Integration Broker listening connector.
Why this matters
The campaign moved from targeted zero-day use to renewed multi-sector mass exploitation and demonstrated that common literal-string WAF blocks can be bypassed. PeopleSoft often holds payroll, HR, student, financial, and identity data, making successful exploitation a direct route to high-impact data theft and extortion.
Exploitation Status
- Vendor-confirmed vulnerability: Oracle confirms unauthenticated RCE in PeopleTools 8.61 and 8.62 and recommends immediate mitigation.
- Researcher-confirmed exploitation: Mandiant/GTIG observed renewed mass exploitation by UNC6240, with web shells on dozens of systems across higher education, technology, IT services, healthcare, agriculture, transportation, and government.
- Observed behavior: bursts of
POSTrequests to/%50SEMHUB/hub, fileless shells spawned by Java,x.jsp,u.jsp,u2.jsp,tunnel.jsp,tunnel.jspx,Ple64.exe, SIDEEYE traffic to162.219.30.165on TCP 3333/3334, and MeshAgent infrastructure.
What this hunt looks for
The queries cover available Microsoft Sentinel telemetry for encoded PSEMHUB requests, known web-shell paths and hashes, Java-spawned shells, post-exploitation tooling, known network indicators, new outbound destinations, staging/archive behavior, and fallback raw logs.
Required logs
Conclusions are limited to data sources and retention available in Microsoft Sentinel. Relevant visibility requires WAF/reverse-proxy or WebLogic access logs, Defender for Endpoint or comparable endpoint telemetry, Syslog/SecurityEvent collection, and network-device or flow logs. Fileless execution will not appear in file-only searches. Absence of matching activity does not confirm absence of exploitation on unmonitored nodes or in non-ingested logs.
1. First Pass – PSEMHUB Exploitation and Encoded WAF-Bypass Requests
union isfuzzy=true
(
AzureDiagnostics
| where TimeGenerated >= ago(30d)
| extend Request=tostring(coalesce(column_ifexists("originalRequestUriWithArgs_s", ""), column_ifexists("requestUri_s", ""), column_ifexists("requestUri_d", ""), column_ifexists("Message", "")))
| project TimeGenerated, SourceIP=tostring(column_ifexists("clientIp_s", "")), Host=tostring(column_ifexists("host_s", "")), Request, Action=tostring(column_ifexists("action_s", "")), SourceTable="AzureDiagnostics"
),
(
CommonSecurityLog
| where TimeGenerated >= ago(30d)
| extend Request=strcat(tostring(RequestMethod), " ", tostring(RequestURL), " ", tostring(Message))
| project TimeGenerated, SourceIP, Host=DestinationHostName, Request, Action=DeviceAction, SourceTable="CommonSecurityLog"
),
(
Syslog
| where TimeGenerated >= ago(30d)
| project TimeGenerated, SourceIP="", Host=Computer, Request=SyslogMessage, Action="", SourceTable="Syslog"
)
| where Request matches regex @"(?i)/(?:%[0-9a-f]{2}|p)semhub/(?:hub|[^ ?]+\.(?:jsp|jspx))"
| project TimeGenerated, SourceTable, SourceIP, Host, Request, Action
| order by TimeGenerated desc2. Burst POST Requests to PSEMHUB Hub Servlet
union isfuzzy=true
(
AzureDiagnostics
| where TimeGenerated >= ago(30d)
| extend SourceIP=tostring(column_ifexists("clientIp_s", "")), Method=tostring(column_ifexists("httpMethod_s", "")), URI=tostring(coalesce(column_ifexists("originalRequestUriWithArgs_s", ""), column_ifexists("requestUri_s", ""))), Host=tostring(column_ifexists("host_s", ""))
),
(
CommonSecurityLog
| where TimeGenerated >= ago(30d)
| extend SourceIP=tostring(SourceIP), Method=tostring(RequestMethod), URI=tostring(RequestURL), Host=tostring(DestinationHostName)
)
| where Method =~ "POST"
| where URI matches regex @"(?i)/(?:%[0-9a-f]{2}|p)semhub/hub"
| summarize Requests=count(), FirstSeen=min(TimeGenerated), LastSeen=max(TimeGenerated), URIs=make_set(URI, 20) by SourceIP, Host, bin(TimeGenerated, 5m)
| where Requests >= 3
| order by Requests desc3. Java or WebLogic Spawning Command Shells
DeviceProcessEvents
| where TimeGenerated >= ago(30d)
| where InitiatingProcessFileName in~ ("java.exe", "java", "javaw.exe")
| where FileName in~ ("cmd.exe", "powershell.exe", "pwsh.exe", "sh", "bash", "dash", "ksh")
| project TimeGenerated, DeviceName, AccountName, FileName, ProcessCommandLine, InitiatingProcessFileName, InitiatingProcessCommandLine, InitiatingProcessFolderPath, SHA256
| order by TimeGenerated desc4. PeopleSoft Web-Shell and Backdoor File Artifacts
let KnownHashes = dynamic(["48b4a0827da7bbfce9fb52464f8a659dea7a035189c52c506c0bfb4b1c3fe494","2bee941fb40519d0d1ec52bd79a8f63fc65aac6455c8f2d6b668e3360dfdb5d7","419c571ee38b7e7266d130c4b6bbc4dd0ef44d6e5f3bc02cc2cf73b762f07c86","ba14419beb2ec0bb94cab6298c14d7fb3e1d819366fe378290c0c2a4d97f7e07","3ba215692665513abfffd4e815c5c45f2d41e5dcc4283a2a3b740930c5c417c3"]);
DeviceFileEvents
| where TimeGenerated >= ago(30d)
| where FolderPath contains "PSEMHUB.war" or FolderPath contains "PORTAL.war" or SHA256 in~ (KnownHashes)
| where FileName in~ ("x.jsp", "u.jsp", "u2.jsp", "tunnel.jsp", "tunnel.jspx", "Ple64.exe") or FileName endswith ".jsp" or FileName endswith ".jspx" or SHA256 in~ (KnownHashes)
| project TimeGenerated, DeviceName, ActionType, FolderPath, FileName, SHA256, InitiatingProcessAccountName, InitiatingProcessFileName, InitiatingProcessCommandLine
| order by TimeGenerated desc5. Known Campaign Network Indicators
let KnownIPs = dynamic(["5.199.162.157","104.219.234.138","162.219.30.165"]);
let KnownDomains = dynamic(["winmanage-me.network","azurenetfiles.net","microsoft-entra.net","enroll.azuredevice.cloud"]);
union isfuzzy=true
(
DeviceNetworkEvents
| where TimeGenerated >= ago(30d)
| where RemoteIP in (KnownIPs) or RemoteUrl has_any (KnownDomains)
| project TimeGenerated, DeviceName, RemoteIP, RemoteUrl, RemotePort, InitiatingProcessAccountName, InitiatingProcessFileName, InitiatingProcessCommandLine, SourceTable="DeviceNetworkEvents"
),
(
CommonSecurityLog
| where TimeGenerated >= ago(30d)
| where DestinationIP in (KnownIPs) or DestinationHostName has_any (KnownDomains) or RequestURL has_any (KnownDomains)
| project TimeGenerated, DeviceName=SourceHostName, RemoteIP=DestinationIP, RemoteUrl=coalesce(DestinationHostName, RequestURL), RemotePort=DestinationPort, InitiatingProcessAccountName=SourceUserName, InitiatingProcessFileName="", InitiatingProcessCommandLine="", SourceTable="CommonSecurityLog"
)
| order by TimeGenerated desc6. SIDEEYE Control and Data Ports
union isfuzzy=true
(
DeviceNetworkEvents
| where TimeGenerated >= ago(30d)
| where RemotePort in (3333, 3334)
| project TimeGenerated, DeviceName, LocalIP, RemoteIP, RemotePort, InitiatingProcessFileName, InitiatingProcessCommandLine, SourceTable="DeviceNetworkEvents"
),
(
CommonSecurityLog
| where TimeGenerated >= ago(30d)
| where DestinationPort in (3333, 3334)
| project TimeGenerated, DeviceName=SourceHostName, LocalIP=SourceIP, RemoteIP=DestinationIP, RemotePort=DestinationPort, InitiatingProcessFileName="", InitiatingProcessCommandLine="", SourceTable="CommonSecurityLog"
)
| order by TimeGenerated desc7. MeshAgent and Neo-reGeorg Follow-On Activity
union isfuzzy=true
(
DeviceProcessEvents
| where TimeGenerated >= ago(30d)
| where FileName has_any ("meshagent", "meshctrl") or ProcessCommandLine has_any ("meshagent", "meshcentral", "Neo-reGeorg", "tunnel.jsp", "tunnel.jspx")
| project TimeGenerated, DeviceName, EvidenceType="Process", AccountName, FileName, FolderPath, ProcessCommandLine, SHA256
),
(
DeviceFileEvents
| where TimeGenerated >= ago(30d)
| where FileName has_any ("meshagent", "meshagent.msh", "meshagent.db", "tunnel.jsp", "tunnel.jspx")
| project TimeGenerated, DeviceName, EvidenceType="File", AccountName=InitiatingProcessAccountName, FileName, FolderPath, ProcessCommandLine=InitiatingProcessCommandLine, SHA256
)
| order by TimeGenerated desc8. Archive Creation and Transfer Utilities on PeopleSoft/WebLogic Hosts
DeviceProcessEvents
| where TimeGenerated >= ago(30d)
| where InitiatingProcessFileName in~ ("java.exe", "java", "cmd.exe", "sh", "bash") or InitiatingProcessCommandLine has_any ("PeopleSoft", "WebLogic", "PSEMHUB")
| where FileName in~ ("tar", "tar.exe", "zstd", "zstd.exe", "rsync", "rsync.exe", "sshpass", "sshpass.exe", "curl", "curl.exe") or ProcessCommandLine has_any (".tar.gz", ".zst", "rsync", "sshpass", "/dev/tcp")
| project TimeGenerated, DeviceName, AccountName, FileName, ProcessCommandLine, InitiatingProcessFileName, InitiatingProcessCommandLine
| order by TimeGenerated desc9. Rare Outbound Destinations From Known PeopleSoft Hosts
let PeopleSoftDevices = dynamic(["REPLACE_WITH_PEOPLESOFT_HOST"]);
let BaselineStart = ago(30d);
let RecentStart = ago(7d);
let Baseline = DeviceNetworkEvents
| where TimeGenerated between (BaselineStart .. RecentStart)
| where DeviceName in~ (PeopleSoftDevices)
| where isnotempty(RemoteIP)
| summarize by DeviceName, RemoteIP, RemotePort;
DeviceNetworkEvents
| where TimeGenerated >= RecentStart
| where DeviceName in~ (PeopleSoftDevices)
| where isnotempty(RemoteIP)
| join kind=leftanti Baseline on DeviceName, RemoteIP, RemotePort
| summarize FirstSeen=min(TimeGenerated), LastSeen=max(TimeGenerated), Connections=count(), URLs=make_set(RemoteUrl, 20), Processes=make_set(InitiatingProcessFileName, 20) by DeviceName, RemoteIP, RemotePort
| order by Connections descDetection Notes
- Queries 1 and 2 are the highest-signal network hunts. Defenders must normalize URL paths; matching only literal
/PSEMHUB/misses the documented bypass. - Query 3 detects both fileless and web-shell execution when endpoint process telemetry exists.
- Hash-only detection is insufficient because minor JSP changes alter hashes; path, parent-process, and behavior searches are more durable.
- Query 9 requires confirmed PeopleSoft hostnames to replace the placeholder.
- Load-balanced deployments require review of every WebLogic node. Repeated exploit requests may intentionally reach multiple backend nodes.
AzureDiagnosticsfield availability varies by WAF connector and resource type. Adjust the URI, method, host, and client-IP columns to the deployed schema.- Expected noise includes legitimate EMHub administration, approved JSP deployment, authorized MeshCentral use, and routine Java child processes; validate against change records and server roles.