Skip to content

Commit cdde8e6

Browse files
committed
Provide finder grained control of multi-part requests
This exposes two new configuration attributes on the Connector: - maxPartCount - maxPartHeaderSize
1 parent 9263758 commit cdde8e6

6 files changed

Lines changed: 85 additions & 6 deletions

File tree

java/org/apache/catalina/connector/Connector.java

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -212,6 +212,10 @@ public Connector(ProtocolHandler protocolHandler) {
212212
*/
213213
protected int maxParameterCount = 10000;
214214

215+
private int maxPartCount = 10;
216+
217+
private int maxPartHeaderSize = 512;
218+
215219
/**
216220
* Maximum size of a POST which will be automatically parsed by the container. 2 MiB by default.
217221
*/
@@ -482,6 +486,26 @@ public void setMaxParameterCount(int maxParameterCount) {
482486
}
483487

484488

489+
public int getMaxPartCount() {
490+
return maxPartCount;
491+
}
492+
493+
494+
public void setMaxPartCount(int maxPartCount) {
495+
this.maxPartCount = maxPartCount;
496+
}
497+
498+
499+
public int getMaxPartHeaderSize() {
500+
return maxPartHeaderSize;
501+
}
502+
503+
504+
public void setMaxPartHeaderSize(int maxPartHeaderSize) {
505+
this.maxPartHeaderSize = maxPartHeaderSize;
506+
}
507+
508+
485509
/**
486510
* @return the maximum size of a POST which will be automatically parsed by the container.
487511
*/

java/org/apache/catalina/connector/Request.java

Lines changed: 22 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2589,13 +2589,29 @@ private void parseParts(boolean explicit) {
25892589
upload.setFileItemFactory(factory);
25902590
upload.setFileSizeMax(mce.getMaxFileSize());
25912591
upload.setSizeMax(mce.getMaxRequestSize());
2592-
if (maxParameterCount > -1) {
2593-
// There is a limit. The limit for parts needs to be reduced by
2594-
// the number of parameters we have already parsed.
2595-
// Must be under the limit else parsing parameters would have
2596-
// triggered an exception.
2597-
upload.setFileCountMax(maxParameterCount - parameters.size());
2592+
upload.setPartHeaderSizeMax(connector.getMaxPartHeaderSize());
2593+
/*
2594+
* There are two independent limits on the number of parts.
2595+
*
2596+
* 1. The limit based on parameters. This is maxParameterCount less the number of parameters already processed.
2597+
*
2598+
* 2. The limit based on parts. This is maxPartCount.
2599+
*
2600+
* The lower of these two limits will be applied to this request.
2601+
*
2602+
* Note: Either of both limits may be set to -1 (unlimited).
2603+
*/
2604+
int partLimit = maxParameterCount;
2605+
if (partLimit > -1) {
2606+
partLimit = partLimit - parameters.size();
2607+
}
2608+
int maxPartCount = connector.getMaxPartCount();
2609+
if (maxPartCount > -1) {
2610+
if (partLimit < 0 || partLimit > maxPartCount) {
2611+
partLimit = maxPartCount;
2612+
}
25982613
}
2614+
upload.setFileCountMax(partLimit);
25992615

26002616
parts = new ArrayList<>();
26012617
try {

webapps/docs/changelog.xml

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -146,6 +146,13 @@
146146
<code>BlockingQueue</code> implementation. Pull request provided by
147147
Paulo Almeida. (markt)
148148
</scode>
149+
<add>
150+
Provide finer grained control of multi-part request processing via two
151+
new attributes on the <code>Connector</code> element.
152+
<code>maxPartCount</code> limits the total number of parts in a
153+
multi-part request and <code>maxPartHeaderSize</code> limits the size of
154+
the headers provided with each part. (markt)
155+
</add>
149156
</changelog>
150157
</subsection>
151158
<subsection name="Jasper">

webapps/docs/config/ajp.xml

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -188,6 +188,21 @@
188188
exceed the limit.</p>
189189
</attribute>
190190

191+
<attribute name="maxPartCount" required="false">
192+
<p>The maximum total number of parts permitted in a request where the
193+
content type is <code>multipart/form-data</code>. This limit is in
194+
addition to <code>maxParameterCount</code>. Requests that exceed this
195+
limit will be rejected. A value of less than 0 means no limit. If not
196+
specified, a default of 10 is used.</p>
197+
</attribute>
198+
199+
<attribute name="maxPartHeaderSize" required="false">
200+
<p>The maximum number of header bytes permitted per part in a request
201+
where the content type is <code>multipart/form-data</code>. Requests that
202+
exceed this limit will be rejected. A value of less than 0 means no limit.
203+
If not specified, a default of 512 is used.</p>
204+
</attribute>
205+
191206
<attribute name="maxPostSize" required="false">
192207
<p>The maximum size in bytes of the POST which will be handled by
193208
the container FORM URL parameter parsing. The limit can be disabled by

webapps/docs/config/http.xml

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -184,6 +184,21 @@
184184
exceed the limit.</p>
185185
</attribute>
186186

187+
<attribute name="maxPartCount" required="false">
188+
<p>The maximum total number of parts permitted in a request where the
189+
content type is <code>multipart/form-data</code>. This limit is in
190+
addition to <code>maxParameterCount</code>. Requests that exceed this
191+
limit will be rejected. A value of less than 0 means no limit. If not
192+
specified, a default of 10 is used.</p>
193+
</attribute>
194+
195+
<attribute name="maxPartHeaderSize" required="false">
196+
<p>The maximum number of header bytes permitted per part in a request
197+
where the content type is <code>multipart/form-data</code>. Requests that
198+
exceed this limit will be rejected. A value of less than 0 means no limit.
199+
If not specified, a default of 512 is used.</p>
200+
</attribute>
201+
187202
<attribute name="maxPostSize" required="false">
188203
<p>The maximum size in bytes of the POST which will be handled by
189204
the container FORM URL parameter parsing. The limit can be disabled by

webapps/docs/config/http2.xml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -240,6 +240,8 @@
240240
<li>maxHttpHeaderSize</li>
241241
<li>maxHttpRequestHeaderSize</li>
242242
<li>maxParameterCount</li>
243+
<li>maxPartCount</li>
244+
<li>maxPartHeaderSize</li>
243245
<li>maxPostSize</li>
244246
<li>maxSavePostSize</li>
245247
<li>maxTrailerSize</li>

0 commit comments

Comments
 (0)