version 1.49, 2003/09/26 19:04:06
|
version 1.53, 2003/10/05 15:36:03
|
|
|
else | else |
{ | { |
// set status to DYING | // set status to DYING |
_entries[indx]._status.value() == _MonitorEntry::DYING; |
_entries[indx]._status = _MonitorEntry::DYING; |
} | } |
} | } |
} | } |
|
|
_stopConnections = 0; | _stopConnections = 0; |
} | } |
| |
|
Uint32 _idleEntries = 0; |
|
|
for( int indx = 0; indx < (int)_entries.size(); indx++) | for( int indx = 0; indx < (int)_entries.size(); indx++) |
{ | { |
if(_entries[indx]._status.value() == _MonitorEntry::IDLE) | if(_entries[indx]._status.value() == _MonitorEntry::IDLE) |
{ | { |
|
_idleEntries++; |
FD_SET(_entries[indx].socket, &fdread); | FD_SET(_entries[indx].socket, &fdread); |
} | } |
} | } |
| |
|
_entry_mut.unlock(); |
int events = select(FD_SETSIZE, &fdread, NULL, NULL, &tv); | int events = select(FD_SETSIZE, &fdread, NULL, NULL, &tv); |
|
_entry_mut.lock(pegasus_thread_self()); |
| |
#ifdef PEGASUS_OS_TYPE_WINDOWS | #ifdef PEGASUS_OS_TYPE_WINDOWS |
if(events && events != SOCKET_ERROR ) |
if(events == SOCKET_ERROR) |
#else | #else |
if(events && events != -1 ) |
if(events == -1) |
#endif | #endif |
{ | { |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"Monitor::run - errorno = %d has occurred on select.", errno); |
|
// The EBADF error indicates that one or more or the file |
|
// descriptions was not valid. This could indicate that |
|
// the _entries structure has been corrupted or that |
|
// we have a synchronization error. |
|
|
|
PEGASUS_ASSERT(errno != EBADF); |
|
} |
|
else if (events) |
|
{ |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"Monitor::run select event received events = %d, monitoring %d idle entries", |
|
events, _idleEntries); |
for( int indx = 0; indx < (int)_entries.size(); indx++) | for( int indx = 0; indx < (int)_entries.size(); indx++) |
{ | { |
if(FD_ISSET(_entries[indx].socket, &fdread)) |
// The Monitor should only look at entries in the table that are IDLE (i.e., |
|
// owned by the Monitor). |
|
if((_entries[indx]._status.value() == _MonitorEntry::IDLE) && |
|
(FD_ISSET(_entries[indx].socket, &fdread))) |
{ | { |
MessageQueue *q = MessageQueue::lookup(_entries[indx].queueId); | MessageQueue *q = MessageQueue::lookup(_entries[indx].queueId); |
if(q == 0) |
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
{ |
"Monitor::run indx = %d, queueId = %d, q = %p", |
try |
indx, _entries[indx].queueId, q); |
{ |
PEGASUS_ASSERT(q !=0); |
_entries[indx]._status = _MonitorEntry::EMPTY; |
|
} |
|
catch(...) |
|
{ |
|
| |
} |
|
continue; |
|
} |
|
try | try |
{ | { |
if(_entries[indx]._type == Monitor::CONNECTION) | if(_entries[indx]._type == Monitor::CONNECTION) |
{ | { |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"_entries[indx].type for indx = %d is Monitor::CONNECTION", indx); |
static_cast<HTTPConnection *>(q)->_entry_index = indx; | static_cast<HTTPConnection *>(q)->_entry_index = indx; |
if(static_cast<HTTPConnection *>(q)->_dying.value() > 0 ) | if(static_cast<HTTPConnection *>(q)->_dying.value() > 0 ) |
{ | { |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"Monitor::run processing dying value > 0 for indx = %d, connection being closed.", |
|
indx); |
_entries[indx]._status = _MonitorEntry::DYING; | _entries[indx]._status = _MonitorEntry::DYING; |
MessageQueue & o = static_cast<HTTPConnection *>(q)->get_owner(); | MessageQueue & o = static_cast<HTTPConnection *>(q)->get_owner(); |
Message* message= new CloseConnectionMessage(_entries[indx].socket); | Message* message= new CloseConnectionMessage(_entries[indx].socket); |
|
|
} | } |
else | else |
{ | { |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"Non-connection entry, indx = %d, has been received.", indx); |
int events = 0; | int events = 0; |
events |= SocketMessage::READ; | events |= SocketMessage::READ; |
Message *msg = new SocketMessage(_entries[indx].socket, events); | Message *msg = new SocketMessage(_entries[indx].socket, events); |
|
|
| |
PEG_METHOD_ENTER(TRC_HTTP, "Monitor::solicitSocketMessages"); | PEG_METHOD_ENTER(TRC_HTTP, "Monitor::solicitSocketMessages"); |
| |
int index = -1; |
|
_entry_mut.lock(pegasus_thread_self()); | _entry_mut.lock(pegasus_thread_self()); |
| |
for(index = 0; index < (int)_entries.size(); index++) |
for(int index = 0; index < (int)_entries.size(); index++) |
{ | { |
try | try |
{ | { |
|
|
} | } |
_entry_mut.unlock(); | _entry_mut.unlock(); |
PEG_METHOD_EXIT(); | PEG_METHOD_EXIT(); |
return index; |
return -1; |
} | } |
| |
void Monitor::unsolicitSocketMessages(Sint32 socket) | void Monitor::unsolicitSocketMessages(Sint32 socket) |
{ | { |
|
|
PEG_METHOD_ENTER(TRC_HTTP, "Monitor::unsolicitSocketMessages"); | PEG_METHOD_ENTER(TRC_HTTP, "Monitor::unsolicitSocketMessages"); |
_entry_mut.lock(pegasus_thread_self()); | _entry_mut.lock(pegasus_thread_self()); |
| |
|
|
if(_entries[index].socket == socket) | if(_entries[index].socket == socket) |
{ | { |
_entries[index]._status = _MonitorEntry::EMPTY; | _entries[index]._status = _MonitorEntry::EMPTY; |
|
_entries[index].socket = -1; |
break; | break; |
} | } |
} | } |
|
|
PEGASUS_THREAD_RETURN PEGASUS_THREAD_CDECL Monitor::_dispatch(void *parm) | PEGASUS_THREAD_RETURN PEGASUS_THREAD_CDECL Monitor::_dispatch(void *parm) |
{ | { |
HTTPConnection *dst = reinterpret_cast<HTTPConnection *>(parm); | HTTPConnection *dst = reinterpret_cast<HTTPConnection *>(parm); |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"Monitor::_dispatch: entering run() for indx = %d, queueId = %d, q = %p", |
|
dst->_entry_index, dst->_monitor->_entries[dst->_entry_index].queueId, dst); |
|
try |
|
{ |
dst->run(1); | dst->run(1); |
if( dst->_monitor->_entries.size() > (Uint32)dst->_entry_index ) |
} |
dst->_monitor->_entries[dst->_entry_index]._status = _MonitorEntry::IDLE; |
catch (...) |
|
{ |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"Monitor::_dispatch: exception received"); |
|
} |
|
Tracer::trace(TRC_HTTP, Tracer::LEVEL4, |
|
"Monitor::_dispatch: exited run() for index %d", dst->_entry_index); |
|
|
|
dst->_monitor->_entry_mut.lock(pegasus_thread_self()); |
|
// It shouldn't be necessary to set status = _MonitorEntry::IDLE |
|
// if the connection is being closed. However, the current logic |
|
// in Monitor::run requires this value to be set for the close |
|
// to be processed. |
| |
|
PEGASUS_ASSERT(dst->_monitor->_entries[dst->_entry_index]._status.value() == _MonitorEntry::BUSY); |
|
dst->_monitor->_entries[dst->_entry_index]._status = _MonitorEntry::IDLE; |
|
if (dst->_connectionClosePending) |
|
{ |
|
dst->_dying = 1; |
|
} |
|
dst->_monitor->_entry_mut.unlock(); |
return 0; | return 0; |
} | } |
| |