cancel
Showing results for 
Search instead for 
Did you mean: 
Login & Join the DevCentral Connects Group to watch the Recorded LiveStream (May 12) on Basic iControl Security - show notes included.

HTTP collect not working when POST is multiple TCP segments

Lorn
Nimbostratus
Nimbostratus

When attempting to collect and parse data from the payload of an HTTP post, the HTTP collect command fails to gather any data when the HTTP request is across multiple TCP segments. If the HTTP request is a single TCP segment it works fine. Is this expected behavior and is there a workaround?

 

 

when HTTP_REQUEST {

 

if {[HTTP::header "Content-Length"] ne "" && [HTTP::header "Content-Length"] <= 1000}{

 

set content_length [HTTP::header "Content-Length"]

 

} else {

 

set content_length 1000

 

}

 

log local0.info "Content Length = $content_length"

 

if { $content_length > 0}{

 

log local0.info "Begin http collect content Length is $content_length"

 

HTTP::collect $content_length

 

if { [HTTP::payload] eq ""}{

 

log local0.info "No Payload"

 

HTTP::release

 

}

 

}

 

}

 

when HTTP_REQUEST_DATA {

 

log local0.info "Begin http request data"

 

set payload [HTTP::payload]

 

log local0.info "$payload"

 

}

 

4 REPLIES 4

Kevin_Stewart
F5 Employee
F5 Employee
First, I think you may be setting your payload length to an arbitrarily small number for POST data.

 

 

Second, you can use the HTTP::collect command within the HTTP_REQUEST_DATA event to iteratively collect all of the rest of the payload. Take a look at this codeshare example:

 

 

https://devcentral.f5.com/wiki/iRules.HTTPPayloadCollection.ashx

 

Lorn
Nimbostratus
Nimbostratus

Thanks for the response. The data I'm collecting is in the first 200 bytes of payload data. I'm only collecting request data from an HTTP POST. The messages are small and rarely get segmented into more than one TCP segment. However, when the data is within two TCP segments (single HTTP message but 2 TCP segments due to small MTU on a device in the path), after executing HTTP::collect in the HTTP_REQUEST event, it collects 0 bytes and therefore the HTTP_REQUEST_DATA event does not seem to be triggering. I've also opened a case with F5 but was hoping someone else may have come across this.

 

nitass
F5 Employee
F5 Employee
it seems you have already found the problem.

 

 

regarding potential ddos attack, is this article usable?

 

 

Mitigating Slow HTTP Post DDoS Attacks With iRules – Follow-up by George Watkins

 

https://devcentral.f5.com/tech-tips/articles/mitigating-slow-http-post-ddos-attacks-with-irules-ndash-follow-up

Lorn
Nimbostratus
Nimbostratus
Yes, the issue was trying to collect more payload data than existed when a content length wasn't specified. I changed the irule to only collect data when a content length header was present, however that brings up the potential DDoS attack where an attacker could arbitrarily set a content length header causing the session to stay open until the idle timeout expires. The link you provided to prevent this looks promising.

 

 

Thank you.