00001
00002
00003 #include <iostream>
00004 using namespace std;
00005
00006 #include <ctype.h>
00007
00008 #include "RodModule.h"
00009
00010 #include "primParams.h"
00011 #include "RCCVmeInterface.h"
00012 #include "parameters.h"
00013 #include "PPBuffer.h"
00014 #include "PPThread.h"
00015 #include "PPThreadAttr.h"
00016 #include "PPMutex.h"
00017 #include "PPCondition.h"
00018
00038 using namespace SctPixelRod;
00039
00040 class ParamList
00041 {
00042 public:
00043 ParamList(){m_finished = false;};
00044 ParamList(RodModule* rod, PPBuffer<unsigned long>* replyBuffer, PPBuffer<char>* textBuffer,
00045 PPBuffer<char>* errBuffer, PPMutex* coutMutex){
00046 m_rod = rod;
00047 m_replyBuffer = replyBuffer;
00048 m_textBuffer = textBuffer;
00049 m_errBuffer = errBuffer;
00050 m_coutMutex = coutMutex;
00051 m_finished = false;
00052 };
00053 ParamList( const ParamList&){};
00054 ParamList& operator=(const ParamList&){};
00055 ~ParamList(){};
00056
00057 void setRod(RodModule* rod) {m_rod = rod; return;};
00058 void setReplyBuffer(PPBuffer<unsigned long>* replyBuffer)
00059 {m_replyBuffer=replyBuffer; return;};
00060 void setTextBuffer(PPBuffer<char>* textBuffer)
00061 {m_textBuffer=textBuffer; return;};
00062 void setErrBuffer(PPBuffer<char>* errBuffer)
00063 {m_errBuffer=errBuffer; return;};
00064 void setCoutMutex(PPMutex* coutMutex) {m_coutMutex = coutMutex; return;};
00065 void setFinished(bool finished) {m_finished = finished; return;};
00066 RodModule* getRod() {return m_rod;};
00067 PPBuffer<unsigned long>* getReplyBuffer() {return m_replyBuffer;}
00068 PPBuffer<char>* getTextBuffer() {return m_textBuffer;}
00069 PPBuffer<char>* getErrBuffer() {return m_errBuffer;}
00070 PPMutex* getCoutMutex() {return m_coutMutex;}
00071 bool getFinished() {return m_finished;};
00072
00073 private:
00074 RodModule* m_rod;
00075 PPBuffer<unsigned long>* m_replyBuffer;
00076 PPBuffer<char>* m_textBuffer;
00077 PPBuffer<char>* m_errBuffer;
00078 PPMutex* m_coutMutex;
00079 bool m_finished;
00080 };
00081
00082 void *bkgStart(void *arg) {
00083
00089 long myTextLength;
00090 TEXT_BUFFER_TYPE myTextType;
00091
00092
00093 char * myTextBuffer = new char[TEXT_BUFF_SIZE];
00094 PrimState returnPState;
00095 TextBuffState returnTState;
00096
00097
00098 ParamList* myParamList;
00099 myParamList = static_cast<ParamList*>(arg);
00100 RodModule* rod0 = myParamList->getRod();
00101 PPBuffer<unsigned long>* userBuffer = myParamList->getReplyBuffer();
00102 PPBuffer<char>* textBuffer = myParamList->getTextBuffer();
00103
00104
00105 while (1) {
00106 do {
00107 if (myParamList->getFinished()) break;
00108 returnPState = rod0->primHandler();
00109 returnTState = rod0->textHandler();
00110 if (returnTState == TEXT_RQ_SET) {
00111 do {
00112 returnTState = rod0->textHandler();
00113 } while (returnTState != TEXT_READOUT);
00114 rod0->getTextBuffer(myTextBuffer, myTextLength, myTextType);
00115 rod0->clearTextBuffer();
00116 rod0->sleep(50);
00117 textBuffer->fillBuffer(myTextBuffer, myTextLength);
00118 }
00119 } while (returnPState != PRIM_EXECUTING);
00120 do {
00121 try {
00122 returnPState = rod0->primHandler();
00123 }
00124 catch (RodException &r) {
00125 cerr << r.getDescriptor() <<", " << r.getData1() << ", " << r.getData2()
00126 << '\n';
00127 }
00128 } while (returnPState != PRIM_WAITING);
00129
00130
00131 RodOutList* outList = rod0->getOutList();
00132 UINT32 outLength = UINT32(outList->getLength());
00133 unsigned long* outBody = outList->getBody();
00134
00135
00136 userBuffer->fillBuffer(outBody, outLength);
00137
00138
00139 if (!myParamList->getFinished()) break;
00140 };
00141
00142 delete [] myTextBuffer;
00143 return 0;
00144
00145 }
00146
00147 void* errStart(void *arg) {
00148
00155 using namespace SctPixelRod;
00156
00157
00158 ParamList* myParamList;
00159 myParamList = static_cast<ParamList*>(arg);
00160 PPBuffer<char>* errBuffer = myParamList->getErrBuffer();
00161
00162
00163 while (1) {
00164 errBuffer->waitForFilled();
00165 long totItems = errBuffer->getTotItems();
00166 if (totItems > 0) {
00167 char* errArray = new char[totItems];
00168 errBuffer->dumpBuffer(errArray, totItems);
00169 for (int i=0; i<totItems; i++) cerr << errArray[i];
00170 delete [] errArray;
00171 }
00172 if (myParamList->getFinished()) break;
00173 }
00174 return 0;
00175 }
00176
00177 void* textStart(void *arg) {
00178
00186 using namespace SctPixelRod;
00187
00188
00189 ParamList* myParamList;
00190 myParamList = static_cast<ParamList*>(arg);
00191 PPBuffer<char>* textBuffer = myParamList->getTextBuffer();
00192 PPMutex* coutMutex = myParamList->getCoutMutex();
00193
00194
00195 while (1) {
00196 textBuffer->waitForFilled();
00197 long totItems = textBuffer->getTotItems();
00198 if (totItems > 0) {
00199 char* textArray = new char[totItems];
00200 textBuffer->dumpBuffer(textArray, totItems);
00201 coutMutex->lock();
00202 for (int i=0; i<totItems; i++) cout << textArray[i];
00203 coutMutex->unlock();
00204 delete [] textArray;
00205 }
00206 if (!myParamList->getFinished()) break;
00207 }
00208 return 0;
00209 }
00210
00211 void* userStart(void *arg) {
00212
00218 using namespace SctPixelRod;
00219
00220
00221 ParamList* myParamList;
00222 myParamList = static_cast<ParamList*>(arg);
00223 PPBuffer<unsigned long>* userBuffer = myParamList->getReplyBuffer();
00224 PPMutex* coutMutex = myParamList->getCoutMutex();
00225
00226
00227 while (1) {
00228 userBuffer->waitForFilled();
00229 UINT32 outLength = userBuffer->getTotItems();
00230 if (outLength > 0) {
00231 unsigned long* outBody = new unsigned long[outLength];
00232 userBuffer->dumpBuffer(outBody, outLength);
00233
00234
00235 UINT32 outIndex = UINT32(outBody[1]);
00236 UINT32 outNumPrims = outBody[2];
00237 UINT32 outPrimVersion = outBody[3];
00238 coutMutex->lock();
00239 cout << "outLength = " << outLength << ", outIndex = " << outIndex <<
00240 ", outNumPrims = " << outNumPrims << ", outPrimVersion = " <<
00241 outPrimVersion <<'\n';
00242 int outPtr = 4;
00243 for (unsigned int j=0; j<outNumPrims; j++) {
00244 UINT32 primLength = outBody[outPtr++];
00245 UINT32 primIndex = outBody[outPtr++];
00246 UINT32 primId = outBody[outPtr++];
00247 UINT32 primVersion = outBody[outPtr++];
00248 cout << "primLength = " << primLength << ", primIndex = " << primIndex <<
00249 ", primId = " << primId << ", primVersion = " << primVersion << '\n';
00250 cout << "ECHO data: ";
00251 hex(cout);
00252 for (unsigned int i=0; i<primLength-4; i++) {
00253 cout.width(8);
00254 cout << outBody[i+outPtr] <<" ";
00255 if (0 == (i+1)%8) cout << endl;
00256 };
00257 if (0 != (primLength-4)%8) cout << endl;
00258 dec(cout);
00259 };
00260 coutMutex->unlock();
00261 }
00262 if (!myParamList->getFinished()) break;
00263 }
00264 return 0;
00265 }
00266
00267 int main(int argc, char *argv[]) {
00268
00281 using namespace SctPixelRod;
00282
00283 const unsigned long mapSize=0xc00040;
00284 RodPrimList primList(1);
00285 long numSlaves = 4;
00286
00287 std::string fileName(""), option;
00288 int slot = -1;
00289 unsigned long baseAddress;
00290
00291 if (argc > 1) {
00292 for (int i=1; i<argc; i++) {
00293 option = argv[i];
00294 if (option[0] != '-') break;
00295 switch (option[1]) {
00296 case 's': {
00297 slot = atoi(option.substr(2).c_str());
00298 break;
00299 }
00300 default: {
00301 break;
00302 }
00303 }
00304 }
00305 }
00306
00307
00308 if (slot < 0 ) {
00309 cout << "Enter slot number (decimal):";
00310 cin >> slot;
00311 while ((slot < 1) || (slot > 21)) {
00312 cout << "Slot number out or range [1:21], re-enter: ";
00313 cin >> slot;
00314 }
00315 }
00316 baseAddress = slot << 24;
00317
00318
00319 RCCVmeInterface *vme1 = new RCCVmeInterface();
00320
00321
00322 RodModule* rod0 = new RodModule(baseAddress, mapSize, *vme1, numSlaves);
00323 try{
00324 rod0->initialize();
00325 }
00326 catch (HpiException &h) {
00327 hex(cout);
00328 cerr << h.getDescriptor() << '\n';
00329 cerr << "calcAddr: " << h.getCalcAddr() << ", readAddr: " <<
00330 h.getReadAddr() << '\n';
00331 dec(cout);
00332 };
00333
00334
00335 PPBuffer<char> textBuffer(1024);
00336 PPBuffer<unsigned long> userBuffer(1024);
00337 PPBuffer<char> errBuffer(1025);
00338 PPMutex bkgMutex, errMutex, textMutex, userMutex;
00339 PPMutex coutMutex;
00340 ParamList myParamList;
00341 myParamList.setRod(rod0);
00342 myParamList.setTextBuffer(&textBuffer);
00343 myParamList.setReplyBuffer(&userBuffer);
00344 myParamList.setErrBuffer(&errBuffer);
00345 myParamList.setCoutMutex(&coutMutex);
00346
00347
00348 PPThreadAttr defaultAttr;
00349
00350 PPThread bkgThread(&defaultAttr, bkgStart, &myParamList);
00351
00352 PPThread errThread(&defaultAttr, errStart, &myParamList);
00353
00354 PPThread textThread(&defaultAttr, textStart, &myParamList);
00355
00356 PPThread userThread(&defaultAttr, userStart, &myParamList);
00357
00358
00359 long dataLength;
00360 coutMutex.lock();
00361 cout << "Enter number of data words: ";
00362 cin >> dataLength;
00363 coutMutex.unlock();
00364 long* echoData = new long[dataLength];
00365 for (long i=0; i<dataLength; i++) {
00366 echoData[i] = 0xbeef0000 | i;
00367 }
00368 RodPrimitive* echo = new RodPrimitive(dataLength+4, 1, ECHO, R_ECHO, echoData);
00369 primList.insert(primList.begin(), *echo);
00370 try {
00371 primList.bufferBuild();
00372 }
00373 catch (PrimListException &p) {
00374 cerr << p.getDescriptor() << " ";
00375 cerr << p.getData1() << ", " << p.getData2() << "\n";
00376 };
00377 try {
00378 rod0->sendPrimList(&primList);
00379 }
00380 catch (HpiException &h) {
00381 hex(cout);
00382 cerr << h.getDescriptor() << '\n';
00383 cerr << "calcAddr: " << h.getCalcAddr() << ", readAddr: " <<
00384 h.getReadAddr() << '\n';
00385 dec(cout);
00386 };
00387 delete [] echoData;
00388
00389
00390 char reply;
00391 coutMutex.lock();
00392 cout << "Press any key followed by <enter> to finish: ";
00393 cin >> reply;
00394 coutMutex.unlock();
00395
00396
00397 primList.clear();
00398 delete echo;
00399 rod0->deleteOutList();
00400
00401
00402 myParamList.setFinished(true);
00403 userBuffer.close();
00404 textBuffer.close();
00405 errBuffer.close();
00406
00407
00408 delete rod0;
00409 delete vme1;
00410
00411 return 0;
00412 }