|
|
|
@ -38,6 +38,7 @@
|
|
|
|
|
#include <signal.h>
|
|
|
|
|
#include <stdlib.h>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//********* JobData ******************************************
|
|
|
|
|
|
|
|
|
|
|
|
|
|
@ -53,8 +54,8 @@ JobData::JobData(QueryType Ntype,bool NnewServer,TQString const& Nserver,int Npo
|
|
|
|
|
//********* DictAsyncClient *************************************
|
|
|
|
|
|
|
|
|
|
DictAsyncClient::DictAsyncClient(int NfdPipeIn, int NfdPipeOut)
|
|
|
|
|
: job(0L), inputSize(10000), fdPipeIn(NfdPipeIn),
|
|
|
|
|
fdPipeOut(NfdPipeOut), tcpSocket(-1), idleHold(0)
|
|
|
|
|
: TQThread(), job(0L), inputSize(10000), fdPipeIn(NfdPipeIn),
|
|
|
|
|
fdPipeOut(NfdPipeOut), tcpSocket(-1), idleHold(0), m_request_termination(false)
|
|
|
|
|
{
|
|
|
|
|
input = new char[inputSize];
|
|
|
|
|
}
|
|
|
|
@ -68,22 +69,6 @@ DictAsyncClient::~DictAsyncClient()
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void* DictAsyncClient::startThread(void* pseudoThis)
|
|
|
|
|
{
|
|
|
|
|
DictAsyncClient* newthis = (DictAsyncClient*) (pseudoThis);
|
|
|
|
|
|
|
|
|
|
if (0!=pthread_setcanceltype(PTHREAD_CANCEL_ENABLE,NULL))
|
|
|
|
|
tqWarning("pthread_setcanceltype failed!");
|
|
|
|
|
if (0!= pthread_setcanceltype(PTHREAD_CANCEL_ASYNCHRONOUS,NULL))
|
|
|
|
|
tqWarning("pthread_setcanceltype failed!");
|
|
|
|
|
|
|
|
|
|
signal(SIGPIPE,SIG_IGN); // ignore sigpipe
|
|
|
|
|
|
|
|
|
|
newthis->waitForWork();
|
|
|
|
|
return NULL;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void DictAsyncClient::insertJob(JobData *newJob)
|
|
|
|
|
{
|
|
|
|
|
if (!job) // don't overwrite existing job pointer
|
|
|
|
@ -97,27 +82,33 @@ void DictAsyncClient::removeJob()
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void DictAsyncClient::waitForWork()
|
|
|
|
|
void DictAsyncClient::run()
|
|
|
|
|
{
|
|
|
|
|
fd_set fdsR,fdsE;
|
|
|
|
|
timeval tv;
|
|
|
|
|
int selectRet;
|
|
|
|
|
char buf;
|
|
|
|
|
timeval timeout_interval;
|
|
|
|
|
|
|
|
|
|
while (true) {
|
|
|
|
|
while (!m_request_termination) {
|
|
|
|
|
if (tcpSocket != -1) { // we are connected, hold the connection for xx secs
|
|
|
|
|
FD_ZERO(&fdsR);
|
|
|
|
|
FD_SET(fdPipeIn, &fdsR);
|
|
|
|
|
FD_SET(tcpSocket, &fdsR);
|
|
|
|
|
FD_ZERO(&fdsE);
|
|
|
|
|
FD_SET(tcpSocket, &fdsE);
|
|
|
|
|
tv.tv_sec = idleHold;
|
|
|
|
|
tv.tv_usec = 0;
|
|
|
|
|
selectRet = KSocks::self()->select(FD_SETSIZE, &fdsR, NULL, &fdsE, &tv);
|
|
|
|
|
int cnt = 0;
|
|
|
|
|
do {
|
|
|
|
|
FD_ZERO(&fdsR);
|
|
|
|
|
FD_SET(fdPipeIn, &fdsR);
|
|
|
|
|
++cnt;
|
|
|
|
|
timeout_interval.tv_sec=1;
|
|
|
|
|
timeout_interval.tv_usec=0;
|
|
|
|
|
selectRet=KSocks::self()->select(FD_SETSIZE, &fdsR, NULL, &fdsE, &timeout_interval);
|
|
|
|
|
} while (!m_request_termination && cnt<idleHold && selectRet==0);
|
|
|
|
|
if (selectRet == 0) {
|
|
|
|
|
doQuit(); // nothing happend...
|
|
|
|
|
} else {
|
|
|
|
|
if (((selectRet > 0)&&(!FD_ISSET(fdPipeIn,&fdsR)))||(selectRet == -1))
|
|
|
|
|
if ((selectRet>0 && !FD_ISSET(fdPipeIn,&fdsR)) || selectRet==-1)
|
|
|
|
|
closeSocket();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
@ -125,8 +116,13 @@ void DictAsyncClient::waitForWork()
|
|
|
|
|
do {
|
|
|
|
|
FD_ZERO(&fdsR);
|
|
|
|
|
FD_SET(fdPipeIn, &fdsR);
|
|
|
|
|
} while (select(FD_SETSIZE, &fdsR, NULL, NULL, NULL)<0); // don't get tricked by signals
|
|
|
|
|
|
|
|
|
|
timeout_interval.tv_sec=1;
|
|
|
|
|
timeout_interval.tv_usec=0;
|
|
|
|
|
} while (!m_request_termination && select(FD_SETSIZE, &fdsR, NULL, NULL, &timeout_interval)<=0);
|
|
|
|
|
|
|
|
|
|
if (m_request_termination)
|
|
|
|
|
return;
|
|
|
|
|
|
|
|
|
|
clearPipe();
|
|
|
|
|
|
|
|
|
|
if (job) {
|
|
|
|
@ -785,7 +781,6 @@ void DictAsyncClient::openConnection()
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
KExtendedSocket ks;
|
|
|
|
|
|
|
|
|
|
ks.setAddress(job->server, job->port);
|
|
|
|
|
ks.setTimeout(job->timeout);
|
|
|
|
|
if (ks.connect() < 0) {
|
|
|
|
@ -1211,11 +1206,12 @@ DictInterface::DictInterface()
|
|
|
|
|
(void) KSocks::self();
|
|
|
|
|
|
|
|
|
|
client = new DictAsyncClient(fdPipeOut[0],fdPipeIn[1]);
|
|
|
|
|
if (0!=pthread_create(&threadID,0,&(client->startThread),client)) {
|
|
|
|
|
if (!client) {
|
|
|
|
|
KMessageBox::error(global->topLevel, i18n("Internal error:\nUnable to create thread."));
|
|
|
|
|
kapp->exit(1);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
client->start();
|
|
|
|
|
|
|
|
|
|
jobList.setAutoDelete(true);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
@ -1223,13 +1219,16 @@ DictInterface::DictInterface()
|
|
|
|
|
DictInterface::~DictInterface()
|
|
|
|
|
{
|
|
|
|
|
disconnect(notifier,TQT_SIGNAL(activated(int)),this,TQT_SLOT(clientDone()));
|
|
|
|
|
|
|
|
|
|
if (0!=pthread_cancel(threadID))
|
|
|
|
|
kdWarning() << "pthread_cancel failed!" << endl;
|
|
|
|
|
if (0!=pthread_join(threadID,NULL))
|
|
|
|
|
kdWarning() << "pthread_join failed!" << endl;
|
|
|
|
|
delete client;
|
|
|
|
|
|
|
|
|
|
if (client)
|
|
|
|
|
{
|
|
|
|
|
client->request_termination();
|
|
|
|
|
if (!client->wait(3000))
|
|
|
|
|
{
|
|
|
|
|
client->terminate();
|
|
|
|
|
client->wait(3000);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if ( ::close( fdPipeIn[0] ) == -1 ) {
|
|
|
|
|
perror( "Closing fdPipeIn[0]" );
|
|
|
|
|
}
|
|
|
|
@ -1242,6 +1241,8 @@ DictInterface::~DictInterface()
|
|
|
|
|
if ( ::close( fdPipeOut[1] ) == -1 ) {
|
|
|
|
|
perror( "Closing fdPipeOut[1]" );
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
delete client;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|