Skip to Content.
Sympa Menu

freetds - RE: [freetds] timeout

freetds AT lists.ibiblio.org

Subject: FreeTDS Development Group

List archive

Chronological Thread  
  • From: Kent Scott <kscott AT logicalsi.com>
  • To: freetds AT lists.ibiblio.org
  • Subject: RE: [freetds] timeout
  • Date: Thu, 08 Jan 2004 18:39:51 -0500


> My biggest problem stems from the fact that if a connection
> is made and
> then lost while trying to run queries (in php) I seem to hang
> indefinitely until the connection comes back.

It fails even in tsql, right?

Yes, even in tsql.


> [good analysis]
...
> What is supposed to be the difference between
> query_timeout and timeout in connect_info?

There are two timeout settings:

1. How long should we wait before we decide there's no server to connect
to?
2. How long should we let a query run before we give up on it?

By default, afaict, all libraries specify no query timeout i.e., they wait
indefinitely, which is what you're bumping into. You'd like to be able to
specify one.

We have not two but four (!):

$ sed -ne'/tds_connect_info/,/}/p' include/tds.h \
|egrep -i 'time|info'
typedef struct tds_connect_info
TDS_INT connect_timeout;
TDS_INT query_timeout;
TDS_INT longquery_timeout;
int timeout;
} TDSCONNECTINFO;

I'm not sure what "timeout" governs (probably queries, once upon a time,
almost), nor longquery_timeout. I suspect axing the "timeout" member would
be a good first step.

Ok, now I know a general direction to look at. Here are my thoughts based off what I have seen so far - and you can correct me where I may be off. The connection timeout (connect_info->connect_timeout) seems to have the most implementation in place. There seems to be 3 ways to set its value - tds_parse_conf_section(), dbsetlogintime(), and tds_set_timeouts(). The first of those 3 is obvious - my guess from the other 2 was that they were set up to be called either by the programmer in the code or by any other language (such as PHP) during an initialization routine? In fact, I had thought that query_timeout might work under the same principles (as the connect timeout). I did notice that PHP does attempt to call dbsettime() except that it isn't implemented yet. The only part that was throwing me off was that tds_parse_conf_section() was looking for and setting timeout and not query_timeout. Would it make sense then to implement dbsettime() to act like dbsetlogintime() for query_timeout as well as to parse freetds.conf for the value?

If so, during tdsdbopen(), it would first look to freetds.conf for any settings and then it would check if something was set calling dbsettime().


We could use some help with this. I think timeout logic is _at best_
muddled in libtds, partly because the APIs' control over them is quite
varied. For reference, I've enumerated them below. In addition, timeouts
interact with error handling, itself both nontrivial and rather shakily
supported in FreeTDS.

To support all of the permutations correctly looks to me to be a big
undertaking, even once the problem is completely understood. Getting any
one of them to work correctly, given the mix of error handling and socket
programming, won't be easy, even if it's not rocket science. As you can
see, it's a matter of conveying the timeout value from freetds.conf (or the
API) to goodread(), getting goodread() to call the error handler, and
retrying/aborting as appropriate. Piece of cake, for the right guy.

I do believe that goodread() needs to be slightly modified for the query_timeout to work. It goes in to a do..while loop if the timeout is set and exits if the time passes (this part works fine). However, the very next thing it does after exiting the loop is to call READSOCKET() where it still hangs. We would need to test if the socket is dead or something and return instead.

As for error handling - I was hoping to avoid looking in to that - although I do need it. I will start trying to get at least a little familiar with it. Just give me your thoughts.


Kent





Archive powered by MHonArc 2.6.24.

Top of Page