mirror of
https://github.com/transmission/transmission
synced 2024-12-27 10:07:40 +00:00
(trunk libT) fix connectivity error reported by Stargazer. Also, add more debug statements to track down errors like this in the future
This commit is contained in:
parent
87c1188866
commit
6f8e5352ab
2 changed files with 55 additions and 30 deletions
|
@ -214,6 +214,7 @@ static void
|
||||||
event_read_cb( int fd, short event UNUSED, void * vio )
|
event_read_cb( int fd, short event UNUSED, void * vio )
|
||||||
{
|
{
|
||||||
int res;
|
int res;
|
||||||
|
int e;
|
||||||
tr_peerIo * io = vio;
|
tr_peerIo * io = vio;
|
||||||
|
|
||||||
/* Limit the input buffer to 256K, so it doesn't grow too large */
|
/* Limit the input buffer to 256K, so it doesn't grow too large */
|
||||||
|
@ -235,7 +236,9 @@ event_read_cb( int fd, short event UNUSED, void * vio )
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
errno = 0;
|
||||||
res = evbuffer_read( io->inbuf, fd, howmuch );
|
res = evbuffer_read( io->inbuf, fd, howmuch );
|
||||||
|
e = errno;
|
||||||
|
|
||||||
if( res > 0 )
|
if( res > 0 )
|
||||||
{
|
{
|
||||||
|
@ -251,13 +254,15 @@ event_read_cb( int fd, short event UNUSED, void * vio )
|
||||||
if( res == 0 ) /* EOF */
|
if( res == 0 ) /* EOF */
|
||||||
what |= EVBUFFER_EOF;
|
what |= EVBUFFER_EOF;
|
||||||
else if( res == -1 ) {
|
else if( res == -1 ) {
|
||||||
if( errno == EAGAIN || errno == EINTR ) {
|
if( e == EAGAIN || e == EINTR ) {
|
||||||
tr_peerIoSetEnabled( io, dir, TRUE );
|
tr_peerIoSetEnabled( io, dir, TRUE );
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
what |= EVBUFFER_ERROR;
|
what |= EVBUFFER_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
dbgmsg( io, "event_read_cb got an error. res is %d, what is %hd, errno is %d (%s)", res, what, e, strerror( e ) );
|
||||||
|
|
||||||
if( io->gotError != NULL )
|
if( io->gotError != NULL )
|
||||||
io->gotError( io, what, io->userData );
|
io->gotError( io, what, io->userData );
|
||||||
}
|
}
|
||||||
|
@ -268,13 +273,16 @@ tr_evbuffer_write( tr_peerIo * io, int fd, size_t howmuch )
|
||||||
{
|
{
|
||||||
struct evbuffer * buffer = io->outbuf;
|
struct evbuffer * buffer = io->outbuf;
|
||||||
int n = MIN( EVBUFFER_LENGTH( buffer ), howmuch );
|
int n = MIN( EVBUFFER_LENGTH( buffer ), howmuch );
|
||||||
|
int e;
|
||||||
|
|
||||||
|
errno = 0;
|
||||||
#ifdef WIN32
|
#ifdef WIN32
|
||||||
n = send(fd, buffer->buffer, n, 0 );
|
n = send(fd, buffer->buffer, n, 0 );
|
||||||
#else
|
#else
|
||||||
n = write(fd, buffer->buffer, n );
|
n = write(fd, buffer->buffer, n );
|
||||||
#endif
|
#endif
|
||||||
dbgmsg( io, "wrote %d to peer (%s)", n, (n==-1?strerror(errno):"") );
|
e = errno;
|
||||||
|
dbgmsg( io, "wrote %d to peer (%s)", n, (n==-1?strerror(e):"") );
|
||||||
|
|
||||||
if( n == -1 )
|
if( n == -1 )
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -289,6 +297,7 @@ static void
|
||||||
event_write_cb( int fd, short event UNUSED, void * vio )
|
event_write_cb( int fd, short event UNUSED, void * vio )
|
||||||
{
|
{
|
||||||
int res = 0;
|
int res = 0;
|
||||||
|
int e;
|
||||||
short what = EVBUFFER_WRITE;
|
short what = EVBUFFER_WRITE;
|
||||||
tr_peerIo * io = vio;
|
tr_peerIo * io = vio;
|
||||||
size_t howmuch;
|
size_t howmuch;
|
||||||
|
@ -308,12 +317,15 @@ event_write_cb( int fd, short event UNUSED, void * vio )
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
errno = 0;
|
||||||
res = tr_evbuffer_write( io, fd, howmuch );
|
res = tr_evbuffer_write( io, fd, howmuch );
|
||||||
|
e = errno;
|
||||||
|
|
||||||
if (res == -1) {
|
if (res == -1) {
|
||||||
#ifndef WIN32
|
#ifndef WIN32
|
||||||
/*todo. evbuffer uses WriteFile when WIN32 is set. WIN32 system calls do not
|
/*todo. evbuffer uses WriteFile when WIN32 is set. WIN32 system calls do not
|
||||||
* *set errno. thus this error checking is not portable*/
|
* *set errno. thus this error checking is not portable*/
|
||||||
if (errno == EAGAIN || errno == EINTR || errno == EINPROGRESS)
|
if (e == EAGAIN || e == EINTR || e == EINPROGRESS)
|
||||||
goto reschedule;
|
goto reschedule;
|
||||||
/* error case */
|
/* error case */
|
||||||
what |= EVBUFFER_ERROR;
|
what |= EVBUFFER_ERROR;
|
||||||
|
@ -341,6 +353,9 @@ event_write_cb( int fd, short event UNUSED, void * vio )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
error:
|
error:
|
||||||
|
|
||||||
|
dbgmsg( io, "event_write_cb got an error. res is %d, what is %hd, errno is %d (%s)", res, what, e, strerror( e ) );
|
||||||
|
|
||||||
if( io->gotError != NULL )
|
if( io->gotError != NULL )
|
||||||
io->gotError( io, what, io->userData );
|
io->gotError( io, what, io->userData );
|
||||||
}
|
}
|
||||||
|
@ -891,25 +906,30 @@ tr_peerIoGetAge( const tr_peerIo * io )
|
||||||
static int
|
static int
|
||||||
tr_peerIoTryRead( tr_peerIo * io, size_t howmuch )
|
tr_peerIoTryRead( tr_peerIo * io, size_t howmuch )
|
||||||
{
|
{
|
||||||
int res;
|
int res = 0;
|
||||||
|
|
||||||
assert( tr_isPeerIo( io ) );
|
assert( tr_isPeerIo( io ) );
|
||||||
|
|
||||||
howmuch = tr_bandwidthClamp( io->bandwidth, TR_DOWN, howmuch );
|
if(( howmuch = tr_bandwidthClamp( io->bandwidth, TR_DOWN, howmuch )))
|
||||||
|
|
||||||
res = howmuch ? evbuffer_read( io->inbuf, io->socket, howmuch ) : 0;
|
|
||||||
|
|
||||||
dbgmsg( io, "read %d from peer (%s)", res, (res==-1?strerror(errno):"") );
|
|
||||||
|
|
||||||
if( EVBUFFER_LENGTH( io->inbuf ) )
|
|
||||||
canReadWrapper( io );
|
|
||||||
|
|
||||||
if( ( res <= 0 ) && ( io->gotError ) && ( errno != EAGAIN ) && ( errno != EINTR ) && ( errno != EINPROGRESS ) )
|
|
||||||
{
|
{
|
||||||
short what = EVBUFFER_READ | EVBUFFER_ERROR;
|
int e;
|
||||||
if( res == 0 )
|
errno = 0;
|
||||||
what |= EVBUFFER_EOF;
|
res = evbuffer_read( io->inbuf, io->socket, howmuch );
|
||||||
io->gotError( io, what, io->userData );
|
e = errno;
|
||||||
|
|
||||||
|
dbgmsg( io, "read %d from peer (%s)", res, (res==-1?strerror(e):"") );
|
||||||
|
|
||||||
|
if( EVBUFFER_LENGTH( io->inbuf ) )
|
||||||
|
canReadWrapper( io );
|
||||||
|
|
||||||
|
if( ( res <= 0 ) && ( io->gotError ) && ( e != EAGAIN ) && ( e != EINTR ) && ( e != EINPROGRESS ) )
|
||||||
|
{
|
||||||
|
short what = EVBUFFER_READ | EVBUFFER_ERROR;
|
||||||
|
if( res == 0 )
|
||||||
|
what |= EVBUFFER_EOF;
|
||||||
|
dbgmsg( io, "tr_peerIoTryRead got an error. res is %d, what is %hd, errno is %d (%s)", res, what, e, strerror( e ) );
|
||||||
|
io->gotError( io, what, io->userData );
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return res;
|
return res;
|
||||||
|
@ -922,16 +942,22 @@ tr_peerIoTryWrite( tr_peerIo * io, size_t howmuch )
|
||||||
|
|
||||||
assert( tr_isPeerIo( io ) );
|
assert( tr_isPeerIo( io ) );
|
||||||
|
|
||||||
howmuch = tr_bandwidthClamp( io->bandwidth, TR_UP, howmuch );
|
if(( howmuch = tr_bandwidthClamp( io->bandwidth, TR_UP, howmuch )))
|
||||||
|
{
|
||||||
|
int e;
|
||||||
|
errno = 0;
|
||||||
|
n = tr_evbuffer_write( io, io->socket, (int)howmuch );
|
||||||
|
e = errno;
|
||||||
|
|
||||||
n = tr_evbuffer_write( io, io->socket, (int)howmuch );
|
if( n > 0 )
|
||||||
|
didWriteWrapper( io, n );
|
||||||
|
|
||||||
if( n > 0 )
|
if( ( n < 0 ) && ( io->gotError ) && ( e != EPIPE ) && ( e != EAGAIN ) && ( e != EINTR ) && ( e != EINPROGRESS ) )
|
||||||
didWriteWrapper( io, n );
|
{
|
||||||
|
const short what = EVBUFFER_WRITE | EVBUFFER_ERROR;
|
||||||
if( ( n < 0 ) && ( io->gotError ) && ( errno != EPIPE ) && ( errno != EAGAIN ) && ( errno != EINTR ) && ( errno != EINPROGRESS ) ) {
|
dbgmsg( io, "tr_peerIoTryWrite got an error. res is %d, what is %hd, errno is %d (%s)", n, what, e, strerror( e ) );
|
||||||
short what = EVBUFFER_WRITE | EVBUFFER_ERROR;
|
io->gotError( io, what, io->userData );
|
||||||
io->gotError( io, what, io->userData );
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return n;
|
return n;
|
||||||
|
|
|
@ -913,8 +913,7 @@ addStrike( Torrent * t,
|
||||||
struct peer_atom * atom = getExistingAtom( t, &peer->addr );
|
struct peer_atom * atom = getExistingAtom( t, &peer->addr );
|
||||||
atom->myflags |= MYFLAG_BANNED;
|
atom->myflags |= MYFLAG_BANNED;
|
||||||
peer->doPurge = 1;
|
peer->doPurge = 1;
|
||||||
tordbg( t, "banning peer %s",
|
tordbg( t, "banning peer %s", tr_peerIoAddrStr( &atom->addr, atom->port ) );
|
||||||
tr_peerIoAddrStr( &atom->addr, atom->port ) );
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1140,7 +1139,7 @@ peerCallbackFunc( void * vpeer, void * vevent, void * vt )
|
||||||
{
|
{
|
||||||
addStrike( t, peer );
|
addStrike( t, peer );
|
||||||
peer->doPurge = 1;
|
peer->doPurge = 1;
|
||||||
tordbg( t, "setting doPurge because we got an EINVAL error" );
|
tordbg( t, "setting %s doPurge flag because we got an EINVAL error", tr_peerIoAddrStr( &peer->addr, peer->port ) );
|
||||||
}
|
}
|
||||||
else if( ( e->err == ERANGE )
|
else if( ( e->err == ERANGE )
|
||||||
|| ( e->err == EMSGSIZE )
|
|| ( e->err == EMSGSIZE )
|
||||||
|
@ -1148,7 +1147,7 @@ peerCallbackFunc( void * vpeer, void * vevent, void * vt )
|
||||||
{
|
{
|
||||||
/* some protocol error from the peer */
|
/* some protocol error from the peer */
|
||||||
peer->doPurge = 1;
|
peer->doPurge = 1;
|
||||||
tordbg( t, "setting doPurge because we got an ERANGE, EMSGSIZE, or ENOTCONN error" );
|
tordbg( t, "setting %s doPurge flag because we got an ERANGE, EMSGSIZE, or ENOTCONN error", tr_peerIoAddrStr( &peer->addr, peer->port ) );
|
||||||
}
|
}
|
||||||
else /* a local error, such as an IO error */
|
else /* a local error, such as an IO error */
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue