From: | Bruce Momjian <pgman(at)candle(dot)pha(dot)pa(dot)us> |
---|---|
To: | Manfred Spraul <manfred(at)colorfullife(dot)com> |
Cc: | Tom Lane <tgl(at)sss(dot)pgh(dot)pa(dot)us>, pgsql-hackers(at)postgresql(dot)org |
Subject: | Re: libpq and psql not on same page about SIGPIPE |
Date: | 2004-12-01 15:41:59 |
Message-ID: | 200412011541.iB1FfxK28146@candle.pha.pa.us |
Views: | Raw Message | Whole Thread | Download mbox | Resend email |
Thread: | |
Lists: | pgsql-hackers pgsql-patches |
Manfred Spraul wrote:
> Bruce Momjian wrote:
>
> >Comments? This seems like our only solution.
> >
> >
> >
> This would be a transparent solution. Another approach would be:
> - Use the old 7.3 approach by default. This means perfect backward
> compatibility for single-threaded apps and broken multithreaded apps.
> - Add a new PQinitDB(int disableSigpipeHandler) initialization function.
> Document that multithreaded apps must call the function with
> disableSigpipeHandle=1 and handle SIGPIPE for libpq. Perhaps with a
> reference implementation in libpq (i.e. a sigpipeMode with 0 for old
> approach, 1 for do nothing, 2 for install our own handler).
>
> It would prefer that approach:
> It means that the multithreaded libpq apps must be updated [are there
> any?], but the solution is simpler and less fragile than calling 4
> signal handling function in a row to selectively block SIGPIPE per-thread.
I think we can get away with three function calls because we can check
errno for EPIPE from the send() call. We already have two function
calls in there so I don't see a third as a huge problem and not worth an
API change unless someone tells us it is a performance hit.
One thing I know from the broken 7.4 code is that calling signal() from
inside a thread is very slow on Linux, like a 20% performance hit
because I assume it has to adjust all the threads signal stacks or
something. Anyway, I assume thread_sigmask() and sigpending() are not
huge hits.
In fact, by checking EPIPE from send() we don't need sigpending at all.
We just block and (if EPIPE) clear using sigwait(), then unblock. I
think we can document that if you are blocking SIGPIPE in your
application and wait to handle it later, you can't keep the pending
signal through a libpq call. I think that is a much easier requirement
than adding a new API call. The most common case of SIG_IGN/SIG_DFL is
not affected by this, only cases where they define their own signal
handler, block it, and then trying to keep a call active across a libpq
call.
Manfred, glad you are around to discuss this. After much research I
came up with a method and then found your description that matched it so
I felt I was on the right track.
--
Bruce Momjian | http://candle.pha.pa.us
pgman(at)candle(dot)pha(dot)pa(dot)us | (610) 359-1001
+ If your life is a hard drive, | 13 Roberts Road
+ Christ can be your backup. | Newtown Square, Pennsylvania 19073
From | Date | Subject | |
---|---|---|---|
Next Message | Robert Treat | 2004-12-01 16:05:15 | Re: Error handling in plperl and pltcl |
Previous Message | Robert Treat | 2004-12-01 15:41:05 | Re: Increasing the length of |
From | Date | Subject | |
---|---|---|---|
Next Message | Bruce Momjian | 2004-12-01 17:23:44 | Re: Developer's FAQ update |
Previous Message | Gavin Sherry | 2004-12-01 07:37:51 | Re: Developer's FAQ update |