Detection: PHP Memory Exhaustion Exploitation Attempt via Multipart Request

Description

This analytic correlates Apache and Nginx access and error logs when "multipart/form-data" requests and PHP memory-limit exhaustion errors occur for the same PID, host, and client. It extracts web request details and "PHP" error messages to support investigation of possible PHP2Shell exploitation attempts.

 1(
 2    `apache_access_logs`
 3    OR
 4    `apache_error_logs`
 5    OR
 6    `nginx_access_logs`
 7    OR
 8    `nginx_error_logs`
 9)
10(
11    (http_content_type="multipart/form-data*" AND http_method=POST)
12    OR
13    (
14        "Allowed memory size of"
15        AND
16        "bytes exhausted"
17    )
18)
19
20
21| rex field=_raw "\[pid\s+(?<pid>\d+)"
22
23| rex field=_raw "\]\s+(?<pid>\d+)\#\d+\:"
24
25
26| rex field=_raw "client\:?\s+(?<client>.*?)(?:,
27|\]
28|$)"
29
30| rex mode=sed field=client "s/\:\d+$//g"
31
32
33| rex field=_raw "server\:\s+(?<server>.*?)(?:,\s
34|$)"
35
36
37| rex field=_raw "request\:\s+\"(?<method>\w+)\s+(?<uri>.*?)\s+HTTP\/\d+\.\d+\"(?:,\s
38|$)"
39
40
41| rex field=_raw "(?i)PHP(?:\s+\w+){1,}:\s+(?<error_message>.*?)$"
42
43
44| eval pid=coalesce(worker_pid,process_id,pid)
45
46| eval message=coalesce(error_message,message)
47
48| eval src=coalesce(client,src,src_ip)
49
50| eval dest=coalesce(server,dest,dest_ip)
51
52| eval uri_query=coalesce(uri_query,"")
53
54| eval uri_path=coalesce(uri_path,"")
55
56| eval uri=coalesce(nullif(uri,""),nullif(uri_path.uri_query,""))
57
58
59| stats count min(_time) as firstTime last(_time) as lastTime
60    dc(source) as dc_source
61    values(source) as source
62    dc(sourcetype) as dc_sourcetype
63    values(sourcetype) as sourcetype
64    values(http_method) as http_method
65    values(dest) as dest
66    values(dest_port) as dest_port
67    values(site) as site
68    values(uri) as uri
69    values(url) as url
70    values(status) as status
71    values(memory_bytes) as memory_bytes
72    values(http_content_length) as http_content_length
73    values(http_content_type) as http_content_type
74    values(http_referrer) as http_referrer
75    values(http_user_agent) as http_user_agent
76    values(message) as message
77    by pid host src
78
79| where dc_sourcetype>1
80
81
82| `security_content_ctime(firstTime)`
83
84| `security_content_ctime(lastTime)`
85
86| `php_memory_exhaustion_exploitation_attempt_via_multipart_request_filter`

Data Source

Name Platform Sourcetype Source
Nginx Error Log Web 'nginx:plus:error' '/var/log/nginx/error.log'
Nginx Access Web 'nginx:plus:kv' '/var/log/nginx/access.log'

Macros Used

Name Value
nginx_access_logs (sourcetype="nginx:plus:kv" OR sourcetype="nginx:plus:access")
php_memory_exhaustion_exploitation_attempt_via_multipart_request_filter search *
php_memory_exhaustion_exploitation_attempt_via_multipart_request_filter is an empty macro by default. It allows the user to filter out any results (false positives) without editing the SPL.

Annotations

CVE

Default Configuration

This detection is configured by default in Splunk Enterprise Security to run with the following settings:

Setting Value
Disabled true
Cron Schedule 0 * * * *
Earliest Time -70m@m
Latest Time -10m@m
Schedule Window auto
Creates Finding (Notable) No
Creates Intermediate Finding (Risk Event) Yes
Anomaly detections generate Intermediate Findings (Risk Events). They do not generate a Finding (Notable) directly.

Implementation

Ingest Apache (https://splunkbase.splunk.com/app/3186) and/or Nginx (https://splunkbase.splunk.com/app/3258) access and error logs into Splunk using their default Splunk add-ons. Follow configuration instructions provided by the respective Splunk add-ons for Apache (https://splunk.github.io/splunk-add-on-for-apache-web-server/Configure/) and Nginx (https://splunk.github.io/splunk-add-on-for-nginx/Setupv2/). In addition to default log formats, enable logging of worker PID (process ID) in both access and error logs. Make sure that you configure the apache_access_logs and apache_error_logs or nginx_access_logs and nginx_error_logs macros with the corresponding source and sourcetype patterns for your environment.

Known False Positives

Legitimate large multipart uploads, application bugs, or load tests can cause memory-limit errors. Review the correlated access and PHP error events before classifying this activity as exploitation.

Associated Analytic Story

Intermediate Findings

Message Entity Field Entity Type Risk Score
PHP memory exhaustion exploitation attempt via multipart/form-data access was observed for PID [$pid$] on host [$dest$] from client [$src$]. host system 30

Threat Objects

Field Type
uri uri

References

Detection Testing

Test Type Status Dataset Source Sourcetype
Validation ✅ Passing N/A N/A N/A
Unit ✅ Passing Dataset /var/log/nginx/error.log nginx:plus:error
Integration ✅ Passing Dataset /var/log/nginx/error.log nginx:plus:error

Replay any dataset to Splunk Enterprise by using our replay.py tool or the UI. Alternatively you can replay a dataset into a Splunk Attack Range


Source: GitHub |

Version: 3