Randy Kobes wrote:
On Fri, 8 Apr 2005, Stas Bekman wrote:


eval block has failed: APR::Socket::recv: (730035) A
non-blocking socket operation could not be completed
immediately.  at
C:\\apache2\\source\\mod_perl-2.0\\t\\response/TestError/runtime.pm
line 156 at
C:\\apache2\\source\\mod_perl-2.0\\t\\response/TestError/runtime.pm
line 114.\n

1) I suppose 730035 is not APR::Const::EAGAIN, so it
doesn't retry as the test goes. Or does it? Try printing:

[ ... ]

so, it looks again the same issue. You are probably
getting a different $@ under windows.

I guess we could find out what is that constant, or try to
use a different operation that will certainly fail and
it'll give the same error constant on all platforms.
Suggestions are welcome.


You're right that the problem is is that a different $@
(730035) is obtained, rather than APR::Const::EAGAIN (which
is 11 on Win32). On linux, I get 11 for both $@ and
APR::Const::EAGAIN on this test.

I think getting 730035 can be understood as follows:
in apr_errorno.h, there's a macro

#define APR_STATUS_IS_EAGAIN(s)         ((s) == APR_EAGAIN \
                || (s) == APR_OS_START_SYSERR + ERROR_NO_DATA \
                || (s) == APR_OS_START_SYSERR + SOCEWOULDBLOCK \
                || (s) == APR_OS_START_SYSERR + ERROR_LOCK_VIOLATION)


which is the suggested way to test for EAGAIN. On Win32, I believe that SOCEWOULDBLOCK is returned in this test, and following through the definitions in apr_errorno.h: ============================================================= use constant APR_OS_START_ERROR => 20000; use constant APR_OS_ERRSPACE_SIZE => 50000; use constant APR_OS_START_STATUS => (APR_OS_START_ERROR + APR_OS_ERRSPACE_SIZE); use constant APR_OS_START_USERERR => (APR_OS_START_STATUS + APR_OS_ERRSPACE_SIZE); use constant APR_OS_START_USEERR => APR_OS_START_USERERR; use constant APR_OS_START_CANONERR => (APR_OS_START_USERERR + (APR_OS_ERRSPACE_SIZE * 10)); use constant APR_OS_START_EAIERR => (APR_OS_START_CANONERR + APR_OS_ERRSPACE_SIZE); use constant APR_OS_START_SYSERR => (APR_OS_START_EAIERR + APR_OS_ERRSPACE_SIZE); use constant SOCBASEERR => 10000; use constant SOCEWOULDBLOCK => (SOCBASEERR+35); =================================================================== one then finds APR_OS_START_SYSERR + SOCEWOULDBLOCK is indeed 730035, which would cause APR_STATUS_IS_EAGAIN(s) to be true. In the sense of APR_STATUS_IS_EAGAIN(), then, I think the test as written should be considered as having passed on Win32.

So what we could do is, instead of using APR::Const::EAGAIN,
put in a APR_STATUS_IS_EAGAIN() sub based on the above
macro. This has the downside of requiring all the above
constants to be defined within the test, as they're not
available within APR::Const::*.

Thanks for the research, Randy.

How about a simpler solution. Create a new APR::Status class and have IS_EAGAIN function in it. No need to load any constants, as it'll be on the C level. Notice that this issue is essential for all uses, not just to make the test pass.

Later we may need to add other IS_* status checking subs. I see there are quite a lot of those.

--
__________________________________________________________________
Stas Bekman            JAm_pH ------> Just Another mod_perl Hacker
http://stason.org/     mod_perl Guide ---> http://perl.apache.org
mailto:[EMAIL PROTECTED] http://use.perl.org http://apacheweek.com
http://modperlbook.org http://apache.org   http://ticketmaster.com

---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Reply via email to