Learn F5 Technologies, Get Answers & Share Community Solutions Join DevCentral

Filter by:
  • Solution
  • Technology
Answers

Logging FTP access data (with NETed FTP virtual serveur)


Hi,

Due to some constraints i had to setup an FTP virtual serveur on an bigip,
using SNAT. However this has a limitation, the end server cannot see the real
source IP.

So, using ideas from the different Log* samples and the passive_ftps_in_ccc_mode iRule,
I'm trying to cook an access log iRule.

My problem is that whenever i add TCP::collect to the CLIENT_ACCEPTED event the ftp connection fail
(the client is connected but there is no response from the F5)

here is what i've got now, any idea ?

when CLIENT_ACCEPTED {   
set vip [IP::local_addr]:[TCP::local_port]
set user "unknown"
TCP::collect
}

when SERVER_CONNECTED {
set client "[IP::client_addr]:[TCP::client_port]"
set node "[IP::server_addr]:[TCP::server_port]"
set inside "[serverside {IP::local_addr}]:[serverside {TCP::local_port}]"
}

when CLIENT_CLOSED {
# log connection info
log local0. "FTP connection from $client. Mapped to $inside -> $node, user $user"
}

when CLIENT_DATA {
# check if payload contains the string we want to replace
if { [TCP::payload] contains "USER" }
{
# use a regular expression to save the user name
regexp "USER \(\[a-zA-Z0-9]+)" [TCP::payload] all user

# release the packet, and end collection
TCP::release
}
else
{
# release the packet, and collect a new one
TCP::release
TCP::collect
}
}
0
Rate this Question

Answers to this Question

placeholder+image
USER ACCEPTED ANSWER & F5 ACCEPTED ANSWER

Could it be that the session is put on hold due to the TCP::collect while the client is waiting from the server
to answer so it can't speak ?
0
placeholder+image
USER ACCEPTED ANSWER & F5 ACCEPTED ANSWER
Yep, looks like it's more like this:

when CLIENT_ACCEPTED {   
set vip [IP::local_addr]:[TCP::local_port]
set user "unknown"
# TCP::collect
}

when SERVER_CONNECTED {
set client "[IP::client_addr]:[TCP::client_port]"
set node "[IP::server_addr]:[TCP::server_port]"
set inside "[serverside {IP::local_addr}]:[serverside {TCP::local_port}]"

TCP::collect
}

when SERVER_DATA {
TCP::release
clientside { TCP::collect }
}

when CLIENT_DATA {
log local0. "[IP::client_addr]:[TCP::client_port]: collected payload ([TCP::payload length]): [TCP::payload]"

# check if payload contains the string we want to replace
if { [TCP::payload] contains "USER" }
{
# use a regular expression to save the user name
regexp "USER \(\[a-zA-Z0-9]+)" [TCP::payload] all user

# log connection info
log local0. "FTP connection from $client. Mapped to $inside -> $node, user $user"
TCP::release
return
}
else {
# release the packet, and collect a new one
TCP::release
TCP::collect
}
}
0
placeholder+image
USER ACCEPTED ANSWER & F5 ACCEPTED ANSWER
Hello Everyone,

I've gone ahead and added this to the code share at the following link:


I've changed some changes to the packet collection and instead of having it return, I've had it continue collecting to capture a larger spread. It also gave me the ability to watch multiple login/logout FTP commands for tracking. Without this change only the initial login is caught and the user would be able to logout and back in with another username.
0
placeholder+image
USER ACCEPTED ANSWER & F5 ACCEPTED ANSWER
Awesome, thanks for the codeshare submission, much appreciated. :)

#Colin
0