00001 #include "lugre_prefix.h"
00002 #include "lugre_thread.h"
00003 #include "lugre_net.h"
00004 #include "lugre_fifo.h"
00005 #include "lugre_net.h"
00006
00007 #include <iostream>
00008 #include <fstream>
00009
00010 #ifdef ENABLE_THREADS
00011 #include <boost/thread/thread.hpp>
00012 #endif
00013
00014 #define kThreadNetMinRecvSpace (1024*32)
00015 #define kThreadNetStartSpace (1024*32*2)
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056 namespace Lugre {
00057
00058
00059
00060
00061
00062 class cThread_NetRequestImpl { public:
00063 std::string msHost;
00064 int miPort;
00065 cFIFO* mpSendData;
00066 cFIFO* mpAnswerBuffer;
00067 int* mpResultCode;
00068
00069 cThread_NetRequestImpl (int* pResultCode,const std::string& sHost,const int iPort,cFIFO* pSendData,cFIFO* pAnswerBuffer) :
00070 mpResultCode(pResultCode), msHost(sHost), miPort(iPort), mpSendData(pSendData), mpAnswerBuffer(pAnswerBuffer) {}
00071
00072 void operator()() {
00073 do {
00074
00075 uint32 iIP = cNet::GetHostByName(msHost.c_str());
00076 int iSocket = cNet::ConnectSocket(iIP,miPort);
00077 if (cNet::IsInvalidSocket(iSocket)) {
00078 printf("cThread_NetRequest : ConnectSocket failed (%s:%d)\n",msHost.c_str(),miPort);
00079 break;
00080 }
00081
00082
00083 if (mpSendData && mpSendData->size() > 0) {
00084 int res = cNet::Send(iSocket,mpSendData->HackGetRawReader(),mpSendData->size(),0);
00085 if (res != mpSendData->size()) {
00086 printf("cThread_NetRequest : sending failed (%s:%d) : %d\n",msHost.c_str(),miPort,res);
00087 break;
00088 }
00089 }
00090
00091
00092 if (mpAnswerBuffer) {
00093 do {
00094 char *rw = mpAnswerBuffer->HackGetRawWriter(kThreadNetMinRecvSpace);
00095 int fs = mpAnswerBuffer->HackGetFreeSpace();
00096 int res = cNet::Recv(iSocket,rw,fs,0);
00097 if (res <= 0) break;
00098 mpAnswerBuffer->HackAddLength(res);
00099 } while (1);
00100 }
00101
00102
00103 cNet::CloseSocket(iSocket);
00104
00105
00106 *mpResultCode = 0;
00107 return;
00108
00109 } while (0) ;
00110
00111
00112 *mpResultCode = -1;
00113
00114 }
00115 };
00116
00117
00118 cThread_NetRequest::cThread_NetRequest (const std::string& sHost,const int iPort,cFIFO* pSendData,cFIFO* pAnswerBuffer) {
00119 miResultCode = 1;
00120 cThread_NetRequestImpl myImpl(&miResultCode,sHost,iPort,pSendData,pAnswerBuffer);
00121 #ifdef ENABLE_THREADS
00122
00123 boost::thread myboostthread(myImpl);
00124 #else
00125
00126 myImpl();
00127 #endif
00128 }
00129 cThread_NetRequest::~cThread_NetRequest () {}
00130
00131
00132
00133
00134
00135
00136
00137 class cThread_LoadFileImpl { public:
00138 std::string msFilePath;
00139 cFIFO* mpAnswerBuffer;
00140 int miStart;
00141 int miLength;
00142 int* mpResultCode;
00143
00144 cThread_LoadFileImpl (int* pResultCode,const std::string& sFilePath,cFIFO* pAnswerBuffer,const int iStart,const int iLength) :
00145 mpResultCode(pResultCode), msFilePath(sFilePath), mpAnswerBuffer(pAnswerBuffer), miStart(iStart), miLength(iLength) {}
00146
00147 void operator()() {
00148 do {
00149 if (!mpAnswerBuffer) break;
00150 std::ifstream myFileStream(msFilePath.c_str(),std::ios_base::binary);
00151 if (!myFileStream) { printf("cThread_LoadFile : failed to open file %s (start=%d,len=%d)\n",msFilePath.c_str(),miStart,miLength); break; }
00152 myFileStream.seekg(0, std::ios::end);
00153 int iFullFileSize = myFileStream.tellg();
00154 int iReadStart = mymax(0,miStart);
00155 int iReadLen = (miLength < 0) ? iFullFileSize : mymin(iFullFileSize-iReadStart,miLength);
00156
00157 myFileStream.seekg(iReadStart, std::ios::beg);
00158
00159 char *pWriter = mpAnswerBuffer->HackGetRawWriter(iReadLen);
00160 myFileStream.read(pWriter,iReadLen);
00161 mpAnswerBuffer->HackAddLength(iReadLen);
00162 myFileStream.close();
00163
00164
00165 *mpResultCode = 0;
00166 return;
00167
00168 } while (0) ;
00169
00170
00171 *mpResultCode = -1;
00172
00173 }
00174 };
00175
00176
00177 cThread_LoadFile::cThread_LoadFile (const std::string& sFilePath,cFIFO* pAnswerBuffer,const int iStart,const int iLength) {
00178 miResultCode = 1;
00179 cThread_LoadFileImpl myImpl(&miResultCode,sFilePath,pAnswerBuffer,iStart,iLength);
00180 #ifdef ENABLE_THREADS
00181
00182 boost::thread myboostthread(myImpl);
00183 #else
00184
00185 myImpl();
00186 #endif
00187 }
00188 cThread_LoadFile::~cThread_LoadFile () {}
00189
00190
00191
00192 };