SAP NetWeaver AS Java — Security Assessment & Hardening
1. Architecture primer — what you are actually testing
1.1 Two generations, and why port tables disagree online
| 6.40 / 7.0x ("NW04", "NW2004s") | 7.1x – 7.5x | |
|---|---|---|
| Owns the listening sockets | Java dispatcher (jlaunch/jdisp) owns HTTP, P4, IIOP, Telnet | ICM (icman) terminates HTTP/HTTPS/P4/IIOP/Telnet, forwards over MPI to Java server nodes |
| Startup framework | jcontrol / jlaunch | jstart |
| Deployment | SDM (5NN17/18/19) + Visual Administrator (over P4) | SL Controller (same ports), JSPM/SUM. Visual Administrator removed in 7.2 |
| Configuration tool | Visual Admin / Config Tool / global-web.xml | NWA (/nwa) + Config Tool; profile icm/server_port_<xx> |
NN = instance number (SAPSYSTEM, 00–99). Java-only instance directories are J<NN> / JC<NN>; central services are a separate instance (SCS<NN>, installer default 01).
For dual-stack, SAP states: "HTTP communication is handled by ICM, which forwards requests to Java EE engine. Therefore the HTTP port is used only for internal communication, and the HTTPS port is not used at all." — the Java node's own 5NN00 is internal; the ICM's port is what's externally reachable.
1.2 Practical consequence for the assessment
Everything you check has two possible locations depending on release. Where they differ, this document gives both. Never assume a 7.0x system behaves like a 7.5 one — the 7.0x/7.1x population is where the unpatched, TLS-incapable, invoker-servlet-enabled systems actually live.
Hard finding for any 7.0x/7.1x system still in production: SAP JVM 4 (NW 7.0x) and SAP JVM 5 (NW 7.1x) do not support TLS 1.1/1.2 at all (KBA 2417205). Outbound connections from those systems cannot be made modern-TLS compliant without a release upgrade.
2. Phase 1 — Discovery and inventory
2.1 The port map
Every AS Java port is a formula of the instance number. Derive, don't brute-force.
Dispatcher / ICM element ports — 50000 + 100×NN + index
| idx | Service | Formula | NN=00 | Internet-facing? |
|---|---|---|---|---|
| 0 | HTTP | 5NN00 | 50000 | Only behind Web Dispatcher. Never raw. |
| 1 | HTTP over SSL | 5NN01 | 50001 | Same; preferred over 5NN00 |
| 2 | IIOP Initial Context | 5NN02 | 50002 | No — internal only |
| 3 | IIOP over SSL | 5NN03 | 50003 | No |
| 4 | P4 | 5NN04 | 50004 | No — admin network only |
| 5 | P4 over HTTP tunnelling | 5NN05 | 50005 | No — ≤7.0 only |
| 6 | P4 over SSL (P4SEC) | 5NN06 | 50006 | No |
| 7 | IIOP | 5NN07 | 50007 | No |
| 8 | Telnet admin console | 5NN08 | 50008 | Absolutely not |
| 10 | JMS | 5NN10 | 50010 | No — ≤7.0 only |
Documentation conflict you must know about. The 7.4/7.5 versions of SAP's "AS Java Ports" help page publish a different index table (Telnet at index 7, IIOP at 6) and drop the resolved port-number table entirely. Taken literally that yields Telnet = 5NN07. This contradicts the
icm/server_port_<xx>parameter documentation for the same releases. Trust the parameter defaults and the live system, not the index table. Verify per system withsapcontrol -nr NN -function GetAccessPointListor SAP MC → Access Points.
Shipped icm/server_port_<xx> defaults (7.1+), verbatim from SAP
system/type = J2EE (Java only)
icm/server_port_0 = PROT=HTTP,PORT=5$(SAPSYSTEM)00,TIMEOUT=60,PROCTIMEOUT=600
icm/server_port_1 = PROT=P4,PORT=5$(SAPSYSTEM)04
icm/server_port_2 = PROT=IIOP,PORT=5$(SAPSYSTEM)07
icm/server_port_3 = PROT=TELNET,PORT=5$(SAPSYSTEM)08,HOST=localhost
system/type = DS (dual stack) — same four, plus:
icm/server_port_4 = PROT=SMTP,PORT=0,TIMEOUT=120,PROCTIMEOUT=120
Three audit-relevant facts in that block:
HOST=localhoston Telnet is the shipped default in 7.1+. If a scan finds 5NN08 answering from the network, someone deliberately removed it — that is a finding, and KBA 2445893 ("How to access NetWeaver AS Java via Telnet from any host") documents exactly how it's done.- HTTPS / P4SEC / IIOPSEC are NOT configured at installation. No
PROT=HTTPSline ships. A default AS Java carries all admin protocols in cleartext. - These defaults are not visible in the profile. To change one you must explicitly re-declare the parameter. A profile with no
icm/server_port_*lines is running all four defaults.
Valid PROT= values: HTTP, HTTPS, SMTP, P4, P4SEC, IIOP, IIOPSEC, TELNET (ROUTER for Web Dispatcher end-to-end SSL only). Per-port hardening sub-options: HOST= (bind one interface), ACLFILE= (per-port IP ACL), VCLIENT=0|1|2 (client cert; 2 = mandatory), SSLCONFIG=, EXTBIND=1, and PORT=0 to close a protocol entirely.
Ports created dynamically via the ICM monitor / Web Admin are lost on restart. A clean scan can still differ from the running config. Check both.
Java server-node ports (internal, per server process n = 0..15)
| Service | Formula | Notes |
|---|---|---|
| Server join port | 5NN20 + n×5 | internal cluster |
| Server debug port | 5NN21 + n×5 | must never be reachable — debug access is code execution |
| DSR infrastructure | 5NN22 + n×5 | documented from 7.4/7.5 |
SAP marks all of these not external and fixed (unsupported to change).
Administrative services
| Service | Formula | Default | Internet-facing? |
|---|---|---|---|
| sapstartsrv HTTP (SAPControl SOAP) | 5NN13 | 50013 | No — admin net only |
| sapstartsrv HTTPS | 5NN14 | 50014 | No |
| NWDI DTR | 5NN15 | 50015 | No |
| Enqueue replication (NW2007+) | 5NN16 | 50016 | No |
| SDM (7.0x) / SL Controller (7.1+) | 5NN17 / 5NN18 / 5NN19 | 50017–19 | No — fixed, unsupported to change |
| ICM admin internal port | first free from 65000 downwards | 65000 | localhost-only by design |
Central Services instance (SCS, default instance 01)
| Service | Formula | Default | Parameter |
|---|---|---|---|
| Enqueue server | 32NN (sapdpNN) | 3201 | enque/encni/port |
| Gateway (7.1+ Java SCS) | 33NN (sapgwNN) | 3301 | — |
| Gateway, SNC-secured | 48NN (sapgwNNs) | 4800 | marked external by SAP (encrypted only); still restrict |
| Message server, external | 36NN (sapms<SID>) | 3601 | rdisp/msserv |
| Message server, internal | 39NN | — | rdisp/msserv_internal — firewall harder than 36NN |
| Message server HTTP | 81NN | 8101 | ms/server_port_<xx> — leaks instance/host list |
| Message server HTTPS | 444NN | not active | ms/server_port_<xx> |
Two inconsistencies in SAP's own tables, unresolved: 33NN is documented both as Java enqueue replication (≤7.0) and as the Java SCS gateway (7.1+); and the "relevant only prior to NW 7.0" caveat on 36NN/81NN/444NN appears on the ABAP rows but not the Java Central Services rows. Verify against the SCS profile.
Host-level and add-on
| Component | Ports |
|---|---|
| SAPHostControl (Host Agent) | 1128 HTTP / 1129 HTTPS — fixed |
| SAProuter / niping | 3299 / 3298 |
| SAP Web Dispatcher | no installer-assigned default; typically 80/443, but SWPM-era installs use instance-style ports. Read icm/server_port_<xx> from the WD profile. [UNCONFIRMED — no authoritative SAP-published default found] |
| PI/XI standalone adapters | 8200 (config UI), 8210 JMS, 8220 JDBC, 8230 File |
| IGS | multiplexer 4NN00, portwatchers 4NN01–4NN79, HTTP 4NN80–4NN99, plus fixed 40080 |
| TREX | name server 3NN01, HTTP 3NN05, RFC 3NN07, alert 3NN11 |
| MDM | 20003–20007 fixed, plus 2000–2002, 8351–8366, 31596/31597, 31601–31604 |
| Content/cache server | 1090, 1095 |
| Upgrade tooling | 4238–4241; SAPinst/SWPM 21212, 21213 |
Classic collision: IBM DB2/DB6 defaults to 50000, the same as AS Java instance 00.
Scan target list
# per AS Java instance NN
5NN00,5NN01,5NN02,5NN03,5NN04,5NN05,5NN06,5NN07,5NN08,5NN10,
5NN13,5NN14,5NN15,5NN16,5NN17,5NN18,5NN19,5NN20,5NN21,5NN22
# central services / ABAP-side / host-level
32NN,33NN,36NN,39NN,48NN,80NN,81NN,443NN,444NN,4NN00,1128,1129,3298,3299
nmap -sV --version-all -p <list> <target> — -sV is what makes the fingerprints in §2.2 fire.
2.2 Fingerprinting from the network
HTTP Server: header signatures (from nmap's production nmap-service-probes)
| Header | Identifies |
|---|---|
server: SAP NetWeaver Application Server <ver> / ICM <ver> | ICM-fronted NetWeaver — NW release and ICM version in one request |
Server: SAP J2EE Engine/<ver> | AS Java (pre-ICM style) |
server: SAP NetWeaver Application Server / ABAP <ver> | dual-stack or ABAP |
Server: SAP Host Agent + 301 → /sapmc/sapmc.html?SID=<SID>&NR=<NN>&HOST=<host> | Host Agent on 1128/1129 — leaks SID, instance number and hostname with zero auth |
server: SAP Message Server, release <N> | message server HTTP (81NN) |
Server: SAP Internet Graphics Server | IGS |
Server: Cloud Connector | SAP Cloud Connector |
WWW-Authenticate: Basic realm="sapbc" | SAP Business Connector |
Body / error-page signatures
- Web Dispatcher:
HTTP/1.0 400 Bad Requestwith<title>Application Server Error</title>,pragma: no-cache,connection: close. - ICM: error bodies carry
class="note">…code:<n>— Metasploit's ICM scanner greps exactly this to confirm an ICM when theServer:header is suppressed. - AS Java logon:
<title>Logon Error Message</title>on a 404 withcontent-type: text/html; charset=utf-8and noserver:header.
Non-HTTP banners
- Telnet 5NN08:
\xff\xfb\x01\xff\xfb\x03\xff\xfd\x1fthen an ANSI-blue banner of*— nmap matches this asSAP J2EE engine telnetd. Seeing this from off-host means theHOST=localhostdefault was removed. - SAP Logviewer:
READY#Logviewer#<version>\r\n— version pre-auth. - SAProuter (3299):
NI_RTERRblocks containingSAProuter <ver> (SP<nn>) on '<hostname>'and the router's local time — version, patch level, hostname, unauthenticated. - SAP dispatcher (32NN):
\0\0\0\x0e**DPTMMSG**\0\0\xf8.
The /sap/public/info question
/sap/public/info is ABAP-only (an ICF service). AS Java has no single equivalent. Metasploit's sap_icf_public_info returns nothing on a Java-only stack. The Java analogues are all application endpoints:
| Endpoint | Discloses |
|---|---|
/sap/monitoring/SystemInfo, /monitoring/SystemInfo | release, SP, cluster/instance layout, component list |
/sap/monitoring/ComponentInfo | per-SC version + SP + patch |
/utl/UsageTypesInfo | installed usage types (EP, PI, DI, …) |
/rep/build_info.jsp | SLD release + SP (ERPScan DSECRG-11-023) |
/bcb/bcbadmSystemInfo.jsp | Business Communication Broker release + SP (DSECRG-11-027) |
/AdapterFramework/version/version.jsp | PI Adapter Framework version |
/rwb/version.html | PI Runtime Workbench version |
/sap/admin/public/index.html | ICM Monitor, Active Services, Release Information, MPI status — no logon, if ALLOWPUB=TRUE |
/index.html, /startPage | default start page — presence identifies AS Java |
/apidocs/... | shipped Javadoc → engine version, and documents the deploy API |
On dual-stack, /sap/public/icf_info/urlprefix dumps PREFIX= lines for every registered URL prefix — it hands over the custom URL inventory.
2.3 Determining version, SP and patch level
Remotely
Server:header — NW release + ICM version.- Host Agent 1128 — the 301 redirect discloses SID, instance number, hostname.
- SAPControl SOAP on 5NN13 — under the
SDEFAULTkernel default,GetProcessList,GetInstancePropertiesandGetSystemInstanceListneed no authentication.GetSystemInstanceListhands over the whole landscape and therefore the exact port map. - Message server HTTP 81NN —
server: SAP Message Server, release <N>. (Commonly-cited paths/msgserver/text/logonand/msgserver/html/groupare [UNCONFIRMED] against SAP docs — verify on your release.) - The application endpoints in §2.2.
- SAProuter 3299 and Logviewer banners.
Locally (the authoritative view)
sapcontrol -nr <NN> -function GetVersionInfo # kernel/binary versions & patch levels
sapcontrol -nr <NN> -function GetAccessPointList # EVERY listening port, protocol, bound host
sapcontrol -nr <NN> -function GetProcessList
sapcontrol -nr <NN> -function GetSystemInstanceList
sapcontrol -nr <NN> -function GetEnvironment
sapcontrol -nr <NN> -function ListConfigFiles
sapcontrol -nr <NN> -function ParameterValue # dumps all profile parameters
sapcontrol -nr <NN> -function ParameterValue service/protectedwebmethods
GetAccessPointList is the single best command for a port audit — it is ground truth for §2.1.
Java component SP/patch levels — pick what the environment allows:
| Method | How |
|---|---|
| NWA (primary) | /nwa → Configuration → Infrastructure → System Information → Components Info. Deep link …/nwa/sysinfo works on most releases. |
| AS Java start page | http(s)://<host>:5NN00/ → System Information. Often reachable unauthenticated on unhardened systems — itself a finding. |
| Telnet admin shell | telnet <host> 5NN08 (from localhost), then version; lsc to list cluster elements. |
| Config Tool (offline) | Help → Software Components. Works when the server won't start. |
| Config Tool batch | configtool/batchconfig.bat -task get.versions.of.deployed.units — scriptable, good for fleet collection. |
| Database (offline) | select SCNAME, SAPRELEASE, SERVICELEVEL, PATCHLEVEL from <schema>.BC_COMPVERS where COMPONENTTYPE='SC' — fastest fleet-wide inventory. KBA 1752501, 1771843. |
Components whose versions matter: SERVERCORE · J2EE-FRMW · CORE-TOOLS · ENGINEAPI · J2EE-APPS · LMCTC (LM Configuration Wizard / CTC) · LM-TOOLS · LM-CORE · LM-SERVICE (Diagnostics Agent) · VCFRAMEWORK (Visual Composer) · EP-RUNTIME / EPBC · SAP_XIAF / SAP_XITOOL / SAP_XIESR / SAP_XIPCK · WSRM · ADSSAP · SAP_JTECHS (7.0x-era umbrella) · plus KERNEL / KRNL64UC / KRNL64NUC for kernel-side issues.
Do not use
/sap/public/infoas your Java patch oracle. It is ABAP-only, and it is itself an information-disclosure surface SAP recommends restricting.
2.4 Deployed-application inventory
This is the item most assessments skip and the one that matters most, given >1,200 shipped applications on 7.2.
/usr/sap/<SID>/<INST>/j2ee/cluster/apps/— filesystem view- NWA → Operations → Systems → Start & Stop → Java Applications — running state and start-up mode
- Application aliases — KBA 2586026 ("How to check and amend Application Aliases on AS Java"). Alias changes take effect immediately, no restart. The same KBA carries SAP's explicit warning that there is no user-based authorization on the alias feature.
- Telnet console (from localhost):
MAN -glists all shell command groups; theDEPLOYgroup's list/status commands give the application inventory. Capture theMAN/MAN -goutput itself as an audit artefact — command spellings vary across 7.0x/7.1x/7.3+/7.5, and the transcript is immune to that drift.
Deliverable: alias → application → start-up state, one row per entry, with a justification column. Everything unjustified is a finding.
3. Phase 2 — External / black-box attack surface
3.1 Verb tampering — check this first, it is cross-cutting
CVE-2010-0738. AS Java honours HEAD (and historically PUT) and processes them as GET. If a web.xml <security-constraint> declares <http-method>GET</http-method>, then HEAD bypasses the constraint entirely. ERPScan found ~40 vulnerable shipped applications on 6.40 alone.
Remote check: for every path that returns 401, retry with HEAD. A 401-for-GET / 200-for-HEAD differential is the finding. Metasploit's sap_icm_urlscan automates exactly this and reports "Got authentication bypass via HTTP verb tampering". It is entirely read-only and high-yield — script it across your whole path inventory.
Config-state check (the real audit): grep every deployed web.xml for <http-method>. The correct state is no <http-method> elements at all inside <security-constraint> — which makes the constraint apply to all methods. Also confirm <transport-guarantee>CONFIDENTIAL</transport-guarantee> and that <error-page> entries exist so stack traces aren't returned.
Fixes: SAP Note 1503579 (the /dir case) plus general web.xml remediation. ERPScan published a free WEB.XML check tool for this.
3.2 The Invoker Servlet — /<application>/servlet/<class-name>
The single highest-value item on AS Java.
- What: a J2EE convenience feature letting a servlet be invoked by class name even with no
<servlet-mapping>inweb.xml. Intended for debugging. - Why it matters:
web.xmlsecurity constraints protect the mapped URL, not/servlet/*. So/app/servlet/com.sap.admin.Critical.Actionreaches a protected servlet unauthenticated. CVE-2010-5326, CVSS 10.0, in CISA KEV since 2021-11-03. NVD records exploitation "in the wild in 2013 through 2016, aka a Detour attack"; US-CERT TA16-132A documented it at 36 organisations. - This is not answerable from a patch level. Check:
- Global: property
EnableInvokerServletGloballymust befalseon theservlet_jspservice (Web Container), materialised inglobal-web.xml.- 7.0x: Visual Administrator → Server → Services →
servlet_jsp(KBA 2649730 for locating it) - 7.1x–7.5x: NWA → Configuration → Infrastructure → Java System Properties → Services tab → Extended Details; or Config Tool offline; or Telnet
- 7.0x: Visual Administrator → Server → Services →
- Per-application: an individual app can re-enable the invoker locally even when the global switch is false. Auditing global-only is the classic incomplete finding. Grep deployed descriptors for
InvokerServletLocallyEnabled/InvokerServletEnabledand for a/servlet/*servlet-mapping. - Positive confirmation: the engine emits
com.sap.ASJ.web.000767— "The servlet invoker will not invoke servlets requested by class name…" — intodefaultTracewhen it is off. Its presence is evidence of correct configuration, not a fault. - Fleet-wide proof: EarlyWatch Alert reports invoker servlet status (KBA 2425081), and Solution Manager Configuration Validation can check the parameter across every Java system. Use one of those as the evidence artefact rather than per-system screenshots.
- On dual-stack, confirm the Java stack is even running — a stopped Java stack is not an exposure.
- Global: property
- Notes: 1445998 (disable globally, plus per-application exception procedure; marked release-independent), 1467771 (NetWeaver Portal specifically — affects 6.40 SP23+, 7.00–7.02, CE 7.10–7.20, 7.30 SP02+). FAQ: KBA 2326767.
- [UNCONFIRMED — sources disagree] Which release first shipped
falseas the default. One line of sources says AS Java 7.20 and later; independent secondary sources (and the upgrade symptom "Servlet with class cannot be loaded") point at 7.30. Note 1445998 itself only creates the property for 7.00 and lower. Assume "default = enabled" for anything at or below 7.31 and verify per system rather than trusting release notes. 7.0x/7.01/7.02/7.11 are the high-risk population either way.
3.3 Endpoint catalogue — what to probe and what "bad" looks like
All probes below are read-only. Expect 401/403/404; a 200 is the finding.
| Path | What it is | Why it matters |
|---|---|---|
/CTCWebService/CTCWebServiceBean (+?wsdl) | LM Configuration Wizard SOAP endpoint | CVE-2020-6287 "RECON", CVSS 10.0. Unauthenticated caller creates a Java user and assigns it Administrator. Retrievable WSDL = exposed. Notes 2934135 / 2939665 / 2948106. |
/ctc, /ctc/servlet/com.sap.ctc.util.ConfigServlet | CTC helper servlet, reachable via the invoker | Historic unauthenticated OS command execution as <sid>adm (CVE-2012-2611, DSECRG). Should be undeployed/disabled in production. |
/developmentserver/metadatauploader | Visual Composer Metadata Uploader | CVE-2025-31324, CVSS 10.0, KEV, ransomware-linked. Unauthenticated file upload → JSP webshell → OS command execution. Highest-priority check on any system with VCFRAMEWORK. |
/irj, /irj/portal | Enterprise Portal runtime | Intended to be exposed, but the #1 Shodan fingerprint for internet-facing AS Java. Fronts the entire PRT servlet surface. |
/irj/go/km/navigation?Uri=/ | KM navigation | Anonymous directory listing of KM/filesystem, can leak LDAP users, e-mail addresses, folder structure. Target of nmap NSE http-sap-netweaver-leak. SAP reported this as a configuration issue and "won't fix" — it is purely your hardening item. Same family: /irj/go/km/docs/. |
/webdynpro/dispatcher/..., /webdynpro/resources/... | Web Dynpro Java runtime | WD apps use programmatic (UME) auth, so protection is per application. ERPSCAN-16-010/16-016: anonymously opening a WD URI yielded SAP user names, logins and privileges. |
/webdynpro/dispatcher/sap.com/tc~wd~tools/WebDynproConsole, .../explorer, /webdynpro/welcome/Welcome.jsp | WD developer tools | Should be undeployed in production. |
/nwa, /useradmin, /spml/spmlservice | NWA, UME user admin UI, SPML provisioning web service | The administrative control plane. /spml/spmlservice is a machine interface to full user management. Must not be internet-reachable. Test from an unprivileged session and from a user/DMZ subnet, not just unauthenticated. |
/sap/monitoring/SystemInfo, /ComponentInfo | version/component disclosure | Behaviour is SP-dependent — do not assume it's authenticated, verify. |
/sap/admin/public/index.html | ICM admin without logon when ALLOWPUB=TRUE | Monitor, Active Services, Core Thread Status, Host Name Buffer, Release Information, MPI Status. |
/sap/admin | ICM Web Administration | Default user webadm with the installation master password. |
/dir/support/CheckService, /dir/support/ExportabilityCheck | PI Integration Directory support servlets | The classic verb-tampering targets: a HEAD request executes them without authorization → arbitrary file overwrite (DoS by overwriting the SAP profile) and, on Windows, UNC-driven SMB relay / NTLM capture. ERPScan DSECRG-11-026 (CVSSv2 9.0). Fix: Note 1503579. |
/dir, /rep, /rwb, /mdt, /pimon, /AdapterFramework, /MessagingSystem, /XISOAPAdapter/MessageServlet, /exchangeProfile | PI/PO surfaces | See §6.2. Only PI systems, only internally. |
/wsnavigator/jsps/test.jsp | Web Services Navigator | Shipped test client that invokes any exposed web service. Long-standing public dork. Service discovery + an outbound-request (SSRF-flavoured) primitive + open redirect via redirect.jsp. Undeploy in production. Caveat: patching can re-add it (KBA 2602277) — re-verify after every SP stack. |
/ejbexplorer | EJB Explorer — browse and invoke deployed EJB methods | SAP now ships it disabled: KBA 2957221 (EJB Explorer is disabled/missing in NW 7.5 SP18, startup mode DISABLED in application-j2ee-engine.xml). On older stacks, disable explicitly. (One research pass could not confirm /ejbexplorer in Metasploit's wordlist; the SAP KBA confirms the application exists and its shipped state.) |
/logon/logonServlet?redirectURL=, /logon/index.jsp | UME logon servlet | Classic open-redirect / phishing vector. Also the brute-force target — and AS Java transmits logon credentials in cleartext on 5NN00. |
/AnalyticalReporting/AnalyticalReporting_merge_web.xml | — | Serves a web.xml over HTTP — directly discloses security constraints. |
/mmr/MMR?filename=<UNC> | — | UNC-fetch primitive → SMB relay / NTLM capture on Windows. |
/bcb/bcbadmSystemInfo.jsp and siblings | Business Communication Broker | Release + SP disclosure (DSECRG-11-027). Undeploy unless used. |
/SQLtrace/index.html, /OpenSQLMonitors/ | DB trace/monitor UIs | Query and data exposure. |
/SLDStart/plain, /SLDStart/secure | System Landscape Directory | Landscape inventory. |
/AdobeDocumentServices/Config (+?wsdl), /ADS-EJB, /ADS-License | Adobe Document Services | See §6.4. (/AdobeDocumentServices/Config is [UNCONFIRMED] as an SAP-documented path but is a well-known reachability probe target.) |
/IciEventService/IciEventConf?wsdl and the /Ici*Service/*Conf?wsdl family | CRM ICI services | Historic public dork. |
/GRMGHeartBeat, /GRMGWSTest/service, /CAFDataService/Config?wsdl, /CMSRTS/Config?wsdl, /DataArchivingService, /ApplicationAdminProvider | shipped SOAP endpoints | Enumerate ?wsdl on each. |
/apidocs/ | shipped Javadoc | Documents Deploymanager, DeploymanagerFactory, LoginInfo, IConnection — i.e. it explains the deploy API. Undeploy. |
/@download@, /KW, /SAPIKS, /SAPIKS2/jsp/adminShow.jsp, /VC/default.jsp, /Modeler, /Lighthammer, /TestJDBC_Web | assorted shipped apps | The general rule: undeploy what you don't use. |
/ProfileService — [UNCONFIRMED]. Could not be corroborated as a standard AS Java endpoint in any authoritative source, nor does it appear in Metasploit's 1,633-entry sap_icm_paths.txt. The nearest real endpoints are /exchangeProfile/ (PI) and the SAPControl SOAP profile-reading methods on 5NN13. Replace it in your checklist.
3.4 The read-only probe set
GET /CTCWebService/CTCWebServiceBean?wsdl # expect 401/403/404, NOT 200 + WSDL
GET /ctc/ConfigServlet # expect 401/403/404
HEAD /ctc/ConfigServlet # must NOT differ from GET
GET /developmentserver/metadatauploader # VC uploader reachability
GET /sap/public/icf_info/urlprefix # dual-stack: enumerate exposed URL prefixes
GET /irj/go/km/navigation?Uri=/ # KM anonymous listing (SAP: won't fix)
GET /sap/admin/public/index.html # ALLOWPUB check
GET /sap/monitoring/ComponentInfo # patch-level disclosure
GET /wsnavigator/jsps/test.jsp
GET /nwa /useradmin /spml/spmlservice
Run the whole set from each network zone — internet, DMZ, user LAN, admin LAN — and record the status code matrix. That matrix is your segmentation evidence, and it satisfies PCI DSS Req. 11.3 segmentation validation as a by-product.
Build the full path list from Metasploit's sap_icm_paths.txt + the target's own /sap/public/icf_info/urlprefix + your §2.4 application inventory.
3.5 Cleartext credential exposure — the thing that makes port exposure severe
This is worth its own finding rather than being folded into "service exposed":
- Telnet (5NN08) transmits credentials in cleartext.
- HTTP (5NN00) transmits logon credentials in cleartext.
- P4 (5NN04) "encrypts" the password with a reversible scheme that was publicly broken (Chastuhin, CONFidence 2014).
So 5NN04 and 5NN08 reachability is credential exposure, not merely service exposure. Remediation is P4SEC/IIOPSEC/HTTPS plus network segmentation — noting that SSL is not configured by default on any of them.
ERPScan/Onapsis stated the internal-side rule plainly at Black Hat US-11: "Deny access to open ports from users subnet (except 5NN00). Only Administrators must have access."
4. Phase 3 — Patch and vulnerability verification
4.1 How SAP delivers Java security fixes (and why "is the note applied?" is the wrong question)
- Cadence: SAP Security Patch Day is the second Tuesday of each month. Notes split into Patch Day (apply out-of-cycle) and Support Package (roll into the next SP). SAP breaks cadence for emergencies — CVE-2025-31324's Note 3594142 shipped 24 April 2025, outside patch day.
- There is no ABAP-style transport/SNOTE correction for Java. A Java security fix arrives as one of three things:
- a patched SCA at a specific SP + patch level, deployed via SUM (or JSPM on older releases);
- a kernel/executable patch (ICM, Web Dispatcher, jstart, sapstartsrv, Host Agent) as a kernel SAR;
- a configuration change only — e.g.
EnableInvokerServletGlobally=false, or Note 3593336 Option 0 removing themetadatauploaderapplication.
- Consequence: on Java, "is it patched?" is answered by component SP/patch-level comparison, not a note-status table. And category (3) is invisible to patch-level checks — it must be audited separately as configuration drift.
- No RSECNOTE for Java — correct, and
RSECNOTEis deprecated anyway. The replacements that do cover Java:- System Recommendations (SysRec) — nominally covers "ABAP and non-ABAP notes", but Java verdicts are derived from LMDB/SLD component versions rather than any in-system implementation status. Materially lower precision than for ABAP.
- EarlyWatch Alert — reports Java component patch levels and Invoker Servlet status. (But see §8.3: EWA has no security chapter for Java.)
- Configuration Validation / CSA — the practical way to prove configuration-only fixes fleet-wide.
- Maintenance-window caveat — the most common dead end. SAP's policy (from 11 June 2019) is that High/Very High severity fixes are provided for Support Packages released within the last 24 months. Systems on older SPs get no patch and must take an SP stack or a workaround. Expect this on 7.31 and older.
4.2 Triage order
- CVE-2025-31324 + CVE-2025-42999 — is
VCFRAMEWORKpresent? Is/developmentserver/metadatauploaderreachable? Assume compromise and hunt (§4.6), don't just patch. - CVE-2025-42944 — is P4 (5NN04 / 5NN06) reachable from anything untrusted? CVSS 10.0, unauthenticated.
- CVE-2020-6287 RECON —
LMCTCpatch level, plus alias-deactivation state. - CVE-2022-22536 ICMAD — kernel patch level on every AS Java and every Web Dispatcher and Content Server.
- CVE-2010-5326 Invoker Servlet — global and per-application.
- CVE-2026-40128 — AS Java Web Container, unauthenticated path traversal via a logon request, CVSS 9.0 (SAP), June 2026. Newest unauthenticated AS Java issue — though note
AC:H(see §4.5.1), so it is not trivially exploitable. - The 2023–2026 P4/JNDI deserialization cluster (§4.5).
4.3 CISA KEV — the complete SAP list
Authoritative as of catalog 2026.09.09 (1,699 entries). 14 are SAP; bold = AS Java relevant. No SAP entry has been added to KEV since 15 May 2025 — worth stating so nobody chases phantom 2026 items.
Phrase this carefully in a report. That is a statement about the catalogue, not about threat activity. Absence from KEV is not absence of exploitation: CVE-2025-42957 (S/4HANA ABAP code injection) was widely reported as exploited in the wild in August 2025 and is not in KEV. Use KEV as a floor for prioritisation, never as a ceiling.
| CVE | Product | Added | Ransomware |
|---|---|---|---|
| CVE-2018-2380 | CRM (ABAP) | 2021-11-03 | Known |
| CVE-2010-5326 | NetWeaver — Invoker Servlet | 2021-11-03 | Unknown |
| CVE-2016-9563 | NetWeaver — XXE | 2021-11-03 | Unknown |
| CVE-2020-6287 | NetWeaver — RECON | 2021-11-03 | Unknown |
| CVE-2020-6207 | Solution Manager | 2021-11-03 | Unknown |
| CVE-2016-3976 | NetWeaver — traversal | 2021-11-03 | Unknown |
| CVE-2021-38163 | NetWeaver — Visual Composer 7.0 RT upload | 2022-06-09 | Unknown |
| CVE-2016-2386 | NetWeaver — UDDI SQLi | 2022-06-09 | Unknown |
| CVE-2016-2388 | NetWeaver — UWL info disclosure | 2022-06-09 | Unknown |
| CVE-2022-22536 | Multiple — ICMAD | 2022-08-18 | Unknown |
| CVE-2019-0344 | Commerce Cloud | 2024-09-30 | Unknown |
| CVE-2017-12637 | NetWeaver — scheduler traversal | 2025-03-19 | Unknown |
| CVE-2025-31324 | NetWeaver — VC file upload | 2025-04-29 | Known |
| CVE-2025-42999 | NetWeaver — VC deserialization | 2025-05-15 | Known |
10 of 14 are AS Java or Java-inclusive.
4.4 Actively exploited campaigns
Visual Composer, 2025 → ongoing. The most serious AS Java event on record. Unauthenticated file upload at /developmentserver/metadatauploader (GET/POST/HEAD observed), JSP webshell into the Portal servlet tree, then OS command execution as the Java process owner. Onapsis observed reconnaissance from January 2025, months before the note. CSA Singapore's advisory documents 16 malicious IPv4s, 3 payload-hosting domains, webshells helper.jsp / ran.jsp / shell.jsp, plus reverse shells and SSH proxy tooling. CVE-2025-31324 alone is not a complete fix — CVE-2025-42999 is the root-cause deserialization flaw in the same uploader; both notes are required, plus 3660659 (JVM serialFilter).
Invoker Servlet, 2013–2016. US-CERT TA16-132A: exploitation at 36 organisations across oil & gas, telecom, utilities, retail, automotive, in multiple countries, via a flaw patched in 2010.
Solution Manager CVE-2020-6207. Public PoC January 2021; Tenable recorded probing immediately after. EPSS ~0.98 — near-certain exploitation attempts if reachable.
RECON CVE-2020-6287. Weaponised PoCs public since 2020; CISA issued dedicated advisory AA20-195A.
4.5 Vulnerability catalogue by class
Corrections to widely-repeated misattributions — worth knowing before you write a report:
- CVE-2020-6286 is AS Java LM Configuration Wizard path traversal (the RECON sibling, same Note 2934135), not Solution Manager. CVE-2020-6207 is Solution Manager.
- CVE-2018-2380 is SAP CRM (ABAP), Note 2547431 — in KEV and ransomware-flagged, but not an AS Java issue.
- CVE-2016-3976 is directory traversal (
CrashFileDownloadServlet). CVE-2016-9563 is XXE, authenticated, CVSS 6.5 — not traversal. Neither is P4. The real P4 CVEs are CVE-2017-5372, CVE-2016-9562, CVE-2020-6263, CVE-2025-42944.- CVE-2021-21481 is the MigrationService missing authorization check (Note 3022422), not a JMX/MMC issue. [UNCONFIRMED] whether a JMX/MMC-specific CVE exists under another ID.
- CVE-2019-0330 is SAP Diagnostics Agent / LM-Service OS command injection (Note 2808158) — adjacent, not AS Java core.
- CVE-2021-33690 is NWDI Component Build Service SSRF (Note 3072955). The PI Messaging System issue is CVE-2022-41271; PI User Defined Search is CVE-2022-41272.
4.5.1 Unauthenticated RCE / configuration abuse
CVE-2025-31324 — Visual Composer Metadata Uploader CVSS 10.0 (SAP) / 9.8 (NVD), CWE-434, published 24 Apr 2025. Component VCFRAMEWORK — optional, but Onapsis estimates it on 50–70 % of AS Java systems. Affected: all 7.1x+ releases, all SPS. Notes: 3594142 (patch) · 3593336 (workarounds — Option 0 = remove the metadataupload application; Options 1–2 were deprecated "Do Not Use" on 12 May 2025) · 3596125 (FAQ + compromise assessment) · 3660659 (JVM serialFilter). Am I affected? NWA → System Information → Components Info → search VISUAL COMPOSER FRAMEWORK / VCFRAMEWORK.SCA. Absent ⇒ not applicable. Patched? VCFRAMEWORK patch level ≥ that named in 3594142 for your SP, and 3604119 applied, and serialFilter per 3660659. If the workaround was taken instead, a patch-level check will read as unpatched — record which control is in force per system.
CVE-2025-42999 — Visual Composer deserialization CVSS 9.1, CWE-502. Note 3604119. KEV 15 May 2025, ransomware-linked. Note the vector: this one is PR:H — it is not unauthenticated on its own. It is the root-cause deserialization defect in the same uploader, which is why chaining it with 31324 yields unauthenticated RCE. Don't let the pairing imply 42999 is independently unauthenticated.
CVE-2020-6287 "RECON" — LM Configuration Wizard / CTC CVSS 10.0, CWE-306. AS Java 7.30, 7.31, 7.40, 7.50 — per SAP's FAQ, all SPs of all Java stacks on those releases, plus dual-stack; OS- and DB-independent. Unauthenticated attacker executes CTC configuration tasks including creating an administrative user. Notes 2934135 (patch), 2948106 (FAQ), 2939665 (workaround: deactivate the application alias). CISA advisory AA20-195A. LMCTC can often be patched independently of a full SP stack — check the dependency matrix in 2948106. Sibling CVE-2020-6286 (CVSS 5.3, CWE-22): unauthenticated path traversal in the same web service allowing zip download. Same Note 2934135.
CVE-2026-40128 — AS Java Web Container path traversal / file inclusion CVSS 9.0 (SAP as CNA; NVD status is still Awaiting Analysis, so there is no NVD primary score yet), published 9 June 2026, Note 3727078. Unauthenticated. A crafted HTTP logon request manipulates file-inclusion parameters → path traversal → the included file is processed. View/modify sensitive information, or DoS. Found by Onapsis Research Labs. Read the vector before you set the priority: AV:N/AC:H/PR:N/UI:N/S:C/C:H/I:H/A:H — SAP rated attack complexity High. It is the newest unauthenticated AS Java issue and belongs in the top tier, but it is not the trivially-scriptable class that RECON and the VC uploader are.
CVE-2025-42922 — AS Java arbitrary file upload CVSS 9.9, 9 Sep 2025, Note 3643865. Authenticated non-administrative user uploads an arbitrary file → full compromise. Component not narrowed in public sources beyond "AS Java" — [UNCONFIRMED], retrieve the note.
CVE-2021-38163 — Visual Composer 7.0 RT unrestricted upload (KEV) SAP CVSS 9.9 / NVD 8.8. AS Java 7.30–7.50, Note 3084487. Authenticated non-admin → OS commands as the Java process. A different component (VC70RUNTIME) from the 2025 VCFRAMEWORK issues — a system can be exposed to both.
CVE-2020-26829 — P2P cluster communication missing auth CVSS 10.0, AS Java 7.11–7.50, Note 2974774. Arbitrary processes from outside the cluster may connect. Frequently missed because the protocol is assumed network-isolated — verify the isolation actually exists.
CVE-2020-26821 / 26822 / 26823 / 26824 — SolMan Java stack, four × CVSS 10.0 All AS Java 7.20 under SolMan, all Note 2985866. SVG Converter Service, Outside Discovery Configuration Service, Upgrade Diagnostics Agent Connection Service, Upgrade Legacy Ports Service. Unauthenticated, missing authorization. One note fixes all four.
CVE-2020-6364 — CA Introscope Enterprise Manager (SolMan / Focused Run) CVSS 10.0, Note 2969828. Cookie manipulation → OS command execution → host takeover. WILY_INTRO_ENTERPRISE 9.7 / 10.1 / 10.5 / 10.7. Easy to miss: it is a bundled third-party product, not an SCA visible in NWA.
CVE-2016-2386 — UDDI SQL injection (KEV) — CVSS 9.8, J2EE Engine 7.40, Note 2101079. CVE-2020-6309 — CVSS 7.5, Note 2941315; ENGINEAPI 7.10, WSRM 7.10–7.50, J2EE-FRMW 7.10/7.11. The concrete case where ENGINEAPI patch level is the audit target. CVE-2020-26820 — CVSS 7.2, Note 2979062. NWA admin console → filesystem exposure + malicious upload; PR:H but the outcome is unauthenticated filesystem access. CVE-2021-37535 — CVSS 9.8, JMS Connector Service missing authorization, AS Java 7.11–7.50. [UNCONFIRMED note number] — NVD's record lacks it; retrieve from SAP.
4.5.2 P4 / RMI / JNDI / IIOP naming-service class — the under-appreciated cluster
The pattern: the P4/RMI naming service exposes objects whose methods can be invoked without authorization, or deserializes untrusted Java objects.
| CVE | CVSS | Component / Note | Detail |
|---|---|---|---|
| CVE-2025-42944 | 10.0 | SERVERCORE 7.50 SP020–SP035 · Notes 3634501, 3660659, 3670067; FAQ 3637718, guide 3663688 | Unauthenticated deserialization via RMI-P4 → arbitrary OS command execution. Fix implements a Java ObjectInputFilter BlocklistFilter in MarshalInputStream. Requires Java 8u121+ before patching. FAQ scope also names PI/PO, ESR, IBD, EP, BPM. |
| CVE-2023-23857 | 9.9 | AS Java 7.50 · Note 3252433 | Unauthenticated JNDI/naming-API access affecting users and services across systems. |
| CVE-2023-0017 | 9.4 | AS Java 7.50 · Note 3268093 | Unauthenticated improper access control, same open-naming-API pattern. |
| CVE-2020-6263 | 9.8 | SAP-JEECOR 7.00/7.01, SERVERCOR 7.10–7.50, CORE-TOOLS 7.00–7.50 · Note 2878568 | Standalone clients connecting via P4. |
| CVE-2023-30744 | 8.2 | SERVERCORE/J2EE-FRMW/CORE-TOOLS 7.50 · Note 3317453 | Unauthenticated object instantiation → unauthenticated method calls. |
| CVE-2022-41272 | 9.9 | PI User Defined Search 7.50 · Note 3273480 | Unauthenticated JNDI. |
| CVE-2022-41271 | 9.4 | PI Messaging System 7.50 · Note 3267780 | Unauthenticated JNDI. |
| CVE-2017-5372 | 7.5 | SERVERCORE P4 msp / MSPRuntimeInterface | Missing authorization on getInformation → info disclosure. |
| CVE-2016-9562 | 7.5 | AS Java 7.4 · Note 2313835 | sap.com~P4TunnelingApp!web/myServlet → null pointer → icman outage. |
| CVE-2025-42925 | 4.3 | AS Java IIOP · Note 3640477 | Object Identifiers not random → brute-forceable. Low score, but an enabler for the above. |
| CVE-2023-27268 / 24526 / 24527 / 26460 | 5.3 each | Object Analyzing Service 3288480 · Classload Service · Deploy Service 3287784 · Cache Management Service | Same unauthenticated-open-interface family, Mar–Apr 2023. Individually low, collectively a broad unauthenticated attack surface. |
| CVE-2025-42884 | 6.5 | Enterprise Portal · Note 3660969 | Unauthenticated JNDI environment-property / URL injection → unintended JNDI provider. |
Defender action for the whole cluster: the durable control is network isolation of P4 / P4SEC / IIOP, not patching alone. Establish (a) which instances expose these ports, (b) to which zones, (c) whether any DMZ/external path exists. Then patch SERVERCORE / CORE-TOOLS / J2EE-FRMW. Verification signal for CVE-2025-42944: confirm BlocklistFilter activation in the server logs, and regression-test legitimate P4 consumers — SUM and Solution Manager both use P4 and the filter can break them.
4.5.3 ICM / kernel / Web Dispatcher — "ICMAD"
CVE-2022-22536 — memory-pipe desynchronisation → HTTP request smuggling/concatenation. CVSS 10.0 (NVD) / 9.8 (SAP), CWE-444. Note 3123396; FAQ 3148968; workarounds 3137885, 3138881. Affects AS ABAP and AS Java, ABAP Platform, SAP Content Server 7.53, and SAP Web Dispatcher. Kernels 7.22, 7.49, 7.53, 7.77, 7.81, 7.85, 7.86, 7.87, 8.04; Web Dispatcher 7.22EXT, 7.49, 7.53, 7.77, 7.81, 7.85, 7.86, 7.87. Unauthenticated attacker prepends data to a victim's request → executes functions as the victim, steals the session, or poisons intermediary caches. In KEV.
CVE-2022-22532 — improper shared-memory buffer handling (use-after-free), CVSS 9.8, AS Java only, Note 3123427. Unauthenticated crafted HTTP request → impersonation / session theft. CVE-2022-22533 — improper error handling → memory-buffer exhaustion → system shutdown. Same kernels, same Note 3123427. [UNCONFIRMED] delivery vehicle — Tenable states it was not in the February 2022 patch day despite sharing the note.
How a defender verifies:
sapcontrol -nr <NN> -function GetVersionInfoon every AS Java instance and every Web Dispatcher and Content Server. The Web Dispatcher is the most commonly forgotten and it is the internet-facing one.- Compare kernel release + patch level to the minimum in Note 3123396 / 3123427.
- Onapsis published an open-source ICMAD scanner (
github.com/Onapsis/onapsis_icmad_scanner) that works against ABAP and Java, over HTTP/HTTPS, and behind a Web Dispatcher. Onapsis explicitly warns it is best-effort — false positives and negatives are possible, untested behind non-SAP proxies. Corroboration only, never sole evidence. - If a kernel patch isn't possible yet, the workaround notes apply — record which is in force.
Other ICM/kernel items: CVE-2016-3979 (ICM heap corruption, AS Java 7.2–7.4) · CVE-2016-3980 (jstart DoS, Note 2259547) · CVE-2016-4015 (Enqueue Server DoS, Note 2258784) · CVE-2017-14581 (Host Control web service DoS, AS Java 7.0–7.5, Note 2389181) · CVE-2020-6304 (ICM input validation, 7.5) · CVE-2022-29614 (sapstartsrv, ABAP + Java + HANA) · CVE-2024-33005 (6.3 — admin users of Web Dispatcher / AS ABAP+Java / Content Server can impersonate other users, Note 3438085).
4.5.4 Directory traversal / arbitrary file read & write
| CVE | CVSS | Component | Note | Detail |
|---|---|---|---|---|
| CVE-2017-12637 | 7.5 | AS Java 7.5 scheduler UI (scheduler/ui/js/…/UIUtilJavaScriptJS) | 2486657; KEV points at 3476549 | Unauthenticated arbitrary file read via ... Exploited in the wild August 2017; added to KEV 19 Mar 2025 — an eight-year-old bug newly weaponised. |
| CVE-2016-3976 | 7.5 | AS Java 7.1–7.5, CrashFileDownloadServlet | 2234971 | Unauthenticated arbitrary file read. In KEV. Broadest release range of the set. |
| CVE-2026-40128 | 9.0 | AS Java Web Container | 3727078 | §4.5.1 |
| CVE-2025-42977 | 7.6 | Visual Composer | 3610591 | Traversal, PR:H, read or modify arbitrary files. |
| CVE-2020-6203 | 9.1 | UDDI Server (Services Registry) 7.10–7.50 | 2806198 | Insufficient path validation. |
| CVE-2025-42926 | 5.3 | AS Java | (Sept 2025 set) | No authentication check accessing internal files within the web application. |
Adjacent, commonly in the same audit scope: CVE-2018-2380 (CRM, KEV, ransomware, Note 2547431) · CVE-2023-27269 (9.6) / CVE-2023-27501 (8.7) traversal write/delete in AS ABAP · CVE-2020-26837 (9.1, SolMan UEM traversal + script upload, Note 2983204) · CVE-2025-27428 (7.7, SolMan traversal via an RFC-enabled FM reading files from any managed system, Note 3581811).
4.5.5 XXE and XML-processing
| CVE | CVSS | Component | Note |
|---|---|---|---|
| CVE-2016-3974 | 9.1 | Configuration Wizard, AS Java 7.1–7.5 — DoS, SMB relay, arbitrary file access | (ERPScan advisory; note not in NVD — [UNCONFIRMED]) |
| CVE-2016-4014 | 8.6 | UDDI uddi/api/replication, 7.4 — crafted DTD → hang | (Mar/Apr 2016 set) |
| CVE-2024-24743 | 8.6 | CAF – Guided Procedures 7.50 — unauthenticated crafted XML → sensitive file/data read | 3426111 |
| CVE-2017-8913 | 8.8 | Visual Composer VC70RUNTIME 7.50, authenticated | (not in NVD) |
| CVE-2017-11457 | 6.5 | KM com.sap.km.cm.ice 7.50 — file read + SSRF | (not in NVD) |
| CVE-2016-9563 | 6.5 | BC-BMT-BPM-DSK 7.50 | 2296909 · In KEV |
| CVE-2015-4091 | — | SLD tc~sld~wd~main/Main, 7.4 — TCP requests to intranet servers | (not in NVD) |
| CVE-2023-26461 | 6.8 | Enterprise Portal 7.50 XML parser | 3284550 |
| CVE-2021-27635 | 6.5 | AS Java 7.20–7.50, missing XML validation (admin) | 3053066 |
| CVE-2018-2492 | 7.1 | SAML 2.0 — insufficient XML document validation, 7.2–7.50 | 2642680 |
Also CVE-2025-42966 (9.1) — XML Data Archiving Service insecure Java deserialization, Note 3610892; and CVE-2015-8840 (8.8) — XML DAS missing authorization check.
4.5.6 Log4Shell — narrower than the panic suggested
- AS ABAP: not affected (Onapsis, unambiguous).
- AS Java core: essentially not affected. KBA 3129883 ("AS Java Core Components' impact for Log4j", BC-JAS-COR) covers CVE-2021-44228 / -45046 / -45105. Exposure requires Log4j 2.x below 2.17.0; AS Java core does not ship Log4j 2.x. Log4j 1.x is present in places and was never formally assessed — SAP recommends updating it anyway (unsupported since 2015).
- Affected in the SAP Java family: custom/partner applications on NetWeaver Java bundling their own Log4j 2.x; PI/PO Java Web Service Adapter (Note 3130521); SAP Commerce ≤ 1905; HANA XS Advanced runtime < 1.0.140 (Notes 3130698, 3134531); NetWeaver Developer Studio (CVE-2022-29615, log4j 1.x via Eclipse, Note 3202846); SAP IdM.
- Cross-product index: SAP Note 3131047.
- How to determine exposure on AS Java: Onapsis's method is to connect to the telnet admin shell and search for Log4j class files — "Such resource cannot be found" ⇒ not vulnerable. Supplement with a filesystem sweep for
log4j-core-*.jarunder/usr/sap/<SID>/and each deployed application'slib/, since the risk lives in deployed custom applications, not the platform SCAs. - Remediation and verification: remove the
JndiLookupclass from the jar rather than relying onformatMsgNoLookups(which was bypassed). The checkable artefact is the absence ofJndiLookup.class, not a patch level.
4.5.7 Other AS Java items worth a checklist line
| CVE | CVSS | Item | Note |
|---|---|---|---|
| CVE-2021-21481 | 8.8 NVD / 9.6 SAP | MigrationService missing authorization → access configuration objects including those granting administrative privileges, NW 7.10–7.50. NVD vector is AV:A (adjacent), SAP's is AV:N — the discrepancy matters for exposure scoring; SAP's is conservative | 3022422 |
| CVE-2025-42963 | 9.1 | AS Java Log Viewer unsafe deserialization → full OS compromise (authenticated admin) | 3621771 |
| CVE-2024-22127 | 9.1 | NWA Log Viewer plug-in file upload → command injection | 3433192 |
| CVE-2025-42953 | 8.1 | System Configuration missing authorization → privilege escalation | 3623440 |
| CVE-2024-27899 | 8.8 | User Admin self-registration: no requirements on new security-answer content | 3434839 |
| CVE-2024-34688 | 7.5 | Meta Model Repository unrestricted access → DoS | 3460407 |
| CVE-2024-54197 | 7.2 | NWA System Overview SSRF — enumerate internal HTTP endpoints | 3542543 |
| CVE-2021-33670 | 7.5 | HTTP Service Monitoring Filter crash, 7.10–7.50 | 3056652 |
| CVE-2021-33671 | 8.8 | Guided Procedures Administration Workset missing authorization | (not in NVD) |
| CVE-2018-2503 | 7.4 | Keystore service insufficiently restricts access to protected resources by default, ServerCore 7.11–7.50 | 2658279 |
| CVE-2020-26816 | 4.5 | Key Storage Service stores key material DER-encoded in the DB | 2971163 |
| CVE-2024-45283 | 6.0 | Username and password obtainable when creating an RFC destination | 3477359 |
| CVE-2024-47588 | 4.7 | SUM 1.1 writes credentials in plaintext to a log file on upgrade errors | 3522953 |
| CVE-2024-42372 | 6.5 | SLD missing authorization → read/modify global SLD config | 3335394 |
| CVE-2024-47592 | 5.3 | Login brute-forceable to enumerate valid user IDs | 3393899 |
| CVE-2020-6190 | 5.8 | Heap Dump Application leaks hostname, server node, installation path | 2838835 |
| CVE-2025-24869 | 4.3 | Endpoint discloses deployed server components including their XML definitions | 3550027 |
| CVE-2016-2388 | 5.3 | Universal Worklist Configuration discloses sensitive user info. In KEV | 2256846 |
| CVE-2018-2368 | 9.8 | SLD (LM-CORE 7.10–7.40) no authentication checks | (not in NVD) |
| CVE-2025-30012 | 10.0 | SRM Live Auction Cockpit — deprecated Java applet servlet, unauthenticated. Runs on NetWeaver Java | 3578900 |
| CVE-2026-58240 | 9.8 | Message Server — insufficient validation of internal component authenticity at registration; unauthenticated attacker registers a rogue component. Sept 2026 HotNews | 3759472 |
2026 items: CVE-2026-40128 (9.0, unauthenticated Web Container) · CVE-2026-27685 (9.1, EP Administration deserialization, Note 3714585) · CVE-2026-44752 (8.2, AS Java unauthenticated XSS, Note 3748227) · CVE-2026-58235 (6.3, ADS libraries) · CVE-2026-58240 (9.8, Message Server) · and from the 8 Sep 2026 patch day, CVE-2026-66768 (9.0 HotNews, Note 3781729) — SAP GUI for Java, trust-level policy not enforced for functions invoked from a connected backend → arbitrary command execution on the victim's workstation. Client-side, not AS Java server-side — it will appear in a "SAP Java" search; scope it correctly.
Possible incomplete-fix chains — [UNCONFIRMED], verify supersession: EP Administration (3621236 → 3714585) and SolMan RFC code injection (3668705 → 3685270) have identical CVE descriptions weeks apart.
4.6 Compromise assessment — do this regardless of patch state
Patching does not remediate an existing compromise. For CVE-2025-31324:
Hunt for .jsp / .java / .class files with recent mtimes under:
/usr/sap/<SID>/<inst>/j2ee/cluster/apps/sap.com/irj/servlet_jsp/irj/root/
/usr/sap/<SID>/<inst>/j2ee/cluster/apps/sap.com/irj/servlet_jsp/irj/work/ (irjwork, irjworksync)
Known names include helper.jsp, cache.jsp, coresap.jsp, forwardsap.jsp, webhelp.jsp, usage.jsp, 404_error.jsp, ran.jsp, shell.jsp — but observed samples frequently use random 8-character names (cglswdjp.jsp, ijoatvey.jsp). Hunt by extension + timestamp + parent directory, not by filename list.
For RECON: look for unexplained accounts in Administrators / SAP_J2EE_ADMIN created around the exposure window. Onapsis published a dedicated IOC scanner for retrospective detection.
Onapsis + Mandiant published a joint open-source assessment scanner (Onapsis/Onapsis_CVE-2025-31324_Scanner_Tools) doing both detection and compromise assessment — declared no longer actively maintained as of 2025-06-06, so extend the IoC list yourself.
5. Phase 4 — Authenticated configuration audit
5.1 Identity: default and technical accounts
The AS Java standard-user set depends on the UME data source chosen at install:
| Purpose | UME = AS ABAP | UME = LDAP | UME = Java DB |
|---|---|---|---|
| Administrator | chosen at install, e.g. J2EE_ADM_<SID>; add-in installs default to J2EE_ADMIN | Administrator | Administrator |
| Guest | e.g. J2EE_GST_<SID>; add-in default J2EE_GUEST | Guest (locked by default) | Guest (locked by default) |
| Technical/comm. | SAPJSF_<SID> | configured post-install | DB user, e.g. SAP<SID>DB |
Also created by a default install: ADSuser and caf_mp_scvuser.
Standard groups: Administrators (Java DB) or SAP_J2EE_ADMIN (ABAP data source) — "users that have unrestricted administrative privileges on the AS Java"; Guests / SAP_J2EE_GUEST; ADSCallers; and the built-in runtime-evaluated Everyone (a.k.a. all), Authenticated Users, Anonymous Users.
[UNCONFIRMED]
xAdministrators— could not be confirmed as a standard AS Java role or group name in SAP documentation. The documented names areAdministrators,SAP_J2EE_ADMIN, the J2EE security roleAdministrators, and the UME roleAdministrator. Don't publish it as an SAP-standard name without verifying against whatever tool told you.
Per-account checks
Administrator / J2EE_ADMIN / J2EE_ADM_<SID>
- SAP recommends do not delete the default administrator.
- Password changed from the install-time master password?
- If it has been locked in favour of a named admin, two follow-ups are commonly missed and are audit-worthy: secure store credentials updated (
SecStore.properties) and JMS service configuration properties updated. KBA 1901961. - Watch for this pattern: password changed → SDM/deploy and JMS break → someone changes it back. That quietly undoes the hardening.
Guest / J2EE_GUEST
- Must be locked (SAP states it is by default — verify, because it is often unlocked to make anonymous portal content work).
- Check whether it appears in
ume.login.guest_user.uniqueids. Everything in that list is reachable without authentication. - On ABAP-datasource systems, the guest logon ID must not also exist in ABAP or AS Java will not start.
SAPJSF / SAPJSF_<SID> — the UME↔ABAP RFC communication user. The highest-value single item in this section.
- User type must be
System. - Role:
SAP_BC_JSF_COMMUNICATION_RO(read-only) vsSAP_BC_JSF_COMMUNICATION(read-write: authorization to modify and delete all user-related data). If the Java system only authenticates and reads users,_ROis correct; the read-write role gives the Java system full ABAP user-administration power over the coupled client. UME auto-downgrades to read-only if it finds no roles or only_ROat startup. - Naming must be per-system (
SAPJSF_<SID>), not one sharedSAPJSFacross many Java stacks — otherwise one credential compromise reaches every stack. - Check the RFC destinations
UMEBackendConnectionandUMEBackendConnectionForChanges. The forChanges destination should use Current User (Assertion Ticket) — without it, all UME-driven user-master changes in ABAP are logged asSAPJSF. That is a significant audit-trail gap. - SNC recommended: check
ume.r3.connection.master.snc_myname. Without it the RFC carrying user data and password verification is unprotected. - Useful to know: this user cannot log on to the UME, so a locked
SAPJSFis almost always a password mismatch in the destination/secure store, not brute force. - Anything beyond the two shipped roles (
SAP_ALL,SAP_NEW, extraS_USER_*/S_RFCwildcards bolted on to "fix an error") is a finding.
SDM (7.0x/7.1x only)
- SAP: "change the default password as soon as possible after the installation." From WebAS 6.40 SP5 the installer offers to set it; patch-based upgrades do not — upgraded systems are the ones to check.
- The SDM server recognises exactly one user with no attribution: "It is not easy to trace which user performed a particular activity." Treat the SDM password as a shared root credential and ask how many people know it.
- SAP recommends not running the SDM server except during deployment. The client↔server connection is non-secure.
- Escalation path to check: any OS user who can reach the central-instance install directory can use the SDM CLI to change the SDM password.
ADSuser / ADS_AGENT — see §6.4.
PI/PO service users — see §6.2. Solution Manager users — see §6.3.
On the coupled ABAP data source (SAP*, DDIC, EARLYWATCH, SAPCPIC, TMSADM): SAP publishes the defaults itself as must-change items (SAP* = 06071992 or PASS; DDIC = 19920706; EARLYWATCH = support). Verify with RSUSR003. TMSADM has a documented default password; the fix is program TMS_UPDATE_PWD_OF_TMSADM per Note 1414256.
Why the ABAP data source matters to a Java audit: when UME uses AS ABAP, the ABAP client is your Java identity store. The Java password policy is largely bypassed (§5.2), ABAP roles surface as UME groups, and a compromise of
SAP*/DDICin that client is a compromise of AS Java administration. Note also SAP Note 718383: once you choose the ABAP data source you cannot change to another — relevant to remediation planning.
The emergency user SAP* on AS Java (distinct from ABAP SAP*)
- Properties
ume.superadmin.activatedandume.superadmin.password, set in the Config Tool (offline), then restart. - "The
SAP*user has full administrator authorizations"; "once activated, no other user can log in to the system"; no default password. - Review:
ume.superadmin.activatedmust befalsein steady state;ume.superadmin.passwordmust not be left populated after use; activation requires a restart, so correlate any restart + this property against change records. - This is the single cleanest privilege-escalation path from OS access to AS Java administrator, and it leaves almost no application-layer audit trail. Call it out explicitly. Anyone with Config Tool access (i.e.
<sid>admOS access) has it.
"Has the password been changed?" — UME has no RSUSR003
- ABAP data source →
RSUSR003/ EWA "Default Password of Standard Users" (KBA 1610103). - Java DB → Identity Management search on "Date of Last Password Change" — but note the documented limitation: it "only considers actions performed using the AS Java tools." A user created at install and never touched shows no change date.
- Use the UME Export function (§5.4) to snapshot users/groups/roles for offline diffing. Passwords are deliberately not exported.
5.2 UME configuration hardening
Where: 7.1x+ → NWA → Configuration → Security → Identity Management (/nwa/identity); UME security policy via the UME configuration UI (Modify Configuration → Security Policy). 7.0x and any offline change → Config Tool.
[UNCONFIRMED] A dedicated UME-configuration quick link (often cited as
/nwa/ume-config) is not in SAP's Configuration Work Center quick-link list. Confirmed quick links:/nwa/identity,/nwa/auth,/nwa/trusted-systems,/nwa/spnegoconfig,/nwa/key-storage,/nwa/ssl,/nwa/sys-config,/nwa/cfg-browser,/nwa/sessionmgt,/nwa/http,/nwa/destinations,/nwa/jco-destinations,/nwa/adobe,/nwa/virus-scan,/nwa/log-config.
Password / logon-ID policy — ume.logon.security_policy.*
SAP's defaults are weak by modern standards. That is the point of the check.
| Property | SAP default | Review note |
|---|---|---|
password_min_length | 1 | Baseline expects ≥ 8. Usually the single worst default. |
password_max_length | 14 | Must be ≥ the sum of the required-character settings. |
password_alpha_numeric_required | 1 | n = at least n letters and n digits. |
password_mix_case_required | 0 | n = at least n lower and n upper. |
password_special_char_required | 0 | |
password_expire_days | 90 | 0 = never. |
password_history | 0 | 0 = no history at all. Admin-set passwords are not entered into history. |
oldpass_in_newpass_allowed | FALSE | Keep FALSE. |
userid_in_password_allowed | FALSE | Keep FALSE. |
password_impermissible | – | Deny list with */? wildcards. Populate with company name, sap*, <SID>*, season/year patterns. |
enforce_policy_at_logon | FALSE | If FALSE, tightening the policy has no effect on existing passwords — they persist until voluntarily changed. Set TRUE with a rollout plan, or the policy change is cosmetic. |
password_max_idle_time | 0 (off) | If you enable it, also set password_successful_check_date_default to the current date or you mass-lock users (KBA 2827567). |
password_last_change_date_default | 12/31/9999 | The far-future default means "never expired" for never-changed passwords. |
password_change_allowed | TRUE | Leave TRUE unless a read-write LDAP manages passwords externally. |
Lockout:
| Property | Default | Review note |
|---|---|---|
lock_after_invalid_attempts | 6 | Automatically set to 0 (infinite) in a combined AS Java + AS ABAP installation — on dual-stack/add-in systems Java-side lockout is off by design and ABAP's login/fails_to_user_lock governs. Verify the ABAP side rather than assuming Java protects you. |
auto_unlock_time | 60 min | 0 = admin unlock only. Documented gotcha: auto-unlock does not reset the failed-attempt counter, so a user can re-lock on the next failure. |
Logon-ID shape: useridminlength 5, useridmaxlength 20 (auto-set to 12 in a combined install), userid_digits 0, userid_special_char_required 0. The negative-value semantics are the hardening lever — a negative value forbids, which reduces homoglyph/lookalike-account risk. Documented limitation: logon-ID length rules are only checked at creation and ignored thereafter.
Security-policy profiles: UME has Default and Technical User. Editing Default also changes Technical User — except password expiration, which never applies to Technical User. So service accounts are structurally exempt from expiry; compensate with documented rotation evidence rather than expecting policy enforcement.
Anonymous access, self-registration, logon help — ume.logon.*
| Property | Default | Review note |
|---|---|---|
ume.logon.selfreg | FALSE | Must remain FALSE on internal/production systems. |
ume.logon.logon_help | FALSE | TRUE adds self-service password reset — SAP's own doc: "the system e-mails their password in plain text." |
ume.logon.logon_help.securityquestion | FALSE | PREDEFINED = one of 5 canned questions. Canned questions are weak. |
ume.login.guest_user.uniqueids | guest | Comma-separated list of named anonymous users. Everything listed is authenticated-as-nobody and auto-joins Anonymous Users. Audit this list and every role each entry holds. |
ume.logon.allow_cert | FALSE | TRUE = users self-map client certificates from the logon screen. A self-service credential-enrolment path needing justification. |
ume.logon.force_password_change_on_sso | TRUE | FALSE means expired/reset passwords are never force-changed under ticket/SAML/X.509 — a stale-credential accumulator. |
Corresponding UME actions to look for on roles: Selfregister_User, Logon_Help.
The data source decision and what each implies
Java database — all ume.logon.security_policy.* settings are fully in force. Strongest policy control, weakest governance (no central visibility, no CUA, no SUIM).
AS ABAP — SAP: "If you use ABAP user management as a data source, the system ignores these values in most cases" and "to prevent a conflict… the UME ignores its own security policy to some extent." ⇒ Audit the ABAP login/* profile parameters, not the UME policy. This is the most common audit mistake on Portal and PI systems. Other consequences: read-write by default (degrades per SAPJSF's role); ABAP roles appear as read-only UME groups (maintained in PFCG, not NWA — reviewers routinely look in the wrong tool); new UME groups/roles are stored locally, giving a hybrid authorization store to review in both places; password change limited to once per day; password locks cannot be unlocked from the AS Java UI; ABAP role changes take up to 30 minutes to appear (relevant when validating that a revocation took effect).
LDAP — check the bind DN is least-privilege, the password is rotated, and above all that the connection is LDAPS/TLS (a plain simple bind sends the bind password in clear). If the directory enforces password policy, set password_history = 0 and consider password_change_allowed = FALSE so you don't run two half-enforced policies.
Determine the active data source: KBA 3263478, the UME configuration UI, or /nwa/cfg-browser. [UNCONFIRMED] the property spelling ume.persistence.data_source_configuration.
5.3 Authentication stack and trust
Where: NWA → Configuration → Security → Authentication and Single Sign-On (/nwa/auth), tabs Components / Authentication Stack.
Standard template stacks: SAP-J2EE-Engine (default, BasicPasswordLoginModule), Basic, Form, Client (ClientCertLoginModule), ticket (EvaluateTicketLoginModule SUFFICIENT → BasicPasswordLoginModule REQUISITE → CreateTicketLoginModule OPTIONAL), Evaluation assertion ticket.
JAAS flags — the crux of any stack review:
| Flag | Required to succeed | Behaviour |
|---|---|---|
OPTIONAL | No | continues regardless |
REQUIRED | Yes | continues regardless |
REQUISITE | Yes | on failure, control returns immediately |
SUFFICIENT | No | on success, control returns — remaining modules are skipped |
A SUFFICIENT module early in a stack is a complete authentication path on its own. Enumerate every stack and ask, for each SUFFICIENT module: what does an attacker need to satisfy just this one? A HeaderVariableLoginModule marked SUFFICIENT on a host reachable without a trusted reverse proxy is a full authentication bypass — the header is attacker-controlled.
Also review service.* policy configurations — service.telnet, service.iiop, service.naming.
Logon policies: "if you do not specify a logon policy, the system generates a default one that allows every user to log on." Enabled via ume.logon.apply_logon_policies.
Inheritance trap: "If you change the options of a login module in the user store, the changes are inherited by all policy configurations that use this login module." Conversely, changing options in a single policy configuration breaks inheritance permanently until the options are made identical again. A global hardening change may silently not reach previously-customised stacks — enumerate per stack.
Login modules to know: BasicPasswordLoginModule · EvaluateTicketLoginModule / CreateTicketLoginModule · ClientCertLoginModule + CertPersisterLoginModule (performs automatic certificate mapping on first user logon — a self-enrolment behaviour that binds whatever certificate arrives first; verify it's intended) · SAMLLoginModule / SAML2LoginModule · SPNegoLoginModule / Krb5LoginModule (obtains credentials from the Kerberos keytab — treat that file like a private key) · HeaderVariableLoginModule · the JCA mapping modules ConfiguredIdentityMappingLoginModule, CredentialsMappingLoginModule (both reference stored EIS credentials or an inline user/password — inventory these alongside /nwa/destinations), CallerImpersonationMappingLoginModule (passes caller credentials straight through).
SAP Logon Tickets (MYSAPSSO2) — the trust argument
Issuing. AS Java signs tickets with a key pair in the TicketKeystore view. A default key pair and certificate ship with the product.
- Has the shipped default SSO key pair been replaced with a customer-generated one? Key length, validity? Who holds
KeystoreAdministrator/KeystoreViewCreator? - Ticket options are UME properties:
login.ticket_lifetime(hours, default 8; baseline expects ≤ 8h),login.ticket_client,login.ticket_portalid. There is a documented 3-minute time tolerance. - Cookie protection:
ume.logon.httponlycookie(HttpOnly),ume.logon.security.enforce_secure_cookie(Secure; unencrypted connections then fail authentication),ume.logon.domain.remove_subdomains(controls how many domain levels are stripped — i.e. how widely the ticket is scoped). - Cookie scoping is an underrated finding. A
MYSAPSSO2scoped to*.corp.example.comis sent to every host in that domain, including hosts you don't control. Combined with SAP domain relaxation this is a documented lateral-movement vector.
Accepting. EvaluateTicketLoginModule verifies the issuer's digital signature against a certificate in the ticket-verification keystore view. Trust is managed in NWA → Configuration → Security → Trusted Systems (/nwa/trusted-systems). "The configuration changes made with the wizard have a global effect for ticket-based SSO to the AS Java."
Why this matters, stated for the report:
EvaluateTicketLoginModuleperforms no password verification. It verifies a signature. Any system in theTrusted Systemslist can mint a ticket asserting any user ID the AS Java UME can resolve — includingAdministrator. (The asserted principal still has to exist or be mappable; that is the only limit.) There is no per-user, per-application or per-role restriction in the trust relationship itself, which is precisely why SAP's guidance is to trust only systems of equal or higher security classification.- Therefore the security level of your AS Java is the level of the weakest system whose certificate is in its trust list. A sandbox portal, a decommissioned dev system, or an old ABAP system with
SAP*on the default password becomes an authentication bypass into production. - Signing-key theft equals permanent, undetectable impersonation until the key is rotated and the certificate removed from every accepting system.
- The trust is transitive in effect but not in configuration — nobody owns the graph. Nothing in NWA shows you "which systems accept tickets from me."
Review procedure:
- Export
Trusted Systemsfrom every AS Java; record SID, client, certificate subject/issuer, key length, validity dates, fingerprint. - Do the same on ABAP (
STRUSTSSO2/ tableUSRACLEXT). - Build the full issuer→accepter matrix and justify every edge. Flag: prod accepting from non-prod; expired or near-expiry certificates; entries for systems that no longer exist; weak keys or SHA-1; any trust added without a change record.
- For each accepting system, check whether
EvaluateTicketLoginModuleisSUFFICIENT(normal — and therefore a standalone auth path) and which applications' policy configurations include it. - Verify tickets travel only over TLS (
ume.logon.security.enforce_secure_cookieon Java,login/ticket_only_by_httpson ABAP). - There is no server-side ticket revocation.
login.ticket_lifetimeis your revocation window.
SAML 2.0: review which certificates are selected for signature and encryption; the Trusting an Identity Provider list (every trusted IdP can assert any identity to you); identity federation method; which applications actually require SAML; and whether Single Log-Out is configured — otherwise logout is local only.
X.509: which keystore view is the trust anchor (a broad CA trust list means any cert from any trusted CA can map to a user); whether CRL/revocation checking is enabled; the certificate-to-user mapping rules.
5.4 Authorization model
UME role ← the only assignable container; built from "actions"
├─ J2EE security roles (declared by developers in deployment descriptors)
│ · type J2EE (application level) ← SAP-recommended
│ · type J2EE-MODULE (module-scoped)
└─ UME actions (collections of permissions, deployed in actions.xml)
ACLs ← instance-level protection (portal PCD etc.), managed only in application context
Consequences for the review:
- UME roles are the only assignable container. "Who can do X" is answered by walking UME role → actions → permissions.
- SAP recommends building UME roles from actions of type
J2EE, notJ2EE-MODULE. A role stuffed with module-level actions is a smell. - Permissions are developer-defined and not creatable by administrators — you cannot fix an over-broad permission by configuration, only avoid granting the action that carries it.
- ACLs (portal PCD) sit outside the UME role model and must be reviewed separately (§6.1).
J2EE security roles that mean "full control"
| Role | Meaning |
|---|---|
Administrators | "unrestricted administrative permissions over the applications and services on the J2EE Engine" |
All | sum of all roles on the engine — effectively full control |
KeystoreAdministrator | full unrestricted access to all keystore views and entries — i.e. can read/replace the SSO signing key |
KeystoreViewCreator | create keystore views |
telnet_login | Telnet administration of the engine |
Jndi_all_operations | all JNDI naming operations (without it: lookup only) |
$SAP_J2EE_Engine_Upload | upload permissions |
SAP_JAVA_NWADMIN_CENTRAL | NWA Web Admin across the landscape (from SLD) |
Admin (ADS app) | administrative privileges over Adobe Document Services |
LcrClassWriterAll | SLD write access |
SAMLSSODemo_source / _responder / _destination | protect the SAML SSO demonstration application shipped with AS Java. A demo SSO app in production is a finding — check whether sap.com/tc~sec~app*samlssodemo_* is deployed and undeploy it. |
UME actions that are effectively tier-0
| Action | Why |
|---|---|
Manage_All | Administer users in any company, group and role management, user mapping, import/export, UME configuration, consistency check/repair, full access to the SPML interface. Plus: "In portal installations, any role that includes Manage_All automatically has Role Assigner permissions on all portal roles." |
Manage_Roles | SAP's own warning: "Be careful to whom you assign this action. Users with this action can assign themselves the Administrator role." — self-escalation to full admin. |
AclSuperUser | Portal only. Owner permissions on all PCD objects; cannot be removed in the permission editor. SAP: assign only to the portal Super Administration role. |
Spml_Write_Action | Full access to the SPML provisioning interface — programmatic identity write access, often overlooked because it isn't a UI. |
System_Admin | Change UME configuration + consistency check/repair. |
Second tier: Manage_All_Companies, Manage_All_User_Passwords, Manage_User_Passwords, Manage_Users, Manage_Groups, Read_All, Batch_Admin (import and export), Manage_Role_Assignments, Remote_Producer_Write_Access, Read_User_Mapping_Credentials (SAP: "Only this action in consultation with SAP Support").
Segregation-of-duties variants worth recommending: Manage_Roles_SoD (can create/delete/modify UME roles but cannot change roles assigned to itself, directly or indirectly) and Manage_Role_Assignments_SoD (can assign roles to others in the company, except itself). Flag any role holding the non-SoD variant where the SoD variant would suffice.
Named administrative roles/groups to enumerate
Administrators · SAP_J2EE_ADMIN (ABAP-datasource equivalent — membership is maintained in PFCG/SU01 on the ABAP side, not in NWA) · UME role Administrator · NWA_SUPERADMIN / NWA_READONLY · SAP_JAVA_NWADMIN_LOCAL_READONLY · SAP_JAVA_NWADMIN_CENTRAL / _CENTRAL_READONLY · SAP_SLD_ADMINISTRATOR / SAP_SLD_CONFIGURATOR / LcrClassWriterAll · PI's SAP_XI_ADMINISTRATOR_J2EE etc. · Portal Super/System/User/Content Administration roles.
Everyone / Authenticated Users / Anonymous Users: never grant privileged roles to these. Check every privileged UME role's assigned groups for these three names. Also: do not create directory/DB groups with these names — SAP warns user management will silently malfunction.
Baseline requirement: "Make sure that no users other than system administrators belong to the standard Administrators group."
How to enumerate — and the reporting gap
To see what a UME role grants: /nwa/identity → Search Criteria = Role, data source UME Database → open the role → Assigned Actions tab. To understand an action, re-search with Search Criteria = Action. Reverse direction: select the role → Assigned Users / Assigned Groups, then expand each group transitively (and remember ABAP-sourced groups expand in SU01/PFCG/SUIM, not NWA).
There is no SUIM equivalent. Practical options, best first:
- Identity Management
Export— select users, groups or roles, pressExport; the data renders in the browser in UME import text format. Requires actionBatch_Admin. Passwords excluded. This is the closest thing to a downloadable entitlement extract, and it diffs across audit periods. Caveat:Batch_Adminalso grants import, so scope the reviewer's account carefully (import additionally requires change permission on the principals, soBatch_Admin+ read-only exports but cannot import). - SPML with
Spml_Read_Action— scriptable repeatable extracts without granting write. Prefer overSpml_Write_Action. - ABAP data source → use SUIM,
RSUSR002,RSUSR070,RSUSR008_009_NEW,RSUSR003. Since ABAP roles are the UME groups, most of the entitlement question is answerable there. A genuine argument for the ABAP data source in governance-heavy environments. - Java Configuration Browser (
/nwa/cfg-browser) — read effective property values without changing them. Good for evidence capture. - Session Management (
/nwa/sessionmgt) hasExport to Spreadsheet— point-in-time "who is logged on to what", andTerminatefor incident response. - [UNCONFIRMED] There is no documented UME equivalent of SUIM change-document reporting. Treat the absence of a change trail as a finding rather than assuming one exists.
Also check ume.logon.security_policy.log_client_hostaddress / log_client_hostname — without them, your logon audit records have no source attribution.
5.5 Sessions and cookies
| Cookie | Purpose | Check |
|---|---|---|
JSESSIONID | Web session tracking; also the default SSO mechanism between applications on the same server process | Secure, HttpOnly, Path, Domain, Max-Age |
JSESSIONMARKID | security-session identifier | Secure, HttpOnly |
saplb_<logongroup> | load-balancer stickiness | Secure, HttpOnly; leaks instance + server-process topology |
MYSAPSSO2 | SAP Logon Ticket | HttpOnly via ume.logon.httponlycookie; Secure via ume.logon.security.enforce_secure_cookie; Domain scope via ume.logon.domain.remove_subdomains |
[UNCONFIRMED] The identification of
JSESSIONMARKIDas the security-session identifier cookie is inferential (KBA 3648094 names it as subject to the cookie-protection properties; a primary page naming it as that cookie was not reached). Verify on your release.
HTTP Provider Service properties — NWA → Configuration → Infrastructure → Java System Properties (/nwa/sys-config) → Services → HTTP Provider. (7.0x: Visual Administrator → Services → HTTP Provider.)
| Property | Effect | Caveat |
|---|---|---|
SystemCookiesDataProtection | sets HttpOnly on JSESSIONID, saplb_ (and per KBA 3648094 JSESSIONMARKID) | Default false for backward compatibility. Enable after verifying no application reads system cookies client-side. |
SystemCookiesHTTPSProtection | sets Secure on session-tracking and saplb_ cookies | "it is obligatory that you use SSL since these cookies are not transferred via plain HTTP." Enabling this on an HTTP-reachable system breaks the application — pair it with HTTPS-only enforcement. |
SecuritySessionIDHTTPSProtection | Secure on the security-session cookie only | Overridden if SystemCookiesHTTPSProtection is true. |
SAP's documentation contains a typo on one page —
SystemsCookiesDataProtection. The correct name isSystemCookiesDataProtection.
Web Container properties (same path → Services → Web Container):
| Property | Effect | Review note |
|---|---|---|
SessionIdRegenerationEnabled | regenerates the session ID on every login | This is the session-fixation control. Should be true. Historically off by default; publicly documented for NetWeaver Portal and shows up in scanners as "Session Identifier Not Updated" (KBA 2353999). |
UseSecuritySessionIdUniqueName | unique security-session cookie name per system | Only usable if SessionIdRegenerationEnabled is on. Prevents cross-system cookie collisions between SAP systems sharing a domain. |
SessionIPProtectionEnabled | "the HTTP session cannot be accessed from different IPs" | Strong anti-hijacking control. Breaks under NAT pools, mobile networks, load-balanced egress and some VPNs — recommend with a compatibility caveat, not unconditionally. |
SecuritySessionIdGracePeriod | window (ms) accepting parallel authenticated requests from one client | Default 2000 ms (one SAP page says 3000). "We do not recommend to increase the default value." A raised value widens the session-fixation-protection bypass window — flag anything above the default and demand justification. |
URL rewriting is the flanking risk. If the client rejects cookies, AS Java encodes the session ID as a path parameter (...;JSESSIONID=0123), which lands in proxy logs, browser history and Referer headers. Disable with icm/HTTP/ASJava/disable_url_session_tracking = true — but SAP explicitly cautions: do not set SystemCookiesDataProtection = true and disable_url_session_tracking = true at the same time, or "AS Java cannot handle HTTP sessions correctly." This conflict is a real trap; document it rather than recommending both blindly.
Logout must invalidate three things, not one: the HTTP session (JSESSIONID), the security session (JSESSIONMARKID), and the logon ticket (MYSAPSSO2). A ticket is a bearer credential with no server-side revocation — if logout doesn't clear it, a captured ticket stays valid for the rest of login.ticket_lifetime. Test logout empirically per application; do not assume. Check SAML SLO is configured. Check <session-timeout> per application — an 8-hour idle timeout undermines everything above.
Applicable KBAs: 3648094, 2068872, 1859465, 2353999, 3448970, 1901575, 2233964. Note on stale wording: SAP's text says HttpOnly "currently has effect only for Internet Explorer 6.0 SP1 and later." That is a 2006 statement about browser support, now universal. Don't let it cause a reviewer to dismiss the control.
5.6 Secure Store and key material
Location: /usr/sap/<SID>/SYS/global/security/data/SecStore.properties, with SecStore.key alongside.
Contents, per SAP: the database user SAP<SID>DB and its password, DB pool and connection information, and "information for the user Administrator and its password." Encrypted with the SAP Java Cryptographic Toolkit using triple DES, with the key derived from a key phrase supplied at installation and stored in SecStore.key.
Why the key file matters. Ciphertext and key sit in the same directory on the same filesystem. Anyone who can read both has the AS Java Administrator password and the database password. Therefore:
- OS-level access as
<sid>admis equivalent to AS Java administrator and database administrator, not merely "host access." - Backups, filesystem replicas,
SYS/globalshares, VM snapshots and support-log collections carry the key material off-box. An unrestricted NFS export of/usr/sap/<SID>/SYS/globalis a credential disclosure. - It compounds with the emergency user (§5.1): the same OS access flips
ume.superadmin.activated.
(This document deliberately describes no extraction or decryption procedure. Every item below is "check this permission or setting.")
Filesystem checks
- Restrict ACLs on
/usr/sap/<SID>/SYS/global/security/data/to<sid>admand the SAP group; no world/other read on either file. On Windows check NTFS ACLs and inheritance. - Confirm
SYS/globalis not exposed via an over-permissive NFS/CIFS export or reachable from other systems'<sid>admaccounts (shared-mount landscapes are the usual culprit). - Enumerate who can log in as
<sid>admorsudoto it. That list is the AS Java administrator list — reconcile it against §5.4. - Hunt stray copies:
SecStore*.bak,/tmp, home directories, support-ticket staging areas, old instance directories left by upgrades.
Key phrase
- Changed from any installation default, and unique per system (a landscape sharing one key phrase means one recovered key opens every system).
- SAP's own strength guidance is weak ("between 8 and 30 characters and numbers") but SAP additionally recommends a long phrase with mixed case and special characters. Require the stronger form.
- Held in the organisation's password vault with a documented break-glass procedure — losing it is a recovery problem (KBA 2126229).
- Rotation: Config Tool →
secure store→Change Key Phrase, andFile → Reencrypt Secure Content; cluster stopped, then save and restart. SAP: "The fileSecStore.propertiesmust remain consistent. Do not edit this file manually." - Encryption state: KBA 3109719. The Security Baseline carries a requirement that secure-store encryption is activated.
Backup handling
- Backups of
/usr/sap/<SID>/SYS/globalencrypted at rest, with the backup key held separately from the SAP key phrase? - Who can restore a single file from backup? Selective-file restore of
SecStore.keyby a backup operator bypasses every SAP control. - Retention: old backups contain old key material that still decrypts old ciphertext. After a key-phrase rotation, confirm it was accompanied by password changes for the credentials the store holds (DB user,
Administrator) — otherwise the rotation is cosmetic. - Ask the same questions of DR sites and cloud snapshot repositories.
Related key stores, same logic: the TicketKeystore (SSO signing key, §5.3) and the SSL key pairs live in AS Java Key Storage (/nwa/key-storage), protected by the KeystoreAdministrator / KeystoreViewCreator roles plus the same filesystem/backup exposure. Include them in the same bucket.
ABAP analogue for the coupled system: Secure Storage in the Database, individual key in SecStoreDBKey.pse at rsec/securestorage/keyfile; transaction SECSTORE reports which key type is in use. SAP ships a default key that "provides for obfuscation" only and recommends replacing it — a directly comparable checklist item.
5.7 ICM / HTTP / TLS hardening
Restricting HTTP methods
There is no simple "allowed methods" profile parameter. The documented mechanism is the ICM/Web Dispatcher modification (rewrite) handler: icm/HTTP/mod_<xx> = PREFIX=/, FILE=<action file>. SAP's own idiom:
# only GET and POST allowed
if %{REQUEST_METHOD} !stricmp "GET" [AND]
if %{REQUEST_METHOD} !stricmp "POST"
RegForbiddenUrl ^/(.*) -
Anything else gets 403. This is how you kill TRACE/TRACK and WebDAV verbs. (icm/HTTP/trace_info is a tracing parameter, not the HTTP TRACE method — do not confuse them.)
Web administration interface — icm/HTTP/admin_<xx>
Default: PREFIX=/sap/admin, DOCROOT=$(DIR_ICMAN_ROOT)/admin, AUTHFILE=$(icm/authfile)
| Option | Hardening use |
|---|---|
PORT= | Restrict to specific local ports — use an HTTPS port; SAP: otherwise "the password of the admin user is transferred unencrypted" |
HOST= | Bind to an internal-only interface; localhost/127.0.0.1 = local only |
CLIENTHOST= | Allow admin requests only from named client hosts |
ALLOWPUB= | Set FALSE. With TRUE, public/index.html exposes Monitor, Active Services, Core Thread Status, Host Name Buffer, Release Information and MPI Status without logon |
AUTHFILE= | $(DIR_GLOBAL)/security/data/icmauth.txt — SAP warns users and group membership are plain text here (passwords hashed). "Protect the file from undesired reading." |
SAP recommends client certificates. Installed via SAPinst, user webadm exists with the installation master password — a default-password webadm on an internet-reachable Web Dispatcher is a full compromise path.
For most production AS Java systems the right answer is no ICM web admin exposed at all, or internal-only + HTTPS + ALLOWPUB=FALSE.
URL/IP filtering at the ICM — icm/HTTP/auth_<xx>
Default PREFIX=/, FILTER=SAP. Permission-file line format:
P|D|S <URI pattern> <USER> <GROUP> <CLIENT IP> <SERVER IP>
P permit, D deny, S HTTPS-only for that prefix. Wildcard * only at start or end; empty field = *. Rules evaluate top-to-bottom, first match wins; no match = denied. CASE defaults to FALSE (case-insensitive) and SAP recommends leaving it there. Remember to add both /path and /path/* for applications generating sub-URLs.
Error pages and information leakage
| Parameter | Default | Recommended |
|---|---|---|
is/HTTP/show_detailed_errors | FALSE | Keep FALSE. TRUE leaks server name, date, module, line, component, error description. Cross-ref Note 1616535. |
is/HTTP/show_server_header | FALSE | Keep FALSE — suppresses the server: header. |
icm/HTTP/error_templ_path | $(DIR_ICMAN_ROOT)/error_templ | Custom error pages override the standard ones and make show_detailed_errors irrelevant — review them separately for leakage. |
icm/accept_remote_trace_level | FALSE | Keep FALSE — external clients must not raise the trace level. |
icm/trace_secured_data | FALSE | Keep FALSE — otherwise decrypted SSL payload lands in the ICM trace. |
DoS / resource limits
icm/<PROT>/max_request_size_KB (default 102400 = 100 MB — documented explicitly as DoS protection; lower it to what applications actually need) · icm/max_conn 500 · icm/max_threads 250 · icm/max_sockets 2048 · icm/req_queue_len 1000 · icm/listen_queue_len 512 · icm/conn_timeout 5000s · icm/traffic_control · icm/keep_alive_timeout 60s (range -1, 0, 10–32000; don't go below 10s) · PROCTIMEOUT (ABAP-only 60s; AS Java / dual-stack 600s). SAP recommends setting both TIMEOUT and PROCTIMEOUT explicitly; details in Note 824554. Timeouts apply to HTTP(S) only — not P4/IIOP.
TLS
Profile parameters: ssl/ciphersuites (server), ssl/client_ciphersuites (outbound), icm/HTTPS/client_sni_enabled + ssl/client_sni_enabled = TRUE, per-port icm/ssl_config_<xx> referenced from icm/server_port_<xx> via SSLCONFIG=, icm/HTTPS/verify_client (default 1).
Currently published recommended values (requires CommonCryptoLib ≥ 8.5.4; from SAP Note 510007 §7):
ssl/ciphersuites = 897:PFS:HIGH::EC_X25519:EC_P256:EC_HIGH
ssl/client_ciphersuites = 912:PFS:HIGH::EC_X25519:EC_P256:EC_HIGH
icm/HTTPS/client_sni_enabled = TRUE
ssl/client_sni_enabled = TRUE
Older widely-cited values: 135:PFS:HIGH::EC_P256:EC_HIGH / 150:... (min. CCL 8.4.38).
[UNCONFIRMED] — do not guess the leading integer. It is a bit mask combining allowed TLS protocol versions with cipher-selection flags, documented in Note 510007. The bit table could not be retrieved. Copy the string SAP publishes for your CCL version, then verify empirically.
Verification:
dev_icmtrace → the "SSL Initialization" block; must end with "Success – SapCryptoLib SSL ready!" and lists the effective settings.- CommonCryptoLib version: central note 1848999 — keep it current, it is itself a recurring source of security notes.
- Externally: scan the HTTPS ports and confirm SSLv3/TLS1.0/TLS1.1 are refused and no export/NULL/RC4/3DES suites negotiate.
- AS Java inbound TLS: KBA 3014930. Outbound: KBA 2417205 — note that if the application uses the IAIK library the configuration differs from applications using the SAP JVM/JDK (look for
iaik*packages in connection traces). Minimum JVM levels: SAP JVM 6.1.093+ for NW 7.20/7.3x/7.40, SAP JVM 8 for NW 7.5. SAP JVM 4 (7.0x) and SAP JVM 5 (7.1x) do not support TLS 1.1/1.2 at all — a hard finding for any such system in production. - PI/PO specifically: KBA 2456800.
PSE / key material (NWA Key Storage, /nwa/key-storage):
- Keystore views:
ICM_SSL_<instance_ID>by default;ICM_SSL_<instance_ID>_<port>for additional SSL ports;service_sslholds backup copies. - Each
ICM_SSL_*view holds exactly one key pair — you must remove the old pair before adding a new one, and add the signing CA's certificate to the same view. - Trusted client CAs for client-cert auth go into the same view; the system accepts only client certs signed by a CA present there.
- Every change to an
ICM_SSL_*view must be exported to a PSE file and the ICM restarted before it takes effect. Classic audit finding: view updated, PSE never re-exported. - Certificate review: enumerate every view and every
ICM_SSL_*_<port>; record subject/issuer/notAfter/key size/signature algorithm. Flag <2048-bit RSA, SHA-1 signatures, self-signed server certificates on external endpoints, and anything expiring inside the review window.
5.8 Application-level hardening
Order of preference for switching things off:
- Stop + set start-up mode to "disabled" — NWA → Operations → Systems → Start & Stop → Java Applications. Reversible, survives restart, no deployment change.
- Remove or narrow the application alias — KBA 2586026. Takes effect immediately, no restart.
- Block at the reverse proxy — do this as well, never instead.
- Undeploy the SCA — KBA 2553568. Most invasive; breaks patching/upgrade paths if the component is a dependency, and expect it to be reverted by future SP stacks.
Specific targets are catalogued in §3.3. The consolidated list of "should not be in production": /ctc, /CTCWebService, /wsnavigator, /ejbexplorer, /apidocs, /bcb, the WD tc~wd~tools console/explorer and welcome app, the SAML SSO demo application, /SQLtrace, /OpenSQLMonitors, the default /index.html start page, and Telnet.
Also under the baseline's Java requirement: "unused J2EE Engine services must be deactivated" — NWA → Configuration → Infrastructure → Java System Properties → Services; review the start-up state of each service (telnet provider, IIOP, JMS…) against what applications actually require.
Re-verify after every SP stack. Patching can re-enable or re-add applications (KBA 2602277 for WS Navigator specifically).
Evidence to collect: the alias/application inventory with start-up state, plus an HTTP probe of each sensitive path from an external vantage point showing 403/404 rather than 200.
5.9 Management interfaces
P4 / IIOP / JMX
P4 (5NN04) carries JNDI lookups and JMX/administration traffic — Config Tool, Visual Administrator, telnet-equivalent operations, Solution Manager / Focused Run diagnostics agents, NWDI/NWDS. Plain P4 is not encrypted.
Controls, in order:
- Close it if unused:
icm/server_port_<xx> = PROT=P4,PORT=0(KBA 3583774). Same forIIOP. - Use P4SEC where it must stay:
PROT=P4SECplus a working AS Java SSL setup (KBA 2419031; test per KBA 2134934). - Client side must ask for the secure transport explicitly:
java.naming.provider.url=P4S://host:portorP4HTTPS://host:port, plusTransportLayerQueue=sslorhttptunneling_ssl. ValuesNone/httptunnelingare the insecure variants — look for these in agent and tool configurations. - Network: reachable only from the admin network and diagnostics-agent hosts;
HOST=binding andACLFILE=on the port. - Authorization: P4/JMX access maps to Java administrator roles — tie to the "nobody in
Administratorswho isn't a system administrator" requirement.
JMX read access: SAP's JMX connector is not standard RMI/JMXMP, so plain jconsole will not connect without SAP's client classes (sapj2eeclient.jar / com.sap.engine.* from <instance>/j2ee/j2eeclient). Third-party monitoring products' setup docs are the practical reference for wiring a read-only client. Once connected with a display-only user, the configuration MBeans expose the effective runtime property values — the cleanest way to prove a hardening parameter is actually in force rather than merely written to a profile. Also confirm the JMX/monitoring service account has only monitoring roles.
Telnet admin console
- SAP: "For security reasons, access to the AS Java over Telnet is limited to host 127.0.0.1" and "Communication over Telnet is not encrypted."
- Audit check: enumerate all
icm/server_port_*entries and flag anyPROT=TELNETwhoseHOSTis notlocalhost. - Authorization is the security role
telnet_loginin theservice.telnetpolicy configuration; by default all administrator users qualify. Enumerate its members. SAP: "Do not allow users that are not administrators to use Telnet." - To switch off: KBA 1844869. Note KBAs 2410240 and 1925348 — the NWA route often fails, and the reliable control is the profile:
PROT=TELNET,PORT=0orHOST=localhost. - Read-only inventory commands worth capturing:
LSC(list server processes),JUMP <id>,MAN -g(all command groups),MAN(activated groups),VERSION [-more],LISTPROPS [clusterID] <serviceName>. Default-activated groups:ADMIN,SYSTEM,DEPLOY,TELNET. - Drive it over SSH to the host and script with
expect, capturing transcripts. Do not open it to the network to make scripting easier.
sapstartsrv / SAPControl and SAP Host Agent
Every instance runs sapstartsrv exposing a SOAP web service on 5NN13 / 5NN14, plus the browser SAP MC and the sapcontrol CLI. The Host Agent (1128/1129) exposes the same class of methods. Both bind to 0.0.0.0 by default.
service/protectedwebmethods — the control:
| Value | Effect |
|---|---|
NONE | nothing protected |
DEFAULT | protects ~87 methods |
SDEFAULT | protects ~154 of 169 (kernel 7.53). This is the kernel default from SAP Kernel 7.49 (exact, per SAP's own parameter documentation). |
ALL | everything protected |
Custom deltas: SDEFAULT -GetProcessList style.
Methods left unauthenticated under SDEFAULT: AccessCheck, GetProcessList, GetInstanceProperties, GetSecNetworkId, GetNetworkId, GetSystemInstanceList.
Why it matters: even at SDEFAULT, an unauthenticated caller reaching 1128 or 5NN13 gets GetSystemInstanceList (the full landscape: every instance, host, instance number and feature set — i.e. your exact port map) and GetProcessList. GetAccessPointList enumerates every listening port and protocol.
Recommendation: SAP Security Baseline / Onapsis guidance is SDEFAULT as the floor; current practitioner guidance is to start from ALL — "In standard scenarios there should be no need for unprotected web methods anymore" — and selectively unprotect only what a named legacy tool provably needs (exceptions exist for Azure Monitor for SAP, SUSE SAP Host Exporter, SAP LaMa, Java Log Viewer; see KBAs 2039615, 2577844). Set it in the DEFAULT profile. Apply with sapcontrol -nr <NN> -function RestartService.
Critical limitation to record: sapstartsrv has authentication but no authorization granularity — any user who authenticates can call every web method. The authorised-user list is the real privilege boundary: <sid>adm implicitly, plus service/admin_users and service/admin_groups. (Focused Run setup instructs adding service/admin_users = sapadm — legitimate, but it means sapadm gains full instance-agent control.)
Additional restrictions: service/http/acl_file, service/https/acl_file (localhost must always be included); service/hostname, service/http/hostname, service/https/hostname to bind an interface; enforce HTTPS. Supported auth: OS-level (Unix domain sockets / Windows named pipes), X.509 client certificates, local logon tickets, OS user credentials.
Host Agent specifically — two things to audit:
saphostctrl -function GetCIMObject -enuminstances SAPHostAgentenumerates all configured custom operations. Host Agent "operations" are arbitrary command sets defined in.conffiles under<exe>/operations.d, invoked viaExecuteOperation— a legitimate but powerful remote-execution surface. Check: doesoperations.dexist; is itroot:sapsys 750; is every.confowned by UID 0; what does each command actually run; isExecuteOperationauthenticated?- Host Agent has its own protected-web-methods setting — apply the same unauthenticated-probe test.
The audit test that matters: run each read-only command without -user, from a non-admin host, then from a host outside the intended admin network. Anything that returns data is unauthenticated exposure.
Notes: 927637 (web service authentication in sapstartsrv as of 7.00) and 1439348 (extended security settings — introduces the parameter, ACL files, X.509 SSO). [UNCONFIRMED] exact method counts and shipped defaults per kernel — measure with sapcontrol -function ParameterValue service/protectedwebmethods rather than assuming.
5.10 OS and database layer
File system / accounts
/usr/sap/<SID>and/sapmnt/<SID>owned by<sid>adm:sapsys, group-write only where required. Flag any world-writable or world-readable-sensitive path; noo+wanywhere under/usr/sap/<SID>.- No unexpected
setuid/setgidbinaries —icmbndlegitimately needs privilege forEXTBIND=1ports below 1024; confirm nothing else does. <sid>adm: interactive logon restricted (no shared use, no direct SSH where a jump/sudomodel exists), no password-less SSH keys granting inbound access from user networks,.rhosts/.netrc/shell history free of credentials, umask set so new files aren't group/world writable, no unnecessary group memberships,sudorights enumerated. Same review forsapadmand the DB OS accounts.- Profile files
/usr/sap/<SID>/SYS/profile/*: write access restricted to<sid>adm. Profile write access is equivalent to full system compromise — it setsicm/*andservice/protectedwebmethods. icmauth.txtat$(DIR_GLOBAL)/security/data/icmauth.txt— plain-text users and group membership; restrict read access.- No NFS export of
/sapmntto untrusted subnets (a classic path to profile and Secure Store files).
Database
- The DB technical user used by AS Java must not be DBA-equivalent; password rotated; not reused across systems.
- The DB credentials live in the Secure Store (§5.6) — the checks there are the checks here.
Host firewall: confirm only the intended ports listen (sapcontrol -function GetAccessPointList / netstat inventory against §2.1).
5.11 Logging, monitoring and evidence
AS Java log paths
With <Javadir> = /usr/sap/<SID>/<instance>/j2ee/cluster/server<n>:
| Content | File | Path |
|---|---|---|
| Security audit log | security_audit.log | <Javadir>/log/system/ |
| Default server trace | defaultTrace<n>.trc | <Javadir>/log/ |
| HTTP access log (SAP format) | responses.trc | <Javadir>/log/system/httpaccess/ |
| HTTP access log (CLF) | responses-clf.trc | <Javadir>/log/system/httpaccess/ |
Release split — verify which naming your system uses before writing a procedure. The names above and below come from the 7.31-era "Security Audit Log of the AS Java" page, which is explicit: Log Viewer location
/System/Security/Audit/<subcategories>, file system\usr\sap\<SID>\<instance_number>\j2ee\cluster\server<n>\log\system\security_audit.log, subcategoriesACLs / Configuration / PermissionCheck / PrincipalModification / UserMapping, and event types includingACCESS.ERROR/ACCESS.OK. The 7.00-era (and current S/4HANA-era) pages describe the older security log instead: file\usr\sap\<SID>\<instance_number>\j2ee\cluster\server<n>\log\system\security.<n>.log, a category called "Permission (checking)", and events named "Access violation or access denied" (severity Very high) and "Access granted" (Low), with the.OK/.FAILEDcode family (LOGON.OK,LOGON.FAILED…) belonging to that log. Both are real; they are different logs from different generations. On a 7.0x system look forsecurity.<n>.logand "Permission (checking)"; on 7.1x+ look forsecurity_audit.logandPermissionCheck. The one element common to both is the payload that matters: the record captures the permission the user would have needed. Confirm the file name on the target withlsbefore you script anything against it.
Log Viewer navigation (7.1x+): /System/Security/Audit/<subcategory>. Subcategories: ACLs, Configuration, PermissionCheck, PrincipalModification, UserMapping.
Record format: [Event Name] | [Event Type] | [ObjectID] | [ObjectName] | [Details]. Event types are <PRINCIPAL>.<ACTION> — USER.CREATE, USER.MODIFY_DETAILS, ACL.CREATE/DELETE/MODIFY, ACCESS.OK, ACCESS.ERROR, CUSTOMIZE, LOGIN.OK. Severity mapping: Path=Low, Info=Medium, Warning=High, Error=Very High.
Directly useful for detection rules: user-lock reasons are coded — [1] = locked after too many incorrect logon attempts, [2] = locked by an administrator.
This is the SU53 equivalent — and it is the single most useful thing in the AS Java log estate. On 7.1x+ the PermissionCheck subcategory's ACCESS.ERROR ("Permission check failed") carries, in its Details field, the permission the user would have needed; on 7.0x the equivalent is the security log's "Access violation or access denied" event. Default severity Info logs failures; raising the subcategory to Path also logs ACCESS.OK, which is closer to an ST01 authorization trace. Set ume.secaudit.get_object_name so object IDs resolve to readable names — otherwise non-user/group/role objects show only a hash.
Configuration: NWA → Troubleshooting → Logs and Traces → Log Configuration (/nwa/log-config). KBA 2489841 is the how-to; KBA 3195279 covers "no output to security_audit log".
The two silent-failure traps
- The HTTP access log is driven by logging category
/System/HttpAccess/Access, default severityInfo. SAP: "We recommend that you do not increase the severity as this practically disables the HTTP access log." Someone raising it to Warning/Error to reduce noise silently switches the access log off. FILEWRAP=onin the ICM log parameters overwrites the log each rotation and destroys history. For audit evidence you wantFILEWRAPoff, timestamped filenames,SWITCHTF=day, and an external job shipping rotated files off-host.
Sensitive-data masking in the HTTP access log
Values are replaced with five dots. Masked, exhaustively:
- Path parameter:
jsessionid - Request parameters:
j_password,j_username,j_sap_password,j_sap_again,oldPassword,confirmNewPassword,ticket - Headers:
Authorization,Cookie,JSESSIONID,MYSAPSSO2
Masking does not apply to custom parameters or custom headers. If your applications pass secrets in bespoke query parameters, the access log captures them in clear — a real finding, and the argument for LOGFORMAT=CLFMOD at the ICM (which drops form fields and URI parameters entirely).
ICM / Web Dispatcher logs
icm/security_log = LOGFILE=<file>, LEVEL=<1-3>, MAXSIZEKB=<kb>, SWITCHTF=<hour|day|month>[, FILEWRAP=on]. LEVEL 1 = reason only, 2 = default (adds connection status + start of the offending data), 3 = all data. Default LOGFILE=dev_icm_sec; MAXSIZEKB is documented as both 10000 and 500 depending on the page — read the live value rather than assuming.
icm/HTTP/logging_<xx> — HTTP access log. Default: not set, i.e. no access log. LOGFORMAT options: CLF, CLFMOD (form fields and URI parameters not written — SAP states this is for security reasons; good default), SAP, SAPSMD, SAPSMD2 (adds X-CorrelationID and full headers). Recommended shape:
icm/HTTP/logging_0 = PREFIX=/, LOGFILE=access_log-%y-%m, MAXSIZEKB=10000, SWITCHTF=day, LOGFORMAT=SAPSMD
icm/HTTP/logging_client_<xx> does the same for outbound requests. SAP recommends using the ICM access log rather than the AS Java HTTP Provider access log for AS Java (per-instance instead of per-server-node, better performance).
Other files in /usr/sap/<SID>/<instance>/work/: dev_icm, dev_icm_sec, dev_server<n>, dev_jcontrol, dev_bootstrap, sapstartsrv.log, dev_sldregk/dev_sldregs. Web Dispatcher: dev_webdisp + its own security and access logs.
SIEM feeds, in order of value
security_audit.log(all cluster nodes) — logon failures, admin-group changes, role/ACL changes, UME config changesdev_icm_sec/ Web Dispatcher security log — filter/ACL denials, i.e. attempted access to blocked paths- ICM HTTP access log — the only place you see the actual URLs attempted; essential for detecting
/servlet/*,/ctc/*,/developmentserver/metadatauploader,/wsnavigatorprobing defaultTracefiltered forcom.sap.ASJ.web.*and security-relevant componentssapstartsrvlogs plus OS auth logs for<sid>adm/sapadm
Detection content worth writing: repeated LOGIN.* failures per user/IP · [1] auto-lock events · ACCESS.ERROR bursts · requests to /servlet/, /ctc/, /CTCWebService, /developmentserver/metadatauploader, /wsnavigator, /ejbexplorer, /sap/admin, /nwa from outside the admin network · non-GET/POST methods · new .jsp files under the Portal servlet tree (§4.6).
Retention: Java log files roll aggressively by default and can lose weeks of security_audit.log on a busy system. Confirm the retained window meets policy and that the authoritative copy lives in the SIEM, not on the instance — the ICM work directory is also cleaned by standard housekeeping and is not an archive.
Landscape-wide configuration drift is better handled by Configuration Validation / CSA alerting (§8.3) than by SIEM — wire the CV alerts into the same queue.
6. Phase 5 — Add-on components
Every product below is the same AS Java. Findings in the base stack are findings in all of them. Establish §5 first or the component work is meaningless.
6.1 SAP Enterprise Portal
Anonymous access
The anonymous entry point is <host>:<port>/irj/portal/anonymous. Which users act as "anonymous" is driven by ume.login.guest_user.uniqueids (default guest); every user listed is placed in the Anonymous Users group after restart. A caller can select which named anonymous user to be with ?guest_user=<id>. SAP's own caution: the anonymous role "should ensure that it does not contain sensitive content, for example administration functions."
| Check | Bad looks like |
|---|---|
ume.login.guest_user.uniqueids contents | More anonymous users than the business case needs; an anonymous user that is also a member of real business groups; an anonymous user that is a dialog user with a password usable elsewhere |
Roles assigned to Anonymous Users and Everyone | Anything with admin, content-admin, system-admin, KM-admin, self-registration, or backend-connected iViews reachable anonymously |
| The anonymous role's actual rendered content | Navigation into authenticated worksets; iViews carrying a system alias with mapped credentials |
| Self-registration | Enabled on an internet-facing portal, auto-assigning a group with real content |
Anonymous KM access (/irj/go/km/docs/..., /irj/go/km/navigation?Uri=/) | Anonymous read into KM folders never ACL'd |
Permission model — Permission Editor, ACLs, PCD
Portal permissions are ACL-based over the Portal Content Directory (PCD). Every object inherits from its parent unless it has explicit permissions. Levels: Owner → Full Control → Read/Write → Write → Read → None, plus an independent End User flag (runtime visibility / direct-URL access), plus Role Assigner on role objects and catalog folders. Permissions aggregate — the highest wins. Ship state is deliberately minimal: only super admin has broad rights.
| Check | Bad looks like |
|---|---|
Portal Content root and first-level folders | Everyone / Authenticated Users with Read/Write, Full Control or Owner at or near the root — inheritance then hands it to the whole tree |
| Owner assignments | Any non-super-admin with Owner. Owner = can rewrite the ACL itself, i.e. self-escalation inside the PCD |
Role Assigner on sensitive roles (esp. super_admin_role) | Granted to a broad or delegated-admin group → that group can assign itself administrator roles. The single highest-impact portal ACL finding. |
| End User flag on design-time objects | Enabled on admin iViews/pages/folders, or on objects in a folder end users can reach |
| Aggregation effects | Users "read only" via role but Full Control via a group. Document the effective permission, not the assignment you happened to open. |
| Delegated administration model | One flat "portal admin" group holding super admin instead of separated content/system/user admin roles |
| PCD change control | Content admins able to export/import PCD content between prod and non-prod unreviewed; PCD inspection/debug tools reachable at runtime |
Everyone / Authenticated Users / Anonymous Users are the classic over-assignment vector because they are implicit — nobody "granted" them. Enumerate every ACL entry and role assignment referencing these three; do not sample. Note that SAP's own documentation suggests an Everyone + Write pattern for a shared scratch folder — verify that pattern is used only on an isolated scratch container without End User permission.
Knowledge Management
Two facts make KM a reliable finding source:
- Permission checks only happen if a security manager is configured on the repository manager (System Administration → System Configuration → Knowledge Management → Content Management → Repository Managers → Show Advanced Options → Security Manager). No security manager ⇒ no permission check on that repository.
- From SAP's ACL Permissions report documentation: "If an item neither inherits an ACL nor has its own ACL, all users have full access to it."
| Check | Bad looks like |
|---|---|
| Every repository manager: is a security manager set, and the right one? (ACL Security Manager for DB/CM repos; WebDAV ACL SM only where the remote server is a KM portal; W2k SM for NTFS-backed FS repos) | FS or CM repository with no security manager; WebDAV ACL SM pointed at a non-KM remote; Web Security Manager omitted on an indexed web repo — search snippets and HTML previews then leak content the user can't open |
| Run the ACL Permissions report with "Without Permissions" | Any hits = objects with full access for all users |
Run it with "With Explicit Permissions" for Everyone / Anonymous Users | Anonymous or Everyone read on HR/finance/legal folders; write anywhere |
| Permission owners in the report | Business end users as permission owners (owner ⇒ automatic Full Control) |
| FS repository backing paths and the OS account used | Repo rooted at a share the service account can read broadly — KM becomes a file-share browser |
Archiving Security Manager Roles with Archive Access | Widened beyond super/content admin |
System aliases and user mapping — the highest-value portal finding
User mapping maps portal user → backend user. Two modes: user ID + password (the password is stored in the portal) and logon ticket (no password stored; only an ID mapping, and only where IDs differ — a "reference system" alias lets one mapping serve all ABAP backends with the same ID).
SAP's guidance is explicit: avoid user mapping; use identical user IDs + logon tickets. If you must map, run the connection over SSL/SNC. Strong encryption for user-mapping data must be configured ("Configuring Strong Encryption for User Mapping" is a prerequisite step, not a default guarantee).
| Check | Bad looks like |
|---|---|
Per system object: User Mapping Type and Logon Method | UIDPW mapping to a production ERP — the portal DB now holds reusable backend credentials for every mapped user |
| Admin-maintained ("admin, user") mapping for privileged backend users | A single admin-maintained mapping to a powerful backend account shared by a role — every portal user in that role is that backend user |
| Strong encryption actually configured; where the key material lives | Default/weak encryption; secure-store key phrase unchanged since install ⇒ portal DB backups and prod→non-prod copies carry recoverable backend passwords |
| Transport security on the mapped connection | Mapped UID/PW sent over plain HTTP/RFC without SNC |
| System object permissions | Everyone/Authenticated Users Read on system objects, or End User permission on a system-carrying iView — more people can drive a mapped connection than intended |
| Reference-system alias | Pointing at production while the portal serves an untrusted user population |
| Non-prod portal copies | Prod portal cloned to QA/DEV with user-mapping tables and secure store |
Operational gotcha worth knowing: if all system aliases are removed from a system object, the user mapping is lost even if an alias with the same name is recreated.
Security zones — frequently missed, and it is the anti-direct-URL control
Each portal component/service declares a security zone <vendor>/<security area>/<safety level>/<app>/components/<name>. Documented safety levels include no_safety (anonymous users may access) and low_safety (at least an authenticated portal user); medium_safety / high_safety appear in the shipped hierarchy [UNCONFIRMED as shipped nodes].
A user may invoke a component by direct URL, without an iView, if the component declares a zone and the user has end-user permission on that zone. The additional per-iView zone check is off by default and is enabled with JVM parameter -Dcom.sap.nw.sz=true.
| Check | Bad looks like |
|---|---|
Permissions on the Security Zones folder tree, esp. no_safety / low_safety | Anonymous Users/Everyone end-user permission at a safety-level node (inherited by every component beneath it) rather than on the handful of components that need it |
Components under UndefinedVendor / UndefinedSecurityArea / UndefinedSafetyLevel | Custom or third-party portal apps deployed without zone properties — unclassified code with unclear reachability |
-Dcom.sap.nw.sz | Not set / false on an internet-facing portal — iView components remain invocable by direct URL outside the portal framework |
Custom portalapp.xml review in the transport pipeline | Developers self-assigning no_safety/low_safety to "make it work" |
Portal Activity Report
Off by default. Enabled in NWA (activity report service), plus a Web Dynpro hook (webdynpro/resources/sap.com/pb → PortalHooks → ..._activity_reporting_wd_hook... = true). Central note 1084379. The Activity Data Collector is the per-request raw-log alternative.
| Check | Bad looks like |
|---|---|
| Is any portal usage/access record produced at all | Both Activity Report and ADC off ⇒ no answer to "who viewed what" during an incident |
| Where ADC files go and who can read them | Left on the app server, unrotated, unforwarded |
| Permissions on the Activity Report iView | Exposed to a broad group — treat as personal data |
| Works-council / GDPR sign-off and retention | Activity logging enabled with no documented purpose or retention (a compliance finding in both directions) |
Misconfigurations found repeatedly in assessments
EveryoneorAuthenticated Usershigh on the PCD tree; effective permissions never computed, only assignments spot-checked.- Role Assigner left broad, so delegated admins can self-assign super admin.
- KM repositories with no security manager, and KM objects with no ACL at all.
UIDPWuser mapping to production backends, with a default secure-store key phrase and prod→non-prod copies.- An anonymous role that grew — someone added a "useful" iView with a system alias.
-Dcom.sap.nw.sznever enabled; custom apps inUndefinedSafetyLevel.- Portal published via a plain reverse proxy with no URL allow-list, so
/nwa,/useradmin,/ctc,/webdynpro/dispatcher,/sap/monitoringand KM paths ride along with/irj. - The portal treated as "just a UI" in the risk register while it holds backend credentials and ticket-issuing trust. Public pentest research (Polyakov, Black Hat US-13) makes exactly this argument: compromise of the portal yields access to the connected business systems.
6.2 SAP PI / PO
Exposed paths and required posture
None of these belong on an internet-facing VIP except the one marked.
| Path | What it is | Bad looks like |
|---|---|---|
/dir, /dir/start/directory.jnlp | Integration Directory — channels, agreements, credentials | Reachable from user LAN/DMZ/internet; broad group holding SAP_XI_CONFIGURATOR*; anonymous 200 on the JNLP/start page |
/dir/support/CheckService, /dir/support/ExportabilityCheck | Support servlets | HEAD executes them without authorization → arbitrary file overwrite, SMB relay on Windows (DSECRG-11-026, Note 1503579) |
/rep, /rep/start/repository.jnlp | ESR / Enterprise Services Builder | Design-time write access in production; developer roles in prod |
/rwb | Runtime Workbench | Unauthenticated pages (CVE-2019-0282, CVE-2023-35873 are exactly this class); SAP_XI_MONITOR granted to "all IT" |
/mdt, /pimon | Message Display Tool — shows message payloads | Broad access to payload display. Payloads routinely contain bank details, PII, pricing. CVE-2023-35872 is MDT missing auth |
/AdapterFramework/... (e.g. /admin/channelstatus.jsp) | Adapter Framework admin/status | Channel status readable without auth → adapter inventory, partner endpoints, hostnames |
/MessagingSystem/... | Messaging System monitoring/queues | Queue/status pages open. CVE-2022-41271 (9.4) is unauthenticated here |
/XISOAPAdapter/MessageServlet | The SOAP sender inbound endpoint — the one path with a business reason to be externally reachable | ?channel=*:*:* reachable anonymously; a single shared inbound user for all partners; HTTP not HTTPS; sender agreement with no auth requirement |
/exchangeProfile | Exchange Profile — holds PI service-user names and passwords | Reachable beyond the admin network at all |
/CPACache, /sld, /sr, /nwa, /xpi_inspector | Cache refresh, SLD, Service Registry, NWA, XPI Inspector | XPI Inspector permanently deployed and broadly accessible — it can capture payloads and credentials; SLD open (landscape map + technical system inventory) |
Review method: don't infer from config — enumerate. From an unauthenticated client in each network zone (internet, DMZ, user LAN, admin LAN), request each path and record status codes; "bad" is any 200/302-to-content where you expected 401. Then repeat as a low-privileged authenticated business user — broad-group access to /rwb and /mdt is the common real-world finding.
Technical users
| Component | Default user | ABAP role |
|---|---|---|
| Exchange Profile / SLD | PILDUSER | SAP_BC_AI_LANDSCAPE_DB_RFC |
| Integration Repository / ESR | PIREPUSER / PIREP<SID> | SAP_XI_IR_SERV_USER_MAIN, SAP_SLD_CONFIGURATOR |
| Integration Directory | PIDIRUSER / PIDIR<SID> | SAP_XI_ID_SERV_USER_MAIN, SAP_SLD_CONFIGURATOR, SAP_BC_WEBSERVICE_PI_CFG_SRV |
| Advanced Adapter Engine | PIAFUSER / PIAF<SID> | SAP_XI_AF_SERV_USER_MAIN, SAP_SLD_CONFIGURATOR |
| Integration Server | PIISUSER / PIIS<SID> | SAP_XI_IS_SERV_USER_MAIN, SAP_SLD_CONFIGURATOR |
| Runtime Workbench | PIRWBUSER / PIRWB<SID> | SAP_XI_RWB_SERV_USER_MAIN |
| Sender applications | PIAPPLUSER | SAP_XI_APPL_SERV_USER |
| Principal propagation | PIPPUSER | SAP_XI_APPL_SERV_USER |
| Change Management Server | PILSADMIN / LSADMIN | SAP_XI_CMS_SERV_USER |
Two structural properties from SAP's own PI Security Guide are the actual findings:
- "The name, password and language of all the service users are defined in the exchange profile" — and are retrieved by the Java components at startup. Exchange-profile read access is credential-equivalent for the whole PI landscape. Rotation is a multi-place change; audit for drift (KBA 2474153).
- "All Advanced Adapter Engines of a PI landscape are represented by the same user
PIAFUSER" — one AAE compromise yields a credential valid at every AAE. SAP says the default names "should be changed as required"; per-<SID>naming (PIAF<SID>) is the hardened form.
| Check | Bad looks like |
|---|---|
| Password uniqueness per environment | Same PIAFUSER/PIISUSER password in DEV/QA/PROD — a dev PI box becomes a credential source for prod |
User type of every PI*USER | Type dialog instead of system/service; interactive logon possible |
Where these users can log on besides internal calls (S_RFC, S_TCODE, S_DEVELOP; Java group memberships) | SAP_ALL-equivalent; S_RFC = *; membership in Administrators on the Java side |
| Decentral / non-central Adapter Engines' network position and patch level | A decentral AE in a DMZ or partner zone holding the landscape-wide PIAFUSER password |
Dialog-user roles: SAP_XI_ADMINISTRATOR*, _CONFIGURATOR*, _DEVELOPER*, _MONITOR* | Composite admin roles assigned to whole IT groups; developer + configurator on the same prod user (no SoD between design and runtime config) |
Payload-access roles: SAP_XI_MESSAGE_MODIFY (edit_header/edit_payload), SAP_WS_ADMIN_BIZ_GLB | Payload read/modify granted broadly — payload access means reading business data in transit |
| Channel/partner credentials inside the Integration Directory | Broad Directory read access. CVE-2019-0315 is exactly "Integration Builder Web UI exposes FTP channel passwords." Directory read ≈ read of dozens of third-party and DB credentials |
Repeated lockouts of PIAFUSER/PIDIRUSER/PIISUSER on cache refresh are a known symptom of stale exchange-profile passwords — but should still be triaged, not silently unlocked.
Message-level security
PI provides signature, non-repudiation of origin, non-repudiation of receipt, and encryption via WS-Security, RNIF 2.0, RNIF 1.1/CIDX, SOAP and Mail adapters. Availability differs per adapter. SAP's framing: message-level encryption is required when content must stay confidential in intermediate message stores — i.e. TLS alone does not protect the payload sitting in the PI message persistence and visible in the monitoring tools.
| Check | Bad looks like |
|---|---|
| For every inter-enterprise / regulated interface: signature and/or encryption, or only transport TLS | "We have HTTPS" as the only control on payment/HR/health interfaces — payloads then readable in /mdt and the message store by anyone with monitor access |
| Non-repudiation claims vs what is technically configured | Contractual NRO/NRR claims with no signature configured, or claimed on an adapter that doesn't support NRR |
| Key/certificate lifecycle in the Java keystore | Expired or shared keys; partner certs never rotated; private keys in a view readable by broad admin groups |
Note CVE-2019-0283 (7.1, Note 2747683) — XML digital signature spoofing in the Adapter Engine / Axis adapter. It directly undermines the controls above.
Internet exposure
Only the specific inbound business endpoint should ever be externally reachable, and only via a hardened intermediary with a URL allow-list, TLS termination + re-encryption, authentication (preferably mTLS/client certificate), throttling and WAF inspection.
Microsoft's SAP-on-Azure guidance goes further and recommends an Application Gateway/WAF or API Management rather than SAP Web Dispatcher alone for internet exposure, precisely because Web Dispatcher has no WAF — with the caveat that integration protocols such as AS2 can trip generic WAF rules and need tuning rather than disabling.
PI CVEs to check patch level against
[UNCONFIRMED as to exact scores/scope — verify each against its SAP Note.]
CVE-2022-41272 (~9.9, User Defined Search, Note 3273480, unauthenticated JNDI) · CVE-2022-41271 (~9.4, Messaging System, Note 3267780, unauthenticated JNDI) · CVE-2019-0315 (~7.5, Integration Builder Web UI FTP password exposure, Note 2755438) · CVE-2019-0283 (~7.1, signature spoofing, Note 2747683) · CVE-2019-0328 (~7.2, ABAP Test Modules → OS command execution, Note 2774489) · CVE-2023-35872 (~6.5, MDT, Note 3343564) · CVE-2023-35873 (~6.5, RWB, Note 3343547) · CVE-2020-26826 (~6.5, PI Monitoring unrestricted file upload, Note 2974330) · CVE-2021-27604 (~6.5, XXE in ESR Java Mappings) · CVE-2021-27599 (~6.5, Integration Builder Framework info disclosure) · CVE-2021-27617/27618 (~4.9) · CVE-2019-0282 / 0312 / 0278 (~5.3/4.3, unauthenticated RWB pages, landscape disclosure, DB table-name disclosure) · CVE-2020-6305 (~6.1, REST Adapter XSS) · CVE-2019-0337 (~6.1, Java Proxy Runtime XSS) · plus CVE-2020-6287 (RECON) and Log4Shell in the Web Service Adapter (Note 3130521).
Pattern worth stating in the report: the recurring PI vulnerability class is "monitoring or admin servlet missing an authentication check." That is why network-level restriction of /rwb, /mdt, /MessagingSystem, /AdapterFramework is a control in its own right and not merely defence-in-depth.
Why Integration Directory reachability is a top finding
Read access yields the full interface inventory (who talks to whom), all communication-channel configuration including third-party, DB and FTP credentials, partner endpoints and certificates. Write access yields the ability to re-route or duplicate production message flows — add a receiver, change a channel target — which is a business-transaction manipulation and data-exfiltration capability that leaves no trace in ABAP change logs. Treat Directory write in production as equivalent to a high-privilege business authorization, with change control, four-eyes and dedicated logging.
6.3 SAP Solution Manager
Why SolMan is a landscape-wide target
SolMan holds, by design, RFC destinations into every managed ABAP system and a Diagnostics Agent on every application and database host in the landscape. Destination naming from SAP's Secure Configuration Guide:
SM_<SID>CLNT<Client>_READ— userSM_<SolMan SID>SM_<SID>CLNT<Client>_TRUSTED— trusted RFC into the managed systemSM_<SID>CLNT<Client>_TMW— userSMTW<SolMan SID>SM_<SID>CLNT<Client>_LOGIN— customer-specificSM_<SID>CLNT<Client>_BACK— managed system → SolMan, userSMB_<managed SID>, roleSAP_SOLMAN_BACK. SAP's own text: "The role authorizations are security-critical in general, as this RFC-connection allows a user from a managed system to connect to the SAP Solution Manager" (Note 2257213).
The graph is bidirectional. Compromise of SolMan is compromise of the landscape; compromise of any managed system gives a foothold back into SolMan.
The Java-side bridge that matters most: SM_ADMIN_<SolManSID> is the Java administrator SolMan uses on managed systems, and it is documented as "allowed to create other users in the managed system, assign roles, and run Diagnostics self-check activities" — it creates SAPSUPPORT and SM_COLL_<SolManID>. Whoever controls SolMan controls Java identity on every managed system. Verify it exists only where needed, with a unique password per managed system, and with privileges that are actually required.
CVE-2020-6207 and the EEM agent
Missing authentication check in SolMan 7.2's EEM Manager / User Experience Monitoring (UXMon), CVSS 10.0 (SAP), Note 2890213, exploitable remotely and unauthenticated with access to the SolMan HTTP(S) port. Impact is not confined to SolMan: exploitation enables code execution on managed/satellite systems via the SMD/Diagnostics Agent, i.e. OS-level command execution and takeover of associated SAP systems. In CISA KEV. EPSS ~0.98. Public PoC January 2021.
| Check | Bad looks like |
|---|---|
LM-SERVICE / SOLMANDIAG patch level | Below the Note 2890213 fix level |
| SolMan HTTP(S) port reachability | Reachable from user LAN, DMZ, VPN pool or internet. It should be admin-network only |
| Whether EEM/UXMon is actually used | Deployed and reachable although nobody uses UXMon — remove/restrict rather than only patch |
| Detection coverage | No alerting on SolMan → managed-system agent command execution; no baseline of expected agent activity |
Diagnostics Agent / SMD trust
Technical users and scope: SMD_AGT (agent → SolMan, via P4 / message server), SMD_RFC (ABAP↔Java, created by SOLMAN_ADMIN at runtime, used by Outside Discovery), SMDAGENT_<SolManID> (name is fixed and must not be changed; role SAP_IS_MONITOR), SM_COLL_<SolMan SID>, SAPSUPPORT (dialog, "read-only" diagnostics display), and SM_EXTERN_WS — documented as carrying SAP_SM_EXTERN_WS and SAP_J2EE_ADMIN. There is a dedicated OS user <SID>ADMIN, member of sapsys, documented umask 027. SAP also documents that managed-system role setup "opens a temporary trusted RFC connection."
| Check | Bad looks like |
|---|---|
Password strength/uniqueness of SMD_AGT, SM_EXTERN_WS, SMDAGENT_*, SM_COLL_* | Shared or default; the same agent credentials on prod and non-prod hosts, so a dev host's agent config yields prod-capable credentials |
| Where agent credentials sit on the managed host, and who can read them | Agent config readable by developers or other service accounts; <SID>ADMIN permissions not as documented |
SM_EXTERN_WS privileges as actually assigned | SAP_J2EE_ADMIN present where the scenario doesn't require it — an agent-facing account with Java admin rights |
SAPSUPPORT scope | "Read-only" in name only: extended with S_DEVELOP DEBUG, OS-command or table-display rights |
| Whether temporary trusted RFCs from setup were cleaned up | _TRUSTED destinations left in place after setup, with no owner and no review date |
Agent → SolMan network paths (P4 5NN04, message server 36NN, Introscope 6001, Host Agent 1128) | Agent ports open landscape-wide with no segmentation |
| Direction of trust | Managed production trusting SolMan and SolMan trusting production, while SolMan is administered by a broader group than production is |
Review procedure
- Enumerate
SM_*destinations on SolMan (SM59 /SMSY/LMDB) andSM_*CLNT*_BACKdestinations on each managed system; build the matrix. - Per destination record: type (READ / TRUSTED / TMW / LOGIN / BACK), logon user, whether a password is stored, whether trusted, and the effective authorizations of the logon user in the target.
- Confirm the "read" users are actually read-only in the target — verify against the role, not the name.
- Check
SAP_SOLMAN_BACKin each managed system against Note 2257213. - Trusted RFC: confirm
SAP_SM_S_RFCACL/SAP_SM_BW_S_RFCACLscoping and thatS_RFCACLis not*(§6.7). - Check SolMan's own user population and admin group — SolMan admins are effectively landscape admins.
- Check whether SolMan is in the same change/patch cadence and the same monitoring scope as production ERP. Very often it is not — that is the core finding.
Other high-severity SolMan items: CVE-2020-6198 (9.8, Diagnostics Agent accepts unencrypted connections from unauthenticated sources, Note 2845377) · CVE-2020-6235 (8.6, Collector Simulator, no auth, Note 2906994) · CVE-2022-22544 (9.1, RCA Tools — an administrator can execute code on all connected Diagnostics Agents, Note 3140940) · CVE-2019-0330 (9.1, LM-Service OS command injection, Note 2808158) · CVE-2020-6271 (8.2, Problem Context Manager, Note 2931391) · CVE-2023-36925 / -36921 / CVE-2022-41261 (agent-side issues) · CVE-2025-42887 (9.9, Nov 2025, Note 3668705) and CVE-2025-42880 (9.9, Dec 2025, Note 3685270) — identical descriptions three weeks apart; [UNCONFIRMED] treat 3685270 as a likely incomplete-fix follow-up and verify supersession · CVE-2023-27893 (8.8, ST-PI, Note 3296476) · adjacent: CVE-2023-26458 (6.8, SAP Landscape Management 3.0 — an authenticated LaMa user obtains privileged access to other systems, Note 3312733).
6.4 Adobe Document Services
Accounts and configuration objects
ADSUSER/ADSuser— AS Java side, groupADSCallers→ J2EE security roleADSCaller; rolesSAP_ADSCALLER/SAP_ADSMONITOR. Lives in AS Java or AS ABAP depending on the UME datasource.ADS_AGENT— ABAP-side system user, rolesSAP_BC_FP_ICF/SAP_BC_FPADS_ICF.FP_ICF_DATA_<SID>HTTP destination, typically configured with basic authentication andADS_AGENT's credentials.- ABAP ICF service
fpactivated in SICF; RFC destinationADS; NWA → SOA Management → Technical Configuration → Destination Template Management. Test programsFP_TEST_00,FP_PDF_TEST_00. /AdobeDocumentServices/Configis the commonly-used reachability/version probe. [UNCONFIRMED] as an SAP-documented path — treat it as an assessment target regardless.
| Check | Bad looks like |
|---|---|
| ADS endpoint reachability, unauthenticated and from non-admin zones | Any anonymous 200 returning ADS/version/config detail; endpoint reachable from the user LAN or internet |
ADSUSER type and privileges | Type dialog; interactive logon possible; membership beyond SAP_ADSCALLER/SAP_ADSMONITOR. Note the ADS application also defines an Admin role with administrative privileges over ADS — verify nobody unexpected holds it |
ADS_AGENT type and privileges | Type dialog; roles beyond the two shipped; S_RFC wildcards |
The FP_ICF_DATA_<SID> destination | Basic auth over HTTP; stored credentials for a privileged ABAP user rather than scoped ADS_AGENT; same credentials reused in non-prod |
| Whether ADS is needed on this instance at all | Deployed and reachable on systems that render no forms |
SICF service fp activation scope | Active in clients/systems that don't use interactive forms |
Vulnerability profile — correct a common misconception. Exhaustive NVD searching found no headline ADS XXE CVE. The only confirmed ADS CVEs are third-party library staleness:
- CVE-2025-42927 — CVSS 3.4, Note 3525295: ADS ships a vulnerable OpenSSL version.
- CVE-2026-58235 — CVSS 6.3, Note 3758318: ADS uses outdated open-source cryptographic and data-transfer libraries.
Plus the December 2024 cluster, SAP Note 3536965 (deployment assistance 3544926) — [descriptions from a third-party writeup; verify in the note]:
- CVE-2024-47578 — SSRF: crafted requests reach internal systems from the ADS host.
- CVE-2024-47579 — exposed web service lets an authenticated administrator manipulate PDF font file upload/download.
- CVE-2024-47580 — authenticated attacker creates PDFs with embedded internal server files as attachments (server-side file read via generated PDF).
Interpretation for the checklist: ADS's risk profile is supply-chain/library staleness plus server-side reachability, not a signature XXE. Audit ADSSAP (and ADSSAPHIGHVOL) patch level, and track ADS's bundled library impact KBAs separately (e.g. KBA 3443173 for libcurl/OpenSSL) — patch-level parity with the rest of the stack is not sufficient evidence. If someone on your team is certain about an ADS XXE, they may be recalling CVE-2017-8913 (Visual Composer XXE) or CVE-2024-24743 (CAF Guided Procedures XXE). [Flagged as unresolved.]
Hardening: firewall the ADS endpoint to the calling systems only (it is never an end-user surface) · enforce authentication and verify from each zone · keep ADSUSER/ADS_AGENT as system users, minimum roles, unique per environment, excluded from interactive logon · HTTPS for FP_ICF_DATA_* with certificate validation · patch to at least Note 3536965 · egress-restrict the ADS host (mitigates the SSRF class) · confirm rendering-error responses don't leak file paths or stack traces.
6.5 SAP Web Dispatcher
This is the only component that should terminate internet traffic in front of AS Java.
SAP's stated recommendations (primary source: "Security Information for SAP Web Dispatcher"; Note 870127 is the living source for settings, 538405 for versions):
- Always run the most current version; watch Security Notes affecting it specifically.
- HTTPS instead of HTTP, and use the rewrite handler to force an HTTP→HTTPS switch — this "fully prevents the use of unencrypted HTTP". Caveat SAP raises: not all HTTP clients follow redirects, so web-service endpoints may need switching explicitly.
- HTTPS to the backend too via
wdisp/ssl_encrypt, unless that segment is otherwise adequately secured. - Choose the simplest filter that meets the requirement:
| Mechanism | Use when | Dynamic reload | URL case handling | Security logging |
|---|---|---|---|---|
| ACL files | Restriction is purely client-IP based | Yes | n/a | Yes |
Authentication handler (icm/HTTP/auth_<xx>) | URL filtering; can also key on client/server IP | Yes | Default case-insensitive | Yes |
HTTP rewrite handler (icm/HTTP/mod_<xx>) | Anything the other two can't express | Yes | Per-rule | No |
Note the audit-relevant asymmetry: the rewrite handler produces no security log. If you implement blocking there, add compensating logging.
-
Negative lists must be case-insensitive, because the ABAP application server treats URLs case-insensitively.
-
"Definitely filter the following URLs as these provide details of the infrastructure and the configuration":
/sap/public/icman/*/sap/public/ping/sap/public/icf_info/* -
Enable HTTP logging and security logging.
wdisp/permission_table — the allow-list
P|D|S <URI pattern>
P permit, D deny, S permit only over HTTPS. Wildcard * only at start or end. First match wins. The URI permission table is case-sensitive — which is exactly why SAP insists on a positive list here.
SAP's documented pattern to copy:
P /sap/bc/test.cgi
D *.cgi
P /sap/bc/public/*
P /sap/bc/ping
D *
SAP's explicit recommendation: "Use Positive Lists … at the end of the table set row D *. In this way URLs that are correct might still get rejected … but you do not have the problem that URLs could bypass the Web Dispatcher because they are written differently to a prohibited URL indicated with a D." SAP's stated prerequisite: "You are using the SAP Web dispatcher as the only point of access for HTTP(S) requests."
Size limits (readable in RZ11): wdisp/max_permitted_uri_len 2048 · wdisp/permitted_uri_char_range (e.g. 32-127; empty = all) · wdisp/max_permission_table_size 300 · wdisp/max_permission_table_entry_size 256.
The 300-row cap is a real constraint on how granular an allow-list you can build. Plan the path taxonomy accordingly, or push finer rules into
icm/HTTP/auth_<xx>permission files on the ICM side.
Practical layered shape for an internet-facing Portal / PI
- Firewall/DMZ: only 443 to the Web Dispatcher; WD → backend on HTTP(S) only. P4/P4SEC/IIOP/TELNET/sapstartsrv ports (5NN04, 5NN05, 5NN06, 5NN07, 5NN08, 5NN13, 5NN14) never traverse the DMZ boundary.
- Web Dispatcher: positive
wdisp/permission_tableendingD *;Sentries so exposed paths are HTTPS-only; the three/sap/public/*patterns denied; ACL file on the admin port;icm/HTTP/admin_*with HTTPS +HOST+CLIENTHOST+ALLOWPUB=FALSE; rewrite handler for HTTP→HTTPS and method restriction; HTTP log (CLFMODorSAPSMD) +icm/security_log.- Portal: permit
/irj/*plus the specific/webdynpro/*and/sap/public/bc/*resources actually needed; deny/nwa*,/ctc*,/CTCWebService*,/wsnavigator*,/ejbexplorer*,/sap/admin*,/sap/monitoring*,/AdminTools*,/SQLtrace*,/OpenSQLMonitors*,/apidocs*,/bcb*,/developmentserver*,/*/servlet/*,/. - PI/PO: permit only the concrete partner endpoints (
/XISOAPAdapter/MessageServlet*, the specific/cxf/*paths); deny the rest of/AdapterFramework*,/MessagingSystem*,/dir*,/rep*,/rwb*,/mdt*,/exchangeProfile*,/nwa*.
- Portal: permit
- ICM on the AS Java instance: repeat the restriction with
icm/HTTP/auth_<xx>+PERMFILE(case-insensitive), so the app server is not naked if the proxy is bypassed;ACLFILE=on the HTTP(S) ports to accept connections only from the Web Dispatcher IPs. - Application layer: the apps in §5.8 disabled at source, not merely hidden.
| Check | Bad looks like |
|---|---|
| Filter model | Deny-list or none; /* proxied to the Java backend |
| Case sensitivity of deny rules | Case-sensitive negative rules a different-case request walks past |
| Admin interface | Admin port on HTTP, reachable from outside, ALLOWPUB=TRUE, no CLIENTHOST; default/weak webadm |
| Backend leg | Plain HTTP with wdisp/ssl_encrypt unset on an untrusted segment |
| Patch level | Unpatched for CVE-2022-22536 (ICMAD) — request smuggling in front of a Java stack bypasses proxy-level auth and filters entirely |
| Logging | HTTP + security logging disabled — no external-request evidence exists |
| WAF expectations | Relying on Web Dispatcher alone for internet exposure. It has no WAF. |
| Multiplexing | One WD fronting both internet users and admin access to the same Java systems, distinguished only by URL |
6.6 SAP Content Server
The security model is not an independent authorization system. It assumes the SAP system performs the authorization checks and prevents circumvention with a public/private key procedure: the SAP system's public key is uploaded to the Content Server (putCert), and access URLs carry a secKey signature over the parameters together with accessMode, authId and expiration. Keys are system-specific, not user-specific.
Protection is per document via docProt: docProt= means no access restrictions; docProt=du means only signed URLs may update/delete while reads need no signature. There is a server default for whether a secKey is required, overridable per document. SAP's own words: "In live systems, however, you should use signatures."
| Check | Bad looks like |
|---|---|
Server default for secKey, and the docProt distribution across repositories | Server default = no secKey required; large populations with docProt= — content retrievable by anyone who obtains a URL, with no authorization check |
| Whether the signature was "deactivated" on both sides for convenience | Signature disabled in production (the documentation allows it only if disabled on both sides — and warns against it in live systems) |
expiration handling and URL lifetime | Long or absent expiration → durable, shareable, unauthenticated document links landing in browser history, proxy logs and emails |
| Network exposure of the Content Server HTTP port | Reachable from user LAN or internet rather than only from the SAP systems that front it |
Which SAP systems' public keys are installed (putCert) | Certificates from non-production or decommissioned systems still trusted — those systems can mint valid secKeys for production content |
| TLS and patch level | HTTP-only retrieval; unpatched for CVE-2022-22536 (Content Server explicitly named) |
| Cross-check with the ABAP side | Sample documents accessible via Content Server URL that the corresponding ABAP object-level authorization would deny |
6.7 ABAP ↔ Java trust paths (lateral-movement view)
UME against an ABAP data source
Covered in §5.1 and §5.2. The lateral-movement statement for the report: if the Java side is write-enabled (SAP_BC_JSF_COMMUNICATION), compromise of the Java stack is user administration in the ABAP system — create/modify/delete users — a direct path to ABAP. Worst case is a Java portal serving a broad or external user population using production ERP as its UME datasource with write enabled.
Logon ticket trust (Java ↔ ABAP)
Covered in §5.3. The one-line risk statement: ticket trust is user-ID assertion without password verification. Whoever controls a ticket-issuing system, or obtains its signing key, can assert any user ID to every accepting system.
| Check | Bad looks like |
|---|---|
Inventory of ticket issuers trusted by each accepting system (ABAP: SSO2 ACL entries / STRUSTSSO2; Java: ticket keystore + login module config) | A non-production, DMZ or externally-facing Java system in the trusted-issuer list of a production ABAP system |
| Precision of accepted-issuer entries (SID + client + subject) | Wildcarded or overly generic entries; trust of an issuer whose user population you don't control |
| Where the signing key lives and who can export it | Keypair in a view readable by a broad admin group; the same keypair copied into non-prod during a system copy |
| Ticket lifetime, HttpOnly/Secure, domain scope | Long lifetimes; ticket issued over HTTP; cookie domain broad enough to reach unrelated hosts |
| Ticket-accepting enabled where it isn't needed | Every ABAP system accepting tickets "just in case" — enlarges the graph for free |
| Whether a ticket-issuing portal also allows anonymous/self-registered users | Anonymous or self-registered identities on a ticket-issuing portal |
Trusted RFC (SMT1 / SMT2, S_RFCACL)
SMT1/SMT2 establish a relationship in which a caller from the trusted system logs on without a password; the target checks S_RFCACL (calling system ID, client, calling user, "same user" flag). Reference note 128447.
Why it's a classic finding: over-broad S_RFCACL — especially RFC_SYSID = *, RFC_CLIENT = *, RFC_USER = *, RFC_EQUSER = N — turns "trusted" into "anyone from that system may become anyone here, without a password." Combine that with a non-production system trusted by production and you have a documented, supported, fully-logged path from a weakly-controlled system into production — usually held by developers who also have OS access on the source host.
| Check | Bad looks like |
|---|---|
Full trust matrix (SMT1/SMT2, plus SM59 destinations flagged "Trusted System = Yes") | Production trusting DEV/QA/sandbox; mutual trust everywhere; relationships with no documented owner |
Every role/profile granting S_RFCACL, and its field values | * in RFC_SYSID / RFC_CLIENT / RFC_USER; RFC_EQUSER = N with wildcards; S_RFCACL inside a widely-assigned composite role |
Who holds S_RFCACL in the trusting (target) system | End users or developers rather than a small set of scoped technical identities |
Whether the newer trusted/trusting security concept is in place (Note 3089413; SAP publishes check report zcheck_note_3089413 in the SAP-samples security-services-tools repo; KBA 3493322 covers the one-sided-migration failure mode) | Still on the legacy method; only one side migrated; migration never planned |
| Trusted RFCs created by tooling and never removed | Long-lived _TRUSTED destinations from a one-off SolMan setup |
| "Current user" + trusted where the calling user is privileged in both systems | A single identity that is admin in the source and admin in the target |
Also check patch level for the RFC/trusted-system authentication issues from the SEC Consult RFC exploit-chain disclosure (CVE-2021-27610 and related) — [UNCONFIRMED CVE↔note mapping].
JCo / RFC destinations in NWA with stored credentials
NWA → Configuration → Infrastructure → Destinations (/nwa/destinations) and JCo RFC Provider (/nwa/jco-destinations). Connection data plus often a stored user and password, persisted in the AS Java secure store.
| Check | Bad looks like |
|---|---|
| Inventory every destination: type, target system/client, auth method, stored user | Stored credentials into production from a Java system administered by a broader group; destinations to systems nobody recognises |
| Effective privileges of each destination user in the target — the role, not the name | SAP_ALL; S_RFC = *; broad S_TABU_DIS/S_TABU_NAM; S_DEVELOP with DEBUG; S_RZL_ADM; S_TCODE including SM49/SM69/SE38/STMS — i.e. the Java stack stores credentials for an ABAP account that can execute arbitrary code |
| Ticket/assertion-ticket or "current user" propagation vs stored passwords | Basic auth with a stored technical password where SSO propagation was available |
| Transport security per destination | RFC without SNC; HTTP without TLS; TLS without certificate validation |
| Secure store key phrase and who can administer destinations | Default key phrase; large NWA admin group; destination admin delegated to app teams |
| Non-prod copies and backups of the Java stack | Prod destinations and their stored credentials present in a refreshed QA system |
| Duplicate/orphan destinations | Multiple destinations to the same target with different (older, more privileged) users — the forgotten one is the finding |
Relevant CVE: CVE-2024-45283 (6.0, Note 3477359) — username and password obtainable when creating an RFC destination.
"The weakest system in the trust graph"
Authentication trust is transitive and does not respect your system-classification tiers. The effective security level of a production system is the minimum over: itself, every system whose logon tickets it accepts, every system that trusts it via RFC in either direction, every system holding stored credentials into it, and every system whose administrators can reach those credential stores.
An unpatched sandbox portal, a decentral PI Adapter Engine in a DMZ, or a SolMan on a 2019 patch level is therefore a production-severity finding.
Mapping procedure:
- Inventory nodes — every ABAP and Java system (EP, PI/PO, SolMan, LaMa, BW, ADS host, Content Server, Web Dispatchers), tagged with environment, patch level, admin group and network zone.
- Collect edges:
- ABAP:
SM59(all destinations; trusted flag, stored user, "current user"),SMT1/SMT2,STRUSTSSO2accepted issuers,RFCDES/RFCATTRIB,S_RFCACLrole assignments, CUA relationships,SICFactive services, gateway ACLs (secinfo/reginfo). - Java: NWA destinations + JCo RFC provider, UME datasource config (
dataSourceConfiguration_*.xml), ticket keystore contents +EvaluateTicketLoginModuleconfig, portal system objects + aliases + user-mapping type, PI Exchange Profile and communication channels, SolManSM_*destinations and agent registrations. - Perimeter: Web Dispatcher / reverse-proxy route and permission tables — which external hostname maps to which backend and which URL prefixes.
- ABAP:
- Label each edge with direction, mechanism (trusted RFC / ticket / stored credential / shared account / agent protocol), the identity used, and that identity's effective privileges in the target.
- Compute reachability — for each production system, list all nodes with a path to it and the privilege obtained. The findings write themselves: any path from a lower-tier or externally-exposed node into production at high privilege.
- Look for shared secrets as implicit edges — identical passwords for
SAPJSF*,PIAFUSER,SMD_AGT,ADSUSER,<sid>adm, DB users across environments; the same ticket signing key in prod and QA after a system copy; the same secure-store key phrase everywhere. - Check the admin graph too — who can administer each node's credential store (NWA destination admins, Java keystore admins, OS
<sid>adm, DBA, backup operators, hypervisor/storage admins). Credentials at rest are only as protected as the weakest of those roles. - Report as a diagram plus a table, with a target-state trust policy: no prod↔non-prod trust; no ticket acceptance from systems outside the admin boundary; every stored-credential edge scoped to a least-privilege target user with a named owner and review date.
7. Tooling
7.1 Open-source — honest status, September 2026
| Tool | Status | Value for AS Java |
|---|---|---|
| pysap (OWASP) | Alive — v0.2.0 on PyPI 2026-07-28 (full Python 3 migration, closing a ~5-year gap) | Protocols: NI, DIAG, Enqueue, SAPRouter, Message Server, SNC, IGS, RFC, NWRFC, HDB. Offline file tooling: SAR, PSE, Credv2, SSFS. The only credible open-source library for validating SNC/encryption posture, router ACL reachability, message-server exposure and credential-file hygiene. It is a library, not a scanner — you script against it. |
| OWASP CBAS project | Alive, active 2025/26 | Umbrella for pysap, HoneySAP, sncscan, SAPKiln, SSVS |
| sncscan (usdAG) | Alive but small; RFC support incomplete | Analyses SNC posture; reads snc/data_protection/min/max/use, snc/only_encrypted_gui. Only tool of its kind |
| SSVS / NO MONKEY Security Matrix | Alive, ~226 commits | Control catalogue mapped to NIST CSF × SAP operational area × SAP technology × maturity × People/Process/Technology. Draws on SAP Security Baseline, BSI APP.4.2/APP.4.6, OWASP ASVS. The best open framework for structuring a Java-stack audit, because it is technology-tagged rather than ABAP-assumed. |
| SAPKiln (OWASP) | Alive, v1.0, early | 10 modules / 70+ checks — but Windows-only and SAP GUI / ABAP only. No AS Java coverage. |
| Metasploit SAP modules | Frozen (2011–12 core + 2020 additions); still work | See below. No 2021–2026 CVE coverage in the SAP aux tree — verify against your framework copy |
nmap http-sap-netweaver-leak | In mainline | The only SAP-Java-specific NSE script. Targets /irj/go/km/navigation?Uri=/, which SAP declared won't-fix |
gelim/nmap-sap | Dormant (~24 commits) | Custom nmap-service-probes for router, gateway, enqueue, MS, TREX, AS Java, AS ABAP, SAP MC, IGS, Web Dispatcher, plus sap_ports.py. No NSE scripts. Service probes age well — merge them into your probe file. |
| Onapsis CVE-2025-31324 scanner | Frozen by declaration 2025-06-06 | Still the best single artifact for that CVE: vulnerability detection and compromise assessment. Extend the IoC list yourself. |
| Onapsis ICMAD scanner | Available | Works over HTTP/HTTPS and behind a Web Dispatcher. Onapsis warns it is best-effort — false positives and negatives possible, untested behind non-SAP proxies. Corroboration only |
| PowerSAP (airbus-seclab) | Dormant — zero releases ever | ABAP/RFC-centric; little AS Java value |
| bizploit | Dead — last release March 2015; download pages 404 | Historical only |
| Burp SAP extensions | Do not exist in any maintained form | Practical substitutes: BurpSSOExtension (RUB-NDS) for SAML/SSO flows — directly relevant to AS Java SAML 2.0 and logon tickets; plus generic XML/JWT/param-miner. Wireshark, not Burp, is where the SAP-specific dissectors live. |
SAP_GW_RCE_exploit / 10KBLAZE PoCs | Abandoned | The defensive equivalent is auditing gw/sec_info, gw/reg_info, gw/acl_mode, gw/monitor and ms/acl_info directly. Do that instead of running the PoC. gwlogsanalyzer10KBlaze is a legitimately defensive artifact |
Metasploit modules that matter for AS Java (all read-only checks unless noted):
SAP MC / sapstartsrv (5NN13/14) — the practical test for whether service/protectedwebmethods is correct: sap_mgmt_con_version · sap_mgmt_con_instanceproperties · sap_mgmt_con_getprocesslist · sap_mgmt_con_getprocessparameter · sap_mgmt_con_getenv · sap_mgmt_con_getaccesspoints · sap_mgmt_con_listlogfiles / getlogfiles · sap_mgmt_con_startprofile · sap_mgmt_con_extractusers · sap_mgmt_con_brute_login · sap_mgmt_con_osexec (the "is this fully unprotected" test).
AS Java / ICM / HTTP:
cve_2020_6287_ws_add_user— its check semantics are read-only and safe: GET/CTCWebService/CTCWebServiceBean?wsdl, assert 200 +text/xml+ WSDL namespace + aCTCWebServiceservice element. A clean, non-destructive RECON exposure test worth lifting into your own scripts.sap_icm_urlscan— 1,633-path wordlist + paths harvested from/sap/public/icf_info/urlprefix; records theServer:header per response (flags new server headers seen mid-scan, revealing reverse-proxy/backend splits); classifies status codes; retries every 401 withHEADfor verb tampering.sap_ctc_verb_tampering_user_mgmt— the/ctc/ConfigServletverb-tampering case (Notes 1589525 / 1624450, DSECRG-11-041).sap_configservlet_exec_noauth,sap_igs_xmlchart_xxe,cve_2020_6207_solman_rce.sap_service_discovery— port inventory acrossINSTANCES 00-99. Two known labelling inaccuracies: it labels both 5NN02 and 5NN07 as "IIOP" (5NN02 is IIOP Initial Context), and labels 5NN17/18/19 as "Software Deployment Manager" unconditionally, which is only correct on 7.0x.sap_hostctrl_getcomputersystem,sap_router_info_request,sap_router_portscanner,sap_smb_relay.
7.2 Commercial platforms — what each actually covers
- Onapsis — Assess (missing notes, misconfigurations, dangerous interfaces, user/authorization findings; claims 100 % coverage of in-scope SAP Security Baseline v2.6 control points, with 27 control points explicitly out of scope as unsupported technology — ask in writing whether AS Java items are among them), Defend (runtime detection + virtual patching), Control (transport-time and custom ABAP code), Security Advisor. Also the most prolific public source of patch-day analysis and the CVE-2025-31324 IoC work.
- SecurityBridge — native ABAP add-on architecture, installed via SAINT. Strong module set (Patch Management, Vulnerability Management, CVA, Threat Detection, Interface Traffic Monitor, PAM, DLP, SIEM integration). Caveat: the platform overview does not state AS Java / non-ABAP support, and an ABAP-add-on delivery model implies coverage is at best indirect. Confirm explicitly before scoping.
- Layer Seven Security — Cybersecurity Extension for SAP v2.0 — agentless SAP-certified ABAP add-on built around Solution Manager / Focused Run telemetry. 5,000+ vulnerability checks, 1,200+ IoC patterns, 300+ custom-code checks, SIEM integration. Explicitly states coverage for ABAP, HANA and J2EE — of the three vendors, the one that most clearly claims AS Java. Good fit if you already run Focused Run.
- Fortinet — not an SAP application-layer assessment tool. Network/infrastructure only (FortiGate segmentation, IPS, WAF in front of SAP web front ends); its SAP application coverage comes via a partnership with SecurityBridge. Do not count it toward SAP configuration or authorization assessment coverage.
- Others in the category (not endorsements): Pathlock, Xiting, IBS Schreiber.
7.3 SAP's own tooling — and the Java gap you must plan around
The single most important scoping fact: SAP's automated security content is heavily ABAP-biased.
| Tool | Java status |
|---|---|
| EarlyWatch Alert | Security chapter (Note 863362) covers Standard Users, Communication, Configuration, Maintenance, Critical Authorizations, Review & Monitoring — for ABAP/HANA. SAP's own workshop material states "Java systems currently do not provide data into the EarlyWatch Alert Workspace." A Java EWA exists (KBA 2819676) but covers JVM heap, GC, HTTP sessions, logins, request counts and performance — no security checks. ⇒ Do not represent EWA as security coverage for your Java stack. (It does report Invoker Servlet status — KBA 2425081 — which is a useful exception.) |
| Configuration Validation (Solution Manager) | This, not EWA, is where Java-stack configuration assurance lives. Diagnostics Agents collect AS Java configuration into the CCDB as named stores; you author a target system and per-item compliant rules. Works across Property/Table/Text/XML store types. |
| Configuration & Security Analytics (CSA) (Focused Run) | The scale-out successor. Supported stacks explicitly include NetWeaver ABAP and Java, plus Web Dispatcher, Cloud Connector, HANA and others. Policies are XML; rules are a subset of HANA SQL WHERE conditions. Supports exemptions with due dates and drift alerting. |
| System Recommendations (SysRec) | Covers "ABAP and non-ABAP notes" — but Java verdicts are derived from LMDB/SLD component versions, so precision is materially lower than for ABAP. Documented weaknesses: incomplete prerequisite display, once-daily download job, HTTP_NO_MEMORY on large scopes. Practitioner guidance increasingly points at FRUN CSA NotesPolicies as more reliable. |
| Security Optimization Service (SOS) | A Java variant exists in SAP's portfolio — but the self-service SOS in SolMan is ABAP-only (it runs via ST14, an ABAP transaction). The Java variant is remote/CQC-delivered, not self-service. Confirm current orderability with your SAP CoE before relying on it in an audit plan. |
| Code Vulnerability Analyzer (CVA) | ABAP only. Confirmed. There is no CVA for Java — do not scope it. |
| CVA ↔ Fortify integration | Discontinued — SAP no longer supports it, and no longer resells Fortify under the "SAP Fortify" badge. |
| Enterprise Threat Detection (ETD) | ~200 pre-packaged detection patterns. Log sources: NetWeaver/S4 system log, ABAP Security Audit Log, HTTP server log, RFC gateway log, SOAP web-service log, HANA, BTP. [UNCONFIRMED] AS Java application-log coverage — plan on onboarding AS Java's security_audit.log, HTTP access log and default trace as a custom log source and validating the parsers yourself. SAP's investment is in the cloud edition; check the on-premise entry in the PAM for maintenance-end dates before making it a multi-year control. |
Consequence: for AS Java you get infrastructure (Configuration Validation / CSA) plus self-scripted checks, and you must build the policy content yourself.
For custom Java on AS Java (portal components, Web Dynpro Java, EJBs, custom servlets, PI/PO adapter modules): SAP provides nothing. Bring your own SAST and SCA — the latter matters enormously here (log4j, Struts, Xerces, Commons-Collections deserialization gadgets). Treat AS Java custom code as ordinary Java EE code in your existing AppSec pipeline.
7.4 A licence-free assessment pipeline
- Discover — nmap with
gelim/nmap-sapprobes + the §2.1 port formulas across every instance number in scope. - Inventory —
saphostctrl -function ListInstances/GetCIMObject,sapcontrol -function GetSystemInstanceList/GetAccessPointList, per host. - Config extract — Config Tool / filesystem
*.properties+ NWA Java System Properties + Destinations + SSL config +/nwa/cfg-browserreadings, into version control. - Exposure test — unauthenticated probes of the SAPControl/Host Agent methods from a non-admin network position; the §3.4 HTTP path sweep with the HEAD/GET differential; SNC posture via
sncscan. - Continuous validation — push the same config stores into FRUN CSA or SolMan Configuration Validation, author the Java policy from KBA 2286160 + Security Baseline v2.6, diff on a schedule, exempt with documented justification.
- Custom code — your own SAST + SCA.
- Detection — AS Java security log, HTTP access log and default trace into ETD or your SIEM; validate parsers with synthetic events.
8. Standards, baselines and compliance framing
8.1 SAP Security Baseline Template — your requirements source
Current version 2.6, distributed via KBA 2253549 (or support.sap.com/sos → Media Library). ~150 pages plus companion material. Control counts per Onapsis: 69 critical, 92 standard, 53 extended. SAP's position: baseline requirements "must be fulfilled by all SAP systems regardless of any risk assessments."
Structured along SAP's Secure Operations Map; requirement IDs carry an area prefix: I- Infrastructure Security · C- Secure Code · S- Secure Setup · O- Secure Operation · X- Security Compliance.
Java-relevant items (verified from copies of V1.9 — the current text is login-gated):
| ID | Content |
|---|---|
| S-4 | Secure Configuration of Java Systems — deactivate unused J2EE Engine services and unused J2EE applications; assign proper security roles to custom J2EE applications; activate HTTP-only cookie handling; disable the Invoker Servlet (EnableInvokerServletGlobally = false) |
| S-5 | UME parameters — minimum password length 8, enforce secure (HTTPS) cookies |
| S-7 | RFC Gateway security |
| O-6 | Java system administrators — no users other than system administrators in Administrators (single stack) / SAP_J2EE_ADMIN (dual stack) |
| I-5 | Web Dispatcher security |
| also | Secure Store encryption activated; P4 protocol access control; SAP Logon Ticket lifetime ≤ 8h; ume.logon.selfreg = FALSE; user ID and old password must not appear in new passwords; ume.logon.httponlycookie = TRUE; ume.logon.security.enforce_secure_cookie = TRUE (Notes 943336, 2068872) |
[UNCONFIRMED] Do not cite
S-4/S-5/O-6as v2.6 IDs. SAP renumbered and expanded between 1.9 and 2.x. Pull the current IDs from the v2.6 document. Note that v2.5 (April 2024) focused heavily on trust relationships between systems — directly relevant to §6.7 — so current wording on ticket trust is likely stronger than the older copy.
8.2 KBA 2286160 — the linchpin document you must retrieve
"Security related Configuration Stores for JAVA systems." Its confirmed purpose: "You have found SAP KBA 2253549 – The SAP Security Baseline Template and you want to extend the template for JAVA systems to run an extended configuration validation for JAVA systems." Components SV-SMG-DIA-APP-CA (Change Analysis / Configuration Validation / CCDB) and SV-SMG-SER.
[UNCONFIRMED — blocking gap] The actual list of configuration store names is behind SAP for Me. It could not be retrieved from the public preview, the Wayback Machine, or any third-party reproduction, and CCDB Java store naming is easy to get wrong, so it is deliberately not guessed here.
Action: open KBA 2286160 with an S-user and transcribe the store table. It is the authoritative mapping from "baseline requirement" → "CCDB store + field" for Java. Cross-check against the stores actually present for your systems in SolMan → Configuration Validation → CCDB browser, or in Focused Run CSA's store browser.
8.3 How Configuration Validation / CSA actually works
- The Diagnostics Agent (SolMan) / Simple Diagnostics Agent (Focused Run) collects configuration from each managed AS Java instance into the CCDB as named configuration stores — profile parameters, Java service properties, UME properties, deployed components, keystore contents.
- You author a policy as an XML file of check items, each naming a store, a field, an operator and compliant/non-compliant value sets. Focused Run guidance: "you should not add more than approximately 100 check items to a single policy."
- Best practice is one large policy per system type — "all ABAP security parameters", "all JAVA security parameters", "all HANA security parameters" — not many small ones.
- Policies run against a target system list; results render as a System × Checks matrix.
- Exemptions can be granted per system/check with a due date.
- Once green, Configuration Validation Alert Management alerts on drift.
SAP publishes starter policies at github.com/SAP-samples/frun-csa-policies-best-practices (BaselinePolicies/SOS, NotesPolicies updated per patch day, MiscPolicies). The visible content is ABAP and HANA only — the Java policy is yours to author, which is exactly why KBA 2286160 matters.
This is the single strongest evidence artefact you can produce. "Configuration matches approved baseline, deviations detected within N days, exemptions documented and approved" is far better ICFR/SOX evidence than a point-in-time manual review — and it is the argument for investing in the Java policy work.
8.4 External standards
CIS Benchmarks — no SAP NetWeaver benchmark exists, for ABAP or Java. The CIS catalogue contains zero SAP entries. What CIS does give you for an SAP estate: OS benchmarks (RHEL, SLES, AIX, Windows Server), database benchmarks (Oracle, SQL Server, DB2 — not HANA), and the Apache Tomcat benchmark (relevant to BusinessObjects / Information Platform Services). The practical substitute at the SAP application layer is the SAP Security Baseline Template.
DSAG — "Prüfung von SAP S/4HANA" updated July 2026 (covers S/4HANA On-Premise 2025 and Cloud Public 2508; framed against HGB, AO, GoBD, DSGVO, ISO/IEC 27001, COSO/COBIT). "SAP Security – Best Practice Leitfaden" Version November 2025, 79 pages, structured on NIST CSF 2.0 — the more useful of the two for a security (as opposed to financial-audit) assessment. "DSAG ABAP Leitfaden" April 2026. Java content: thin to absent — both current guides are ABAP/S-4/database/infrastructure oriented; neither has an AS Java chapter. German-language only.
BSI IT-Grundschutz — modules APP.4.2 "SAP-ERP-System" and APP.4.6 "SAP ABAP-Programmierung", each with an Umsetzungshinweis. There is no SAP-Java-specific Baustein. For AS Java, compose coverage from APP.3.1 (Webanwendungen und Webservices), APP.3.2 (Webserver) and the SYS.1.x host modules on top of APP.4.2's SAP-generic controls. (Adopting OWASP SSVS inherits the BSI mappings for free.)
ISACA — "Security, Audit and Control Features: SAP ERP", 4th edition, with audit/assurance programs and internal control questionnaires you can lift into a workpaper set. Bias warning: overwhelmingly business-process, authorization and SoD oriented, ABAP-application-layer, with effectively no AS Java technical content. Use it for audit structure and evidence discipline, not Java technical checks.
PCI DSS — SAP is rarely in the CDE directly, but AS Java frequently is via web-facing front ends. The requirements that bite: Req. 6 (patch currency → SysRec / CSA NotesPolicies; secure development for custom Java → your own SAST/SCA; 6.4.3 / 11.6.1 on payment-page scripts hit custom portal front ends) · Req. 2 (no vendor defaults → the standard-user and service/protectedwebmethods findings) · Req. 1 (segmentation → the §3.4 status-code matrix is your evidence artefact) · Req. 8 (MFA for administrative access to NWA, Config Tool, telnet, P4) · Req. 10 (log retention and integrity, centralisation) · Req. 11.3 (annual internal and external testing including segmentation validation). ASV external scanning will not meaningfully test AS Java internals — do not treat a clean ASV scan as assurance.
SOX / ICFR — ITGC coverage falls out naturally: access to programs and data (NWA/UME administrators, telnet_login membership, P4/JMX service accounts, destinations with stored credentials), program changes (SDM/deploy authorization, who can run deploy/undeploy), program development, computer operations. The Java stack is usually scoped in as a supporting/interface layer to an in-scope ABAP financial system — most often PI/PO moving financially relevant data, or a Portal fronting an in-scope application. The audit question is then integrity and access control over that pipe.
9. Master checklist
Condensed and tickable. Each line maps to a section above.
9.1 Discovery
- Instance numbers enumerated; full port list derived from the formulas (§2.1)
-
sapcontrol -function GetAccessPointListcaptured per instance — ground truth for listening ports -
nmap -sVfrom each network zone; results reconciled againstGetAccessPointList - Version / SP / patch level captured per Java component (§2.3)
- Kernel + ICM + Web Dispatcher + Content Server versions captured separately
- Full deployed-application and alias inventory produced, with a justification column (§2.4)
9.2 Network exposure
- P4 (5NN04/05/06) not reachable outside the admin network — and closed with
PORT=0if unused - IIOP (5NN02/03/07) same
- Telnet (5NN08) bound to
localhost;PROT=TELNETentries checked for a widenedHOST - Server debug ports (
5NN21 + n×5) unreachable - sapstartsrv (5NN13/14) and Host Agent (1128/1129) not reachable from user/DMZ networks
- Message server internal port (39NN) firewalled harder than 36NN;
rdisp/msserv_internalset identically on central system and all app servers - SDM / SL Controller (5NN17–19) internal only
- Only the Web Dispatcher terminates internet traffic
- §3.4 probe set run from every zone; status-code matrix retained as segmentation evidence
9.3 Patching
-
VCFRAMEWORKpresent? → CVE-2025-31324 and CVE-2025-42999 and serialFilter (3660659); compromise hunt run regardless (§4.6) - CVE-2025-42944 (RMI-P4 deserialization) —
SERVERCORElevel; Java 8u121+ prerequisite met; P4 consumers regression-tested - CVE-2020-6287 RECON —
LMCTClevel, or documented alias-deactivation workaround - CVE-2022-22536 ICMAD — kernel level on every AS Java, Web Dispatcher and Content Server
- CVE-2026-40128 — Note 3727078
- Every KEV entry in §4.3 assessed for applicability
- Log4j: filesystem sweep for
log4j-core-*.jarincluding deployed applicationlib/directories;JndiLookup.classabsence verified where found - SP maintenance window checked — systems outside the 24-month window flagged as structurally unpatchable
- Configuration-only fixes tracked separately from patch levels
9.4 Identity
-
Administratorpassword changed; secure store and JMS config updated to match -
Guestlocked;ume.login.guest_user.uniqueidsenumerated and every listed identity's roles reviewed -
SAPJSF*— typeSystem,_ROrole unless write is genuinely needed, per-<SID>naming, SNC,UMEBackendConnectionForChangesusing Current User -
ume.superadmin.activated = false;ume.superadmin.passwordnot left populated - All PI, SolMan, ADS technical users: type, roles, password uniqueness per environment
- ABAP-side
SAP*/DDIC/EARLYWATCH/TMSADMdefaults verified withRSUSR003 - Membership of
Administrators/SAP_J2EE_ADMINreconciled to named system administrators - Holders of
Manage_All,Manage_Roles,AclSuperUser,Spml_Write_Actionenumerated; SoD variants recommended where they'd suffice - No privileged role assigned to
Everyone/Authenticated Users/Anonymous Users -
<sid>admlogin list reconciled against the Java administrator list
9.5 Authentication and trust
- Every policy configuration enumerated; every
SUFFICIENTmodule justified -
HeaderVariableLoginModuleabsent, or provably behind a trusted proxy -
Trusted Systemslist exported per system; full issuer→accepter matrix built and every edge justified - Default shipped SSO signing key pair replaced; key length and validity recorded;
KeystoreAdministratorholders enumerated -
login.ticket_lifetime≤ 8h;ume.logon.httponlycookieandenforce_secure_cookieTRUE;ume.logon.domain.remove_subdomainsscoping reviewed - SAML: trusted IdP list justified; SLO configured
- X.509: trust anchor scope reviewed; revocation checking enabled;
CertPersisterLoginModuleauto-enrolment intended - SAML SSO demo application not deployed
9.6 Configuration
-
EnableInvokerServletGlobally = falseglobally AND no per-application override - Every deployed
web.xmlfree of<http-method>inside<security-constraint>; HEAD/GET differential swept -
ume.logon.security_policy.*reviewed — noting the ABAP-datasource bypass and the dual-stack lockout-disabled behaviour -
enforce_policy_at_logon = TRUE(or the policy change is cosmetic) -
ume.logon.selfreg = FALSE;logon_helpreviewed against the plaintext-email behaviour - Cookie flags:
SystemCookiesDataProtection,SystemCookiesHTTPSProtection -
SessionIdRegenerationEnabled = true;SecuritySessionIdGracePeriodat default - URL session tracking disabled — without simultaneously setting
SystemCookiesDataProtection - Logout invalidates HTTP session, security session and logon ticket — tested empirically
-
is/HTTP/show_detailed_errors = FALSE;is/HTTP/show_server_header = FALSE; custom error pages reviewed -
ALLOWPUB=FALSE; ICM web admin HTTPS-only,HOST/CLIENTHOSTrestricted;webadmpassword changed -
icm/<PROT>/max_request_size_KBlowered from 100 MB - TLS:
ssl/ciphersuitesper Note 510007; SSLv3/TLS1.0/1.1 refused externally; CommonCryptoLib current - Every
ICM_SSL_*keystore view enumerated; PSE re-exported after every change; certificates inventoried for expiry, key size, signature algorithm -
service/protectedwebmethodsatALL(orSDEFAULTwith a documented exception list); ACL files set; HTTPS enforced - Unused J2EE Engine services deactivated
-
/ctc,/wsnavigator,/ejbexplorer,/apidocs, WD tools console, default start page disabled — and re-verified after the last SP stack
9.7 Secrets at rest
-
SecStore.propertiesandSecStore.keyACLs restricted; no stray copies -
SYS/globalnot over-exported via NFS/CIFS - Key phrase changed from default, unique per system, vaulted with break-glass procedure
- Backups of
SYS/globalencrypted; selective-restore rights enumerated; post-rotation password changes confirmed - Every NWA destination inventoried with the effective target privileges of its stored user
- Portal user-mapping type reviewed; strong encryption configured
- PI Exchange Profile access restricted
9.8 Logging
- Security audit log active (
security_audit.logon 7.1x+ /security.<n>.logon 7.0x — confirm which);PermissionCheck/ "Permission (checking)" at leastInfo;ume.secaudit.get_object_nameset -
ume.logon.security_policy.log_client_hostaddress/log_client_hostnameenabled - HTTP access log configured (
icm/HTTP/logging_<xx>) — it is off by default - Logging category
/System/HttpAccess/Accessnot raised aboveInfo -
icm/security_logconfigured;FILEWRAPoff; timestamped filenames;SWITCHTF=day - Custom parameters/headers checked for secrets the masking list does not cover
- Logs from all cluster nodes shipped off-host; retention meets policy
- Detection content written for the §5.11 signals
9.9 Add-ons (where present)
- Portal: anonymous role content, PCD ACLs, Role Assigner, KM security managers, ACL Permissions report run "Without Permissions", user mapping, security zones,
-Dcom.sap.nw.sz, Activity Report - PI/PO: admin path reachability per zone,
PIAFUSERpassword uniqueness, Exchange Profile access, Directory read/write scope, message-level security on regulated interfaces, only the inbound business endpoint externally exposed - SolMan:
SM_*destination matrix,SM_ADMIN_<SolManSID>scope,SM_EXTERN_WSprivileges, temporary trusted RFCs cleaned up, CVE-2020-6207 patched, same patch cadence and monitoring scope as production - ADS: endpoint reachability,
ADSUSER/ADS_AGENTscope,FP_ICF_DATA_*over HTTPS, Note 3536965, bundled-library KBAs tracked, host egress restricted - Web Dispatcher: positive permission table ending
D *, the three/sap/public/*denies, admin interface locked down, ICMAD patched, logging on - Content Server:
secKeyrequired by default,docProtdistribution reviewed,putCerttrust list pruned, expiration short
9.10 Trust graph
- Node inventory built with environment, patch level, admin group, network zone
- All edges collected (ABAP + Java + perimeter) and labelled with mechanism, identity and effective privileges in the target
- Reachability computed per production system
- Shared secrets across environments identified as implicit edges
- Admin graph mapped — including backup operators and hypervisor/storage admins
- Target-state trust policy documented
10. Reporting guidance
Severity should reflect reachability, not just CVSS. A CVSS 10.0 on a P4 port that is genuinely unreachable outside a locked admin VLAN is a lower real risk than a CVSS 6.5 unauthenticated monitoring servlet on an internet-facing PI. Report both the vector and the observed reachability, and make the status-code matrix from §3.4 part of the evidence.
Three findings that are almost always worth escalating above their nominal score:
- Anything on the trust graph that gives a lower-tier or externally-exposed node a path into production. It is a supported, logged, fully-documented feature — which is exactly why it survives audits.
- Stored credentials whose target privileges nobody checked. A destination named
READ_ONLY_MONITORINGwhose ABAP user holdsS_RFC = *is a finding about the role, not the name. - Absence of evidence. No Portal Activity Report, no HTTP access log, no
security_audit.logretention, no UME change trail — these are findings in their own right, because they mean the next question ("was this exploited?") has no answer.
Distinguish clearly in the report between: vulnerable and reachable · vulnerable but isolated · hardening gap with no known exploit · no evidence available either way. Blurring those four is the fastest way to lose the reader.
11. Open items — retrieve these with an S-user before publishing
- KBA 2286160 — the actual configuration-store table for Java. The load-bearing gap. Everything else in this document can be verified from public sources.
- Security Baseline Template v2.6 — current requirement IDs and exact Java wording. The V1.9 items in §8.1 are directionally correct but renumbered.
- SAP Note 510007 — the
ssl/ciphersuitesbit-mask table. - SAP Note 870127 — current Web Dispatcher security settings (SAP's own documentation defers to it).
- KBAs 3014930 / 2417205 / 2489841 / 1844869 — step detail for AS Java inbound/outbound TLS, security-log configuration, telnet disablement. Note 2489841 in particular would settle the
security_audit.logvssecurity.<n>.lognaming question in §5.11 for your release. 5a. SAP Note 1445998 itself — to settle which release first shippedEnableInvokerServletGlobally = false. Public sources split between 7.20 and 7.30 (§3.2). - SAP Note 1439348 —
service/protectedwebmethodsdetail; the note number is cited by third parties but was not independently confirmed. Note 927637 is confirmed by title. - Note numbers missing from NVD for: CVE-2021-37535 (JMS Connector), CVE-2016-3974, CVE-2017-8913, CVE-2017-11457, CVE-2015-4091, CVE-2018-2368, CVE-2021-33671, CVE-2016-3979/3980, and CVE-2017-12637 (original 2486657 vs KEV's 3476549).
- Possible incomplete-fix chains — verify supersession: EP Administration (3621236 → 3714585) and SolMan RFC code injection (3668705 → 3685270).
- CVE-2025-42922 — component not narrowed in public sources beyond "AS Java"; retrieve Note 3643865.
- Whether the SOS Java variant is currently orderable, and whether AS Java items sit inside Onapsis's "27 baseline control points for unsupported technology." Both are procurement questions to put in writing.
- SAP ETD AS Java log-source support and on-premise ETD maintenance-end dates.
- DSAG Prüfleitfaden AS Java chapter — confirmed the guides exist and are current, but no AS-Java-specific chapter was located.
Items flagged [UNCONFIRMED] in the body, collected: xAdministrators as a standard name · JSESSIONMARKID as the security-session cookie · ume.persistence.data_source_configuration spelling · a /nwa/ume-config quick link · /ProfileService as a standard endpoint · /AdobeDocumentServices/Config as an SAP-documented path · medium_safety/high_safety as shipped security-zone nodes · the SP from which EnableInvokerServletGlobally=false first shipped · Web Dispatcher installer default ports · message-server HTTP path strings · service/protectedwebmethods method counts per kernel · CVE-2022-22533's delivery vehicle · whether an ADS-labelled XXE CVE exists · the CVE↔note mapping for the trusted-RFC exploit chain (CVE-2021-27610 and siblings) · whether a JMX/MMC-specific missing-authorization CVE exists (CVE-2021-21481 is MigrationService).
A standing caveat: every affected-version list, minimum patch level and verification procedure in this document that is attributed to an SAP Note came from a secondary source (Onapsis, Rapid7, Tenable, Layer Seven, CSA Singapore, SAP Community). Confirm against the note text before it becomes audit evidence.
12. Sources
SAP Help Portal — ports, ICM, Web Dispatcher
- AS Java Ports — AS Java Security Guide (7.0x) · NW 7.5 · NW 7.4
icm/server_port_<xx>(7.31) · (7.40)icm/HTTP/admin_<xx>·icm/HTTP/auth_<xx>·icm/security_log·icm/HTTP/logging_<xx>- ICM Parameters — Reference for ABAP and Java · is/HTTP/show_detailed_errors · Managing Error Information · Timeout Options · Defining Modification Actions
- Using the Web Administration Interface (
/sap/admin,webadm) · Security Information for SAP Web Dispatcher · Web Dispatcher as a URL Filter /wdisp/permission_table - Security Settings for the SAP Message Server
- Viewing and Configuring the Communication Ports (SAP MC → Access Points)
- TCP/IP Ports Used by SAP Applications (2009 PDF — most complete public port table, but 17 years old; successor is KBA 2506865)
- SSL Parameters for ICM and Web Dispatcher · Configuration of the AS Java Keystore Views for SSL
SAP Help Portal — identity, authentication, authorization
- Authorization Concept of SAP NetWeaver AS for Java · Standard Roles · Standard UME Actions · UME Roles and Actions (AS Java) · Monitoring Roles
- Standard Users (AS Java Security Guide) · Standard User Groups · Protecting Standard Users (AS ABAP)
- UME Properties for the Security Policy · UME Properties for Logon Functions · Configuring the Security Policy for User IDs and Passwords · Activating the Emergency User
- Configuring the UME to Use an AS ABAP as Data Source · Constraints for UME with ABAP Data Source · Requirements for the System User for UME-ABAP Communication (SAPJSF) · LDAP Directory as Data Source
- Login Modules · Policy Configurations and Authentication Stacks · Configuring the AS Java to Issue Logon Tickets · Configuring the AS Java to Accept Logon Tickets · Configuring AS Java as a SAML 2.0 Service Provider
- Exporting User Management Data · Configuration Work Center (NWA quick links)
SAP Help Portal — sessions, secure store, logging
- Session Security Protection (7.3x — fullest property set) · AS Java Cookies · Managing Sessions · HTTP Provider Service
- Data Storage Security (SecStore contents, SDM password) · Managing Secure Storage in the File System · Secure Storage in the Database (ABAP) · Working with the SDM
- Security Audit Log of the AS Java (7.31 —
security_audit.log,PermissionCheck,ACCESS.ERROR) · entry format · Security Audit Log — NW 7.00 variant · Security log —security.<n>.log, "Permission (checking)" (S/4HANA-era page) · Tracing and Logging — AS Java Security Guide · HTTP Access Logs · Masking Security-Sensitive Data in the HTTP Access Log · Administration Using Telnet · Using P4 Protocol Over a Secure Connection
SAP Help Portal — add-ons
- Portal Permissions · Permission Levels · Security Zones · Portal Security Considerations · Configuring Anonymous Logon with Named Anonymous Users · KM ACL Permissions report · KM Security Managers · User Mapping · Portal Activity Report
- PI Security Guide — Service Users for Internal Communication · PI Service Users (config) · PI Message-Level Security
- Secure Configuration Guide — SAP Solution Manager 7.2 (PDF) · Overview: All Users Created in Basic Configuration in SOLMAN_SETUP
- SAP Interactive Forms by Adobe — User Management
- SAP Content Server HTTP Interface (PDF —
secKey/docProt/putCert) - SAPHostControl Web Service Interface (Operations Guide PDF)
SAP Notes and KBAs
(Titles confirmed; most bodies require SAP for Me authentication.)
Baseline & validation: 2253549 · 2286160 · 2554633 Invoker servlet: 2326767 · 2649730 · 2425081 · Notes 1445998, 1467771, 1503579 RECON / VC: 2948106 · Notes 2934135, 2939665, 2947895, 3594142, 3593336, 3596125, 3604119, 3660659 ICMAD: 3148968 · Notes 3123396, 3123427, 3137885, 3138881 P4 / RMI: 3583774 · 2419031 · 2134934 · 3637718 · Notes 3634501, 3670067, 3663688 Log4j: 3129883 · Notes 3131047, 3130521 Applications & aliases: 2586026 · 2553568 · 2957221 · 2602277 · 2445893 · 1844869 · 2410240 · 1925348 Identity & sessions: 1901961 · 1596787 · 2873894 · 3263478 · 2827567 · 3648094 · 2068872 · 2353999 · 3448970 · 1901575 Secure store: 2126229 · 3109719 · 3344775 TLS: 3014930 · 2417205 · 2456800 · 2992945 · 1770585 · Notes 510007, 1848999 Logging: 2489841 · 3195279 · 1596214 · 1610103 Versions: 1752501 · 1771843 · 2506865 · 2819676 Add-ons & trust: 2474153 · 2945501 · 2385361 · 3443173 · 3493322 · 2064251 · Notes 128447, 2257213, 3089413, 1084379, 3536965, 3544926, 870127, 538405, 824554, 821875, 927637, 1439348, 1414256, 718383
Advisories and vendor research
- CISA AA20-195A — RECON · CISA TA16-132A — Exploitation of SAP Business Applications (Invoker Servlet) · CISA KEV catalogue (JSON feed) · CSA Singapore AL-2025-040 — Visual Composer Metadata Uploader · CERT-EU 2022-011 (ICMAD)
- Onapsis: CVE-2025-31324 active exploitation · RECON advisory · The Invoker Servlet: A Dangerous Detour · Log4Shell guidance · XXE in SAP Java NetWeaver (CVE-2021-27635) · SAP Management Console hardening · Is enabling SSL to your Java system enough? · Changing properties in SAP NetWeaver Java · Patch Day Sept 2026 · Patch Day June 2026 (CVE-2026-40128) · Implementing SAP Security Baseline v2.6
- ERPScan / Polyakov: "A crushing blow at the heart of SAP J2EE Engine" (Black Hat US-11) · Practical Pentesting of ERPs and Business Applications (Black Hat US-13) · SAP Java Secure Storage
- Chastuhin: "All your SAP passwords belong to us" (CONFidence 2014 — P4 password decryption)
- Tenable: ICMAD · RECON · CVE-2020-6207 PoC
- Rapid7: Active exploitation of CVE-2025-31324
- Layer Seven: US-CERT alert for the Invoker Servlet · Securing Administrative Access in SAP AS Java · Security Analytics with SAP Focused Run · Cybersecurity Extension for SAP
- RedRays: CVE-2025-42944 RMI-P4 · Exploring the P4 protocol · ADS vulnerabilities (CVE-2024-47578/79/80) · Disabling the invoker servlet in the portal
- SEC Consult — RFC interface exploit chain disclosure · Taddong — NetWeaver Portal session fixation · Patzke — SAP domain relaxation and MYSAPSSO2 cookie scoping · INTEGRITY Labs — CVE-2013-3319 Host Agent info disclosure
Tooling
- OWASP/pysap · pysap docs · OWASP Core Business Application Security · usdAG/sncscan · OWASP/SAPKiln · CBAS SAP Security Verification Standard
- Metasploit:
sap_service_discovery·sap_icm_urlscan·cve_2020_6287_ws_add_user·sap_ctc_verb_tampering_user_mgmt·sap_icm_paths.txtwordlist - nmap
http-sap-netweaver-leak·nmap-service-probesSAP signatures · gelim/nmap-sap - Onapsis CVE-2025-31324 Scanner Tools · Onapsis ICMAD scanner · Onapsis IOC scanner
- SAP-samples/frun-csa-policies-best-practices · SAP-samples/security-services-tools (
zcheck_note_3089413) - Configuration Validation (SolMan expert portal) · Configuration & Security Analytics (Focused Run) · System Recommendations · SAP Security Notes & News
- SAP EarlyWatch Alert security workshop (SAP deck) · Introduction into the SAP Security Optimization Services portfolio (SAP deck) · SAP Code Vulnerability Analyzer
- shipcod3/mySapAdventures — methodology, endpoints, dorks · HackTricks — Pentesting SAP · RUB-NDS BurpSSOExtension
Standards
- CIS Benchmarks catalogue (no SAP NetWeaver benchmark exists)
- DSAG SAP-Leitfäden index · Prüfung von SAP S/4HANA (July 2026 PDF) · SAP Security Best Practice Leitfaden (Nov 2025 PDF)
- BSI IT-Grundschutz-Kompendium · APP.4.2 SAP-ERP-System · APP.4.6 SAP ABAP-Programmierung
- ISACA IS/IT audit programs and tools
- Expose SAP Process Orchestration securely with Azure PaaS (Microsoft Learn)
No exploit code appears in this document. Vulnerability references identify what to check and how to prove remediation. Use it only against systems you are authorised to assess.