From: Herbert R. <he...@wi...> - 2002-06-20 13:47:19
|
hello everyone, I've been developing an application which uses Net::LDAP. In my testing environment, everything was fine. When we moved the application to the production environement, the connection to the LDAP-server would fail after a while. The reason is a check-point firewall, which disconnects idle tcp/ip sessions after a given time. Needless to say, my LDAP-connection can be idle for hours (especially in the night-hours), but for performance reasons it is required that the connection is not being dropped. I've looked into Net/LDAP.pm and found a small and easy solution: just use keepalive-sockets. My patch just adds two lines of perl code to Net/LDAP.pm: 116 sub _connect { 117 my ($ldap, $host, $arg) = @_; 118 119 $ldap->{net_ldap_socket} = IO::Socket::INET->new( 120 PeerAddr => $host, 121 PeerPort => $arg->{port} || '389', 122 Proto => 'tcp', 123 Timeout => defined $arg->{timeout} 124 ? $arg->{timeout} 125 : 120 126 ); ++ 127 $ldap->{net_ldap_socket}->sockopt(SO_KEEPALIVE,1) ++ 128 if defined $arg->{keepalive}; 129 130 } In the main-program, all you do is specifiyng "keepalive=>1" when issuing a new(): : $ldap = Net::LDAP->new( $LDAP_host, : port => $LDAP_port, : timeout => $ldap_connect_timeout, : keepalive => 1); That's it! Now the firewall doesnt kill my ldap-server-connection anymore. Ah, and of course, you also have to configure the tcp/ip keepalive settings systemwide. In linux, which is the OS we use for that task, tcp-keepalive- configuration can be tuned via the proc-filessystem. There are three files to make use of that: bash-2.03# cd /proc/sys/net/ipv4/ bash-2.03# ls -l tcp_keepalive_* -rw-r--r-- 1 root root 0 Jun 20 13:34 tcp_keepalive_intvl -rw-r--r-- 1 root root 0 Jun 20 13:34 tcp_keepalive_probes -rw-r--r-- 1 root root 0 Jun 20 13:34 tcp_keepalive_time o) in "tcp_keepalive_time", set a value after which the tcp-stack should sends keepalive-packets when the connection is idle. o) in "tcp_keepalive_intvl", specify the frequency in which keepalive- packets are sent, once the connection is idle and "tcp_keepalive_time" has exceeded. o) in "tcp_keepalive_probes", specify after how many unsuccessful keepalive-packets (= sent, but no response) the connect is declared dead. e.g., from our "/etc/rc.d/boot.local": # cat /etc/rc.d/boot.local ... echo 45 > /proc/sys/net/ipv4/tcp_keepalive_intvl echo 2 > /proc/sys/net/ipv4/tcp_keepalive_probes echo 1800 > /proc/sys/net/ipv4/tcp_keepalive_time this means: if there is no ldap traffic for more then 1800 seconds = 30 minutes (connect declared "idle"), start sending keep-alive packets. continue sending keep-alive packets each 45 seconds, if the connection remains idle. terminate connection if more than 2 keep-alive requests do not get a response back. the checkpoint-firewall kicks idle connections after 1 hour (3600 seconds), so I chose just halfe the idle time for sending these keepalives. please accept this patch, so we don't have to patch our perl-package each time we install a machine! thank you in advance, herbert -- Dipl.-Ing. Herbert Rosmanith Code Grinder Tiscali Oesterreich GmbH Schillerstr. 53, A-4020 Linz +43 732 610961 / 76 her...@at... |
From: Chris R. <chr...@me...> - 2002-06-21 09:32:49
|
Herbert Rosmanith <he...@wi...> wrote: > > > hello everyone, > > I've been developing an application which uses Net::LDAP. In my testing > environment, everything was fine. When we moved the application to the > production environement, the connection to the LDAP-server would fail > after a while. The reason is a check-point firewall, which disconnects > idle tcp/ip sessions after a given time. Needless to say, my > LDAP-connection can be idle for hours (especially in the night-hours), > but for performance reasons it is required that the connection is not > being dropped. > > I've looked into Net/LDAP.pm and found a small and easy solution: > just use keepalive-sockets. My patch just adds two lines of perl > code to Net/LDAP.pm: > > 116 sub _connect { > 117 my ($ldap, $host, $arg) = @_; > 118 > 119 $ldap->{net_ldap_socket} = IO::Socket::INET->new( > 120 PeerAddr => $host, > 121 PeerPort => $arg->{port} || '389', > 122 Proto => 'tcp', > 123 Timeout => defined $arg->{timeout} > 124 ? $arg->{timeout} > 125 : 120 > 126 ); > ++ 127 $ldap->{net_ldap_socket}->sockopt(SO_KEEPALIVE,1) > ++ 128 if defined $arg->{keepalive}; > 129 > 130 } > > In the main-program, all you do is specifiyng "keepalive=>1" when > issuing a new(): > > : $ldap = Net::LDAP->new( $LDAP_host, > : port => $LDAP_port, > : timeout => $ldap_connect_timeout, > : keepalive => 1); > That looks OK to me. Cheers, Chris |
From: Graham B. <gb...@po...> - 2002-06-21 09:59:07
|
On Fri, Jun 21, 2002 at 10:34:36AM +0100, Chris Ridd wrote: > > 116 sub _connect { > > 117 my ($ldap, $host, $arg) = @_; > > 118 > > 119 $ldap->{net_ldap_socket} = IO::Socket::INET->new( > > 120 PeerAddr => $host, > > 121 PeerPort => $arg->{port} || '389', > > 122 Proto => 'tcp', > > 123 Timeout => defined $arg->{timeout} > > 124 ? $arg->{timeout} > > 125 : 120 > > 126 ); > > ++ 127 $ldap->{net_ldap_socket}->sockopt(SO_KEEPALIVE,1) > > ++ 128 if defined $arg->{keepalive}; > > 129 > > 130 } > > That looks OK to me. I am not so sure. Other than the defined should not be there as it means keepalive => 0 will do the same as keepalive => 1 which is not right IMO. But Net::LDAP does not hide the socket away, it is avaliable via a method for this reason. I dont want to cram _connect with all possible options that people may want. In this case the author could just as easily do $ldap = Net::LDAP->new(...); $ldap->socket->sockopt(SO_KEEPALIVE,1); Graham. |
From: Herbert R. <he...@wi...> - 2002-06-21 10:02:52
|
> But Net::LDAP does not hide the socket away, it is avaliable via a method aha. didnt know that. that's not documented in Net::LDAP manpage. > for this reason. I dont want to cram _connect with all possible options that > people may want. In this case the author could just as easily do > > $ldap = Net::LDAP->new(...); > $ldap->socket->sockopt(SO_KEEPALIVE,1); ok to me if you guarantee that $ldap->socket won't be removed (I assume it will stay). please $ldap->socket to manpage and demonstrate a possible use if it (e.g. by turning on keepalives). thanks, /herp > Graham. > |