[Zope] asyncore+Zope: different behavior in Windows and Linux

Dmitry Dembinsky dmitry at deluxoft.com
Thu Aug 14 19:32:31 EDT 2003


Hello Zopers,

I currently develop a Zope product, part of which will handle incoming
TCP connections.
To avoid multithreading, I intended to use asyncore module.

ZServer already runs asyncore.loop(), so the idea was to put a server
socket 
to a global asyncore.socket_map to have it checked for network events in
a main ZServer loop
and trigger overriden handle_* methods.

To prove the concept, I created a very small test product (see the code
below).

Outside of Zope the code works fine on both Linux and Windows
When running as Zope product it still works on Windows, 
but on Linux causes Zope to crash with the following traceback:

-------------------------------------------------------------
Traceback (most recent call last):
  File "/usr/local/zope/z2.py", line 910, in ?
    asyncore.loop()
  File "/usr/local/zope/lib/python/ThreadedAsync/LoopCallback.py", line
150, in loop
    poll_fun(timeout, map)
  File "/usr/local/zope/lib/python/ThreadedAsync/LoopCallback.py", line
102, in poll
    r, w, e = select.select(r, w, e, timeout)
select.error: (9, 'Bad file descriptor')
-------------------------------------------------------------

My guess is that somehow, closed socket descriptor is not removed from
the socket_map causing select() function to fail.
(In this case I assume that there's a problem with Zserver)

I searched bug collector and mail archives but didn't find any relevant
information.
Any ideas, please?


My working environment:
-------------------
Windows: 
  OS: Windows XP Profesional SP1
  Zope Version:  (Zope 2.6.1 (binary release, python 2.1, win32-x86),
python 2.1.3, win32)  
  Python Version:  2.1.3 (#35, Apr 8 2002, 17:47:50) [MSC 32 bit
(Intel)]  

Linux:
  OS: RedHat 7.2, kernel 2.4.20-19.7
  Zope Version: (Zope 2.6.1 (binary release, python 2.1, linux2-x86),
python 2.1.3, linux2)
  Python Version: 2.1.3 (#1, Sep 19 2002, 13:15:46) [GCC egcs-2.91.66
19990314/Linux (egcs-1.1.2 release)] 


Below is the code of the test product:

File __init__.py:
--------------------------------------------------------------
import socket
import asyncore

class AsyncTestDispatcher( asyncore.dispatcher ):
  def start ( self ):
    self.create_socket( socket.AF_INET, socket.SOCK_STREAM )
    tAddr = ( '0.0.0.0', 1234 )
    self.bind( tAddr )
    self.listen( 1 )
    print self.__class__.__name__, "listening on %s:%d" % tAddr

  def stop ( self ):
    self.close()
    print self.__class__.__name__, "stopped"

_g_oDisp = None

def start ():
  print 'AsyncTest: starting'
  global _g_oDisp
  _g_oDisp = AsyncTestDispatcher()
  _g_oDisp.start ()
  
def stop():
  print 'AsyncTest: stopping'
  global _g_oDisp
  _g_oDisp.stop()
  _g_oDisp = None

# Zope staff
__roles__ = None
__allow_access_to_unprotected_subobjects__ = 1

def initialize( context ):
  print 'AsyncTest initialized'
--------------------------------------------------------------

I put AsyncTest in a Products directory within my Zope installation,
started Zope
and created 2 python scripts via ZMI:

asyncstart:
--------------------------------------------------------------
from Products.AsyncTest import start
start ()
print "AsyncTest started"
return printed
--------------------------------------------------------------

asyncstop:
--------------------------------------------------------------
from Products.AsyncTest import stop
stop ()
print "AsyncTest stopped"
return printed
--------------------------------------------------------------

Then I run asyncstart and asyncstop number of times
Usually the crash happened on the first or the second iteration, always
in stop() function:

start -> stop -> crash (during stop)
start -> stop -> start -> stop -> crash (during stop)

in a rare cases there were 3-4 times before the crash

Thanks in advance,
Dmitry




More information about the Zope mailing list