Skip to content

Commit d7339ab

Browse files
1 parent 9d3cf6e commit d7339ab

8 files changed

Lines changed: 784 additions & 0 deletions

File tree

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
{
2+
"schema_version": "1.4.0",
3+
"id": "GHSA-3h6h-67x3-cv5x",
4+
"modified": "2026-06-08T23:04:25Z",
5+
"published": "2026-06-08T23:04:25Z",
6+
"aliases": [
7+
"CVE-2026-47693"
8+
],
9+
"summary": "Poweradmin: CSV Injection in log export endpoints allows formula execution in spreadsheet applications",
10+
"details": "Description:\n\n### Summary\n\nPoweradmin v4.4.0 is vulnerable to CSV Injection (Formula Injection) in its log export functionality. User-controlled data — specifically the username field — is written to exported CSV files without sanitizing formula trigger characters (=, +, -, @). When an administrator exports activity logs and opens the resulting CSV in a spreadsheet application (Microsoft Excel, LibreOffice Calc, Google Sheets), any formula stored in a username is executed by the application. This can be used for phishing attacks against administrators or data exfiltration.\n\n### Details\n\nThe vulnerability exists in all four log export controllers:\n\n- `lib/Application/Controller/ListLogUsersController.php` (lines 188, 194)\n- `lib/Application/Controller/ListLogZonesController.php`\n- `lib/Application/Controller/ListLogGroupsController.php`\n- `lib/Application/Controller/ListLogApiController.php`\n\nThese controllers export database rows via `fputcsv()` without applying any formula injection countermeasures. The `user` column contains the username of the actor who performed the operation, and the `username` column (in user logs) contains the username of the affected account. Both fields are written verbatim to the CSV output.\n\nA username such as `=1+1` is written **without CSV enclosure quotes** (because it contains no commas or quotes), so spreadsheet applications treat it directly as a formula. A username containing commas or quotes (e.g. `=HYPERLINK(\"http://attacker.com\",\"Click here\")`) is enclosed in CSV quotes with internal quotes doubled, but spreadsheet applications still evaluate the cell value as a formula since it begins with `=`.\n\nAdditionally, PHP deprecation warnings are emitted directly into the HTTP response body before CSV headers, exposing internal file paths (e.g. `/app/lib/Application/Controller/ListLogUsersController.php`) — a secondary information disclosure issue (CWE-209). This also corrupts the CSV file when PHP error reporting is enabled.\n\n### PoC\n\n**Prerequisites:** An account with `user_add_new` permission (administrator role).\n\n**Steps to reproduce:**\n\n1. Log in as administrator.\n2. Navigate to Add User and create an account with:\n - Username: `=HYPERLINK(\"http://attacker.com\",\"Confirm Identity\")`\n - Any valid email and password\n3. Log out, then log in with the newly created account to generate a log entry.\n4. Log back in as administrator.\n5. Navigate to `/users/logs` and click Export CSV.\n6. Open the downloaded CSV file in Microsoft Excel or LibreOffice Calc.\n\n**Result:** Excel renders a clickable hyperlink labeled \"Confirm Identity\" pointing to `http://attacker.com` in the `user` column of the log entry. With the simpler username `=1+1`, the cell displays `2` instead of the literal text, confirming formula execution.\n\nConfirmed on Poweradmin v4.4.0 (Docker image `poweradmin/poweradmin:latest`).\n\n### Impact\n\nThis is a CSV Injection vulnerability (CWE-1236). It affects any administrator who exports activity logs to CSV and opens the file in a spreadsheet application.\n\n**Attack scenarios:**\n\n- **Phishing:** A malicious actor with the ability to create user accounts sets a formula username that renders as a convincing link in the exported report, tricking a higher-privileged administrator into clicking it.\n- **Data exfiltration:** Using `=IMPORTXML()` in Google Sheets or similar, adjacent cell data (log contents) can be sent to an attacker-controlled server silently when the sheet is opened.",
11+
"severity": [
12+
{
13+
"type": "CVSS_V3",
14+
"score": "CVSS:3.1/AV:N/AC:L/PR:H/UI:R/S:C/C:H/I:L/A:N"
15+
}
16+
],
17+
"affected": [
18+
{
19+
"package": {
20+
"ecosystem": "Packagist",
21+
"name": "poweradmin/poweradmin"
22+
},
23+
"ranges": [
24+
{
25+
"type": "ECOSYSTEM",
26+
"events": [
27+
{
28+
"introduced": "0"
29+
},
30+
{
31+
"fixed": "4.2.4"
32+
}
33+
]
34+
}
35+
]
36+
},
37+
{
38+
"package": {
39+
"ecosystem": "Packagist",
40+
"name": "poweradmin/poweradmin"
41+
},
42+
"ranges": [
43+
{
44+
"type": "ECOSYSTEM",
45+
"events": [
46+
{
47+
"introduced": "4.3.0"
48+
},
49+
{
50+
"fixed": "4.3.3"
51+
}
52+
]
53+
}
54+
]
55+
}
56+
],
57+
"references": [
58+
{
59+
"type": "WEB",
60+
"url": "https://github.com/poweradmin/poweradmin/security/advisories/GHSA-3h6h-67x3-cv5x"
61+
},
62+
{
63+
"type": "PACKAGE",
64+
"url": "https://github.com/poweradmin/poweradmin"
65+
},
66+
{
67+
"type": "WEB",
68+
"url": "https://github.com/poweradmin/poweradmin/releases/tag/v4.2.4"
69+
},
70+
{
71+
"type": "WEB",
72+
"url": "https://github.com/poweradmin/poweradmin/releases/tag/v4.3.3"
73+
}
74+
],
75+
"database_specific": {
76+
"cwe_ids": [
77+
"CWE-1236"
78+
],
79+
"severity": "MODERATE",
80+
"github_reviewed": true,
81+
"github_reviewed_at": "2026-06-08T23:04:25Z",
82+
"nvd_published_at": null
83+
}
84+
}
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
{
2+
"schema_version": "1.4.0",
3+
"id": "GHSA-5pvg-856g-cp85",
4+
"modified": "2026-06-08T23:02:48Z",
5+
"published": "2026-06-08T23:02:48Z",
6+
"aliases": [
7+
"CVE-2026-47691"
8+
],
9+
"summary": "Netty has Insufficient Bailiwick Validation for NS Records",
10+
"details": "### Summary\nNetty's `DnsResolveContext` insufficiently validates the bailiwick of NS records, enabling DNS Cache Poisoning. An attacker controlling an authoritative name server for a subdomain can poison the cache for parent domains (like `.co.uk`).\n\n### Details\nIn `io.netty.resolver.dns.DnsResolveContext.AuthoritativeNameServerList#add` method accepts any NS record from the AUTHORITY section as long as the record's name is a suffix of the questionName.\n\nThis means if the resolver queries evil.co.uk., it will accept an NS record claiming authority over co.uk.. Subsequently, the `handleWithAdditional` method caches the associated A records from the ADDITIONAL section directly into the `authoritativeDnsServerCache` under the parent domain's key (co.uk.). This bypasses standard bailiwick rules, where a server authoritative for a subdomain should not be trusted to provide authoritative records for its parent. The poisoned cache is then used for all future resolutions under co.uk..\n\nThe `io.netty.resolver.dns.DnsResolveContext.AuthoritativeNameServerList#cache` method only prevents caching if the record is for the root zone (dots == 1).\n\n### Impact\nDNS Cache Poisoning. Any application using Netty's DNS resolver is impacted.",
11+
"severity": [
12+
{
13+
"type": "CVSS_V3",
14+
"score": "CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:C/C:H/I:H/A:N"
15+
}
16+
],
17+
"affected": [
18+
{
19+
"package": {
20+
"ecosystem": "Maven",
21+
"name": "io.netty:netty-resolver-dns"
22+
},
23+
"ranges": [
24+
{
25+
"type": "ECOSYSTEM",
26+
"events": [
27+
{
28+
"introduced": "4.2.0.Final"
29+
},
30+
{
31+
"fixed": "4.2.15.Final"
32+
}
33+
]
34+
}
35+
],
36+
"database_specific": {
37+
"last_known_affected_version_range": "<= 4.2.14.Final"
38+
}
39+
},
40+
{
41+
"package": {
42+
"ecosystem": "Maven",
43+
"name": "io.netty:netty-resolver-dns"
44+
},
45+
"ranges": [
46+
{
47+
"type": "ECOSYSTEM",
48+
"events": [
49+
{
50+
"introduced": "0"
51+
},
52+
{
53+
"fixed": "4.1.135.Final"
54+
}
55+
]
56+
}
57+
],
58+
"database_specific": {
59+
"last_known_affected_version_range": "<= 4.1.134.Final"
60+
}
61+
}
62+
],
63+
"references": [
64+
{
65+
"type": "WEB",
66+
"url": "https://github.com/netty/netty/security/advisories/GHSA-5pvg-856g-cp85"
67+
},
68+
{
69+
"type": "PACKAGE",
70+
"url": "https://github.com/netty/netty"
71+
},
72+
{
73+
"type": "WEB",
74+
"url": "https://github.com/netty/netty/releases/tag/netty-4.1.135.Final"
75+
},
76+
{
77+
"type": "WEB",
78+
"url": "https://github.com/netty/netty/releases/tag/netty-4.2.15.Final"
79+
}
80+
],
81+
"database_specific": {
82+
"cwe_ids": [
83+
"CWE-345"
84+
],
85+
"severity": "HIGH",
86+
"github_reviewed": true,
87+
"github_reviewed_at": "2026-06-08T23:02:48Z",
88+
"nvd_published_at": null
89+
}
90+
}
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
{
2+
"schema_version": "1.4.0",
3+
"id": "GHSA-5x3r-wrvg-rp6q",
4+
"modified": "2026-06-08T23:02:41Z",
5+
"published": "2026-06-08T23:02:40Z",
6+
"aliases": [
7+
"CVE-2026-47244"
8+
],
9+
"summary": "Netty HTTP/2: Advertised MAX_CONCURRENT_STREAMS are not enforced",
10+
"details": "### Impact\nDefaultHttp2Connection.DefaultEndpoint initialises maxActiveStreams/maxStreams to Integer.MAX_VALUE, and Http2Settings never inserts SETTINGS_MAX_CONCURRENT_STREAMS by default (Http2Settings.java:305-307 only clamps a user-supplied value). Unless the application explicitly calls initialSettings().maxConcurrentStreams(n), a Netty HTTP/2 server advertises no limit and enforces none locally. Each open stream allocates a DefaultStream object, PropertyMap slots, flow-controller state and IntObjectHashMap entry; with ~2^30 permissible odd stream IDs a single TCP connection can create hundreds of thousands of long-lived stream objects. This is also the precondition for CVE-2023-44487-style Rapid-Reset amplification, where the absence of a low concurrent cap multiplies backend work.\n\n### Resources\nhttps://www.rfc-editor.org/rfc/rfc7540.html#section-6.5.2",
11+
"severity": [
12+
{
13+
"type": "CVSS_V3",
14+
"score": "CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:L"
15+
}
16+
],
17+
"affected": [
18+
{
19+
"package": {
20+
"ecosystem": "Maven",
21+
"name": "io.netty:netty-codec-http2"
22+
},
23+
"ranges": [
24+
{
25+
"type": "ECOSYSTEM",
26+
"events": [
27+
{
28+
"introduced": "4.2.0.Final"
29+
},
30+
{
31+
"fixed": "4.2.15.Final"
32+
}
33+
]
34+
}
35+
],
36+
"database_specific": {
37+
"last_known_affected_version_range": "<= 4.2.14.Final"
38+
}
39+
},
40+
{
41+
"package": {
42+
"ecosystem": "Maven",
43+
"name": "io.netty:netty-codec-http2"
44+
},
45+
"ranges": [
46+
{
47+
"type": "ECOSYSTEM",
48+
"events": [
49+
{
50+
"introduced": "0"
51+
},
52+
{
53+
"fixed": "4.1.135.Final"
54+
}
55+
]
56+
}
57+
],
58+
"database_specific": {
59+
"last_known_affected_version_range": "<= 4.1.134.Final"
60+
}
61+
}
62+
],
63+
"references": [
64+
{
65+
"type": "WEB",
66+
"url": "https://github.com/netty/netty/security/advisories/GHSA-5x3r-wrvg-rp6q"
67+
},
68+
{
69+
"type": "PACKAGE",
70+
"url": "https://github.com/netty/netty"
71+
},
72+
{
73+
"type": "WEB",
74+
"url": "https://github.com/netty/netty/releases/tag/netty-4.1.135.Final"
75+
},
76+
{
77+
"type": "WEB",
78+
"url": "https://github.com/netty/netty/releases/tag/netty-4.2.15.Final"
79+
}
80+
],
81+
"database_specific": {
82+
"cwe_ids": [
83+
"CWE-400"
84+
],
85+
"severity": "MODERATE",
86+
"github_reviewed": true,
87+
"github_reviewed_at": "2026-06-08T23:02:40Z",
88+
"nvd_published_at": null
89+
}
90+
}
Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
{
2+
"schema_version": "1.4.0",
3+
"id": "GHSA-5xrh-qmmq-w6ch",
4+
"modified": "2026-06-08T23:02:33Z",
5+
"published": "2026-06-08T23:02:33Z",
6+
"aliases": [
7+
"CVE-2026-46340"
8+
],
9+
"summary": "Netty: SCTP reassembly nests buffers without bound",
10+
"details": "For each non-complete SctpMessage fragment the handler does `fragments.put(streamId, Unpooled.wrappedBuffer(frag, byteBuf))`, wrapping the previous accumulator and the new slice into a *new* CompositeByteBuf every time. After N fragments the accumulator is an N-deep chain of composites, each holding references and component arrays; readableBytes()/getBytes() on the final buffer recurse N levels. There is no limit on N, on total bytes, or on the number of streamIdentifiers an attacker can open (each gets its own map entry). A peer that never sets the `complete` flag can grow this structure indefinitely from tiny 1-byte DATA chunks.",
11+
"severity": [
12+
{
13+
"type": "CVSS_V3",
14+
"score": "CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:N/A:H"
15+
}
16+
],
17+
"affected": [
18+
{
19+
"package": {
20+
"ecosystem": "Maven",
21+
"name": "io.netty:netty-transport-sctp"
22+
},
23+
"ranges": [
24+
{
25+
"type": "ECOSYSTEM",
26+
"events": [
27+
{
28+
"introduced": "4.2.0.Final"
29+
},
30+
{
31+
"fixed": "4.2.15.Final"
32+
}
33+
]
34+
}
35+
],
36+
"database_specific": {
37+
"last_known_affected_version_range": "<= 4.2.14.Final"
38+
}
39+
},
40+
{
41+
"package": {
42+
"ecosystem": "Maven",
43+
"name": "io.netty:netty-transport-sctp"
44+
},
45+
"ranges": [
46+
{
47+
"type": "ECOSYSTEM",
48+
"events": [
49+
{
50+
"introduced": "0"
51+
},
52+
{
53+
"fixed": "4.1.135.Final"
54+
}
55+
]
56+
}
57+
],
58+
"database_specific": {
59+
"last_known_affected_version_range": "<= 4.1.134.Final"
60+
}
61+
}
62+
],
63+
"references": [
64+
{
65+
"type": "WEB",
66+
"url": "https://github.com/netty/netty/security/advisories/GHSA-5xrh-qmmq-w6ch"
67+
},
68+
{
69+
"type": "PACKAGE",
70+
"url": "https://github.com/netty/netty"
71+
},
72+
{
73+
"type": "WEB",
74+
"url": "https://github.com/netty/netty/releases/tag/netty-4.1.135.Final"
75+
},
76+
{
77+
"type": "WEB",
78+
"url": "https://github.com/netty/netty/releases/tag/netty-4.2.15.Final"
79+
}
80+
],
81+
"database_specific": {
82+
"cwe_ids": [
83+
"CWE-770"
84+
],
85+
"severity": "HIGH",
86+
"github_reviewed": true,
87+
"github_reviewed_at": "2026-06-08T23:02:33Z",
88+
"nvd_published_at": null
89+
}
90+
}

0 commit comments

Comments
 (0)