Thanks for reply. You are right about clean up, but is there cleaner way to 
timeout the connection? 
My application is single threaded and can't afford to block and wait too long 
on connect (which it does if I don't raise an alarm).

Thanks,
J


-----Original Message-----
From: Hendrik Schumacher [mailto:h...@activeframe.de]
Sent: Thu 1/15/2009 4:00 AM
To: Martin Gainty
Cc: Jaya Meghani; dbi-users@perl.org
Subject: RE: DBI connect and ports issue
 
Just an idea:

You raise an alarm when DBD::Oracle/OCI takes too long waiting for a
connection. If you just quit the connection attempt then, OCI may never
have a chance to clean up its connection attempt (especially the opened
UDP port).

Am Do, 15.01.2009, 04:01, schrieb Martin Gainty:
>
> Jaya-
>
> Port 1526 sounds odd as the default port for oracle is 1521
>
> Anyone see anything obvious?
> Martin
> ______________________________________________
> Disclaimer and confidentiality note
> Everything in this e-mail and any attachments relates to the official
> business of Sender. This transmission is of a confidential nature and
> Sender does not endorse distribution to any party other than intended
> recipient. Sender does not necessarily endorse content contained within
> this transmission.
>
>
>
>
>> Subject: DBI connect and ports issue
>> Date: Wed, 14 Jan 2009 16:31:12 -0500
>> From: jaya.megh...@vonage.com
>> To: dbi-users@perl.org
>>
>> Hi,
>>
>>
>>
>>
>>
>> My first post too the list!
>>
>>
>>
>> First some environment details:
>>
>> Red Hat Enterprise Linux WS release 4 (Nahant Update 4)
>>
>> Perl Version = 5.008007
>>
>> DBI Version = 1.48
>>
>> DBD::Oracle Version = 1.16
>>
>> Issue:
>>
>> My application connects to Oracle and some times the DB host is down. I
>> use sigaction to put a timeout on DBI->connect and retry again till
>> connection is established.
>>
>> The problem is: I see a lot of unused ports for the application process.
>>
>> 1). TCP ports in CLOSE_WAIT and ESTABLISHED states.
>>
>> 2). Ephemeral UDP ports.
>>
>> These ports accumulate over time as DB connection is lost and
>> re-established.
>>
>> I use lsof and netstat commands to check the stats on ports.
>>
>>
>>
>> To reproduce the issue I have this script (see below), I don't see any
>> TCP ports waiting in CLOSE_WAIT and ESTABLISHED states but each time the
>> script tries to connect (and is timed-out) a new ephemeral UDP port is
>> created.
>>
>> I use iptables to DROP any packets to DB host to simulate DB host down
>> scenario.
>>
>> ************************************************************************
>> ******
>>
>> Output:
>>
>> Here is the output of script and Port stats:
>>
>>
>>
>> $perl sigTry.perl
>>
>> I am in handler
>>
>> Trying to connect
>>
>> Error connecting to DB
>>
>> I out of handler
>>
>> <Hit Return key>
>>
>> I am in handler
>>
>> Trying to connect
>>
>> Error connecting to DB
>>
>> I out of handler
>>
>> <Hit Return key>
>>
>> I am in handler
>>
>> Trying to connect
>>
>> Error connecting to DB
>>
>> I out of handler
>>
>> #Command to see ports stats
>>
>> $lsof -p `pgrep perl` | egrep "TCP|UDP"
>>
>> perl    28572 jmeghani    4u  IPv4 2132909             UDP
>> localhost:33544
>>
>> perl    28572 jmeghani    5u  IPv4 2132913             TCP host1:33466->
>> someDBhost:1526 (SYN_SENT)
>>
>> perl    28572 jmeghani    7u  IPv4 2132924             UDP
>> localhost:33545
>>
>> perl    28572 jmeghani    8u  IPv4 2132926             TCP host1->
>> someDBhost:1526 (SYN_SENT)
>>
>> perl    28572 jmeghani   10u  IPv4 2132927             UDP
>> localhost:33546
>>
>> perl    28572 jmeghani   11u  IPv4 2132929             TCP
>> host1:33468->someDBhost:1526 (SYN_SENT)
>>
>> SYN_SENT ports go away with time but UDP ports (33544-33546) don't.
>>
>> ************************************************************************
>> ******
>>
>> Finally actual script (I have removed actual DB details)
>>
>> Script:
>>
>> ************************************************************************
>> ******
>>
>> $ENV{ORACLE_HOME} = '/usr/vendor/pkg/oracle/product/10.2.0';
>>
>> use strict;
>>
>> use warnings;
>>
>> use POSIX;
>>
>> use DBI;
>>
>> my $db_hostname = 'someDBhost';
>>
>> my $db_port = 1526;
>>
>> my $db_user = 'test';
>>
>> my $db_pass = 'test';
>>
>> my $db_sid = 'SID';
>>
>> my $dbh = undef;
>>
>> sub finished {
>>
>>         print "I am outta here\n";
>>
>>         exit(1);
>>
>> }
>>
>> sub handler {
>>
>>         print "I am in handler\n";
>>
>>         if (!defined($dbh)) {
>>
>>                 print "Trying to connect\n";
>>
>>                 my $old_action = POSIX::SigAction->new();
>>
>>                 my $action = POSIX::SigAction->new( sub{die 'TIMEOUT';
>> });
>>
>>                 sigaction(SIGALRM,$action, $old_action);
>>
>>                 my $old_t;
>>
>>                 eval {
>>
>>                         sigprocmask(SIG_UNBLOCK,
>> POSIX::SigSet->new(SIGALRM));
>>
>>                         $old_t = alarm(2);
>>
>>                         $dbh =
>> DBI->connect("dbi:Oracle:host=$db_hostname;sid=$db_sid;port=$db_port",
>>
>>                                             $db_user, $db_pass,
>>
>>                                     {PrintError => 0, RaiseError => 1,
>> AutoCommit => 0});
>>
>>                         alarm(0);
>>
>>                         print "I am connected\n";
>>
>>                 };
>>
>>         alarm(0);
>>
>>         sigaction(SIGALRM, $old_action);
>>
>>         alarm($old_t);
>>
>>         if ($@) {
>>
>>                 if(defined($dbh)){
>>
>>                         print "dbh was defined\n";
>>
>>                         $dbh=undef;
>>
>>                 }
>>
>>                 print("Error connecting to DB\n");
>>
>>         }
>>
>>       }
>>
>>       else {
>>
>>                 print "Already connected\n";
>>
>>         }
>>
>>         print "I out of handler\n";
>>
>> }
>>
>> sub main {
>>
>>         my $action_die = POSIX::SigAction->new(\&finished);
>>
>>         sigaction(SIGINT,$action_die);
>>
>>         my $old_action = POSIX::SigAction->new();
>>
>>         my $action = POSIX::SigAction->new(\&handler);
>>
>>         sigaction(SIGALRM,$action,$old_action);
>>
>>         while(1)
>>
>>         {
>>
>>                 alarm(3);
>>
>>                 my $foo = <STDIN>;
>>
>>         }
>>
>> }
>>
>> exit(main());
>>
>> **********************************************************************
>>
>>
>>
>> If you are still reading ;) any help is greatly appreciated.
>>
>>
>>
>>
>>
>> Jaya
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>>
>
> _________________________________________________________________
> Windows Live*: Keep your life in sync.
> http://windowslive.com/howitworks?ocid=TXT_TAGLM_WL_t1_allup_howitworks_012009



Reply via email to