From fff79fbbb655816ed8dcd81ad6baaf65aedd8469 Mon Sep 17 00:00:00 2001 From: Erik Frojdh Date: Thu, 16 May 2019 16:58:03 +0200 Subject: [PATCH 1/8] const char* for command --- .../include/slsDetectorCommand.h | 96 +++---- .../src/slsDetectorCommand.cpp | 96 +++---- slsSupportLib/include/CmdLineParser.h | 3 +- slsSupportLib/src/CmdLineParser.cpp | 37 ++- slsSupportLib/tests/test-CmdLineParser.cpp | 243 +++++++++--------- 5 files changed, 243 insertions(+), 232 deletions(-) diff --git a/slsDetectorSoftware/include/slsDetectorCommand.h b/slsDetectorSoftware/include/slsDetectorCommand.h index 39fb02d5c..f9cb934a7 100755 --- a/slsDetectorSoftware/include/slsDetectorCommand.h +++ b/slsDetectorSoftware/include/slsDetectorCommand.h @@ -29,14 +29,14 @@ class slsDetectorCommand : public virtual slsDetectorDefs { * @param action can be PUT_ACTION or GET_ACTION(from text client even READOUT_ACTION for acquisition) * @param detPos -1 for all detectors in multi detector list or position of a specific detector in list */ - std::string executeLine(int narg, char *args[], int action, int detPos = -1); + std::string executeLine(int narg, const char * const args[], int action, int detPos = -1); /* /\** */ /* returns the help for the executeLine command */ /* \param os output stream to return the help to */ /* \param action can be PUT_ACTION or GET_ACTION (from text client even READOUT_ACTION for acquisition) */ /* *\/ */ - std::string helpLine(int narg, char *args[], int action=HELP_ACTION, int detPos = -1); + std::string helpLine(int narg, const char * const args[], int action=HELP_ACTION, int detPos = -1); static std::string helpAcquire(int action); static std::string helpData(int action); static std::string helpStatus(int action); @@ -96,56 +96,56 @@ class slsDetectorCommand : public virtual slsDetectorDefs { multiSlsDetector *myDet; - std::string cmdUnderDevelopment(int narg, char *args[], int action, int detPos = -1); - std::string cmdUnknown(int narg, char *args[], int action, int detPos = -1); - std::string cmdAcquire(int narg, char *args[], int action, int detPos = -1); - std::string cmdData(int narg, char *args[], int action, int detPos = -1); - std::string cmdStatus(int narg, char *args[], int action, int detPos = -1); - std::string cmdDataStream(int narg, char *args[], int action, int detPos = -1); - std::string cmdFree(int narg, char *args[], int action, int detPos = -1); - std::string cmdHostname(int narg, char *args[], int action, int detPos = -1); - std::string cmdUser(int narg, char *args[], int action, int detPos = -1); - std::string cmdHelp(int narg, char *args[], int action, int detPos = -1); - std::string cmdExitServer(int narg, char *args[], int action, int detPos = -1); - std::string cmdSettingsDir(int narg, char *args[], int action, int detPos = -1); - std::string cmdTrimEn(int narg, char *args[], int action, int detPos = -1); - std::string cmdOutDir(int narg, char *args[], int action, int detPos = -1); - std::string cmdFileName(int narg, char *args[], int action, int detPos = -1); - std::string cmdFileIndex(int narg, char *args[], int action, int detPos = -1); - std::string cmdRateCorr(int narg, char *args[], int action, int detPos = -1); - std::string cmdNetworkParameter(int narg, char *args[], int action, int detPos = -1); - std::string cmdPort(int narg, char *args[], int action, int detPos = -1); - std::string cmdLock(int narg, char *args[], int action, int detPos = -1); - std::string cmdLastClient(int narg, char *args[], int action, int detPos = -1); - std::string cmdOnline(int narg, char *args[], int action, int detPos = -1); - std::string cmdConfigureMac(int narg, char *args[], int action, int detPos = -1); - std::string cmdDetectorSize(int narg, char *args[], int action, int detPos = -1); - std::string cmdSettings(int narg, char *args[], int action, int detPos = -1); - std::string cmdSN(int narg, char *args[], int action, int detPos = -1); - std::string cmdDigiTest(int narg, char *args[], int action, int detPos = -1); - std::string cmdRegister(int narg, char *args[], int action, int detPos = -1); - std::string cmdDAC(int narg, char *args[], int action, int detPos = -1); - std::string cmdTiming(int narg, char *args[], int action, int detPos = -1); - std::string cmdTimer(int narg, char *args[], int action, int detPos = -1); - std::string cmdTimeLeft(int narg, char *args[], int action, int detPos = -1); - std::string cmdSpeed(int narg, char *args[], int action, int detPos = -1); - std::string cmdAdvanced(int narg, char *args[], int action, int detPos = -1); - std::string cmdConfiguration(int narg, char *args[], int action, int detPos = -1); - std::string cmdImage(int narg, char *args[], int action, int detPos = -1); - std::string cmdCounter(int narg, char *args[], int action, int detPos = -1); - std::string cmdADC(int narg, char *args[], int action, int detPos = -1); - std::string cmdTempControl(int narg, char *args[], int action, int detPos = -1); - std::string cmdEnablefwrite(int narg, char *args[], int action, int detPos = -1); - std::string cmdOverwrite(int narg, char *args[], int action, int detPos = -1); - std::string cmdReceiver(int narg, char *args[], int action, int detPos = -1); - std::string cmdPattern(int narg, char *args[], int action, int detPos = -1); - std::string cmdPulse(int narg, char *args[], int action, int detPos = -1); - std::string cmdProcessor(int narg, char *args[], int action, int detPos = -1); + std::string cmdUnderDevelopment(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdUnknown(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdAcquire(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdData(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdStatus(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdDataStream(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdFree(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdHostname(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdUser(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdHelp(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdExitServer(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdSettingsDir(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdTrimEn(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdOutDir(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdFileName(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdFileIndex(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdRateCorr(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdNetworkParameter(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdPort(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdLock(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdLastClient(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdOnline(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdConfigureMac(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdDetectorSize(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdSettings(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdSN(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdDigiTest(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdRegister(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdDAC(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdTiming(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdTimer(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdTimeLeft(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdSpeed(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdAdvanced(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdConfiguration(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdImage(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdCounter(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdADC(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdTempControl(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdEnablefwrite(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdOverwrite(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdReceiver(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdPattern(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdPulse(int narg, const char * const args[], int action, int detPos = -1); + std::string cmdProcessor(int narg, const char * const args[], int action, int detPos = -1); int numberOfCommands; std::string cmd; - typedef std::string (slsDetectorCommand::*MemFuncGetter)(int narg, char *args[], int action, int detPos); + typedef std::string (slsDetectorCommand::*MemFuncGetter)(int narg, const char * const args[], int action, int detPos); struct FuncTable diff --git a/slsDetectorSoftware/src/slsDetectorCommand.cpp b/slsDetectorSoftware/src/slsDetectorCommand.cpp index 4208c0c25..a1d02ca49 100755 --- a/slsDetectorSoftware/src/slsDetectorCommand.cpp +++ b/slsDetectorSoftware/src/slsDetectorCommand.cpp @@ -2130,7 +2130,7 @@ slsDetectorCommand::slsDetectorCommand(multiSlsDetector *det) { //----------------------------------------------------------- -std::string slsDetectorCommand::executeLine(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::executeLine(int narg, const char * const args[], int action, int detPos) { if (action == READOUT_ACTION) return cmdAcquire(narg, args, action, detPos); @@ -2161,14 +2161,14 @@ std::string slsDetectorCommand::executeLine(int narg, char *args[], int action, return cmdUnknown(narg, args, action, detPos); } -std::string slsDetectorCommand::cmdUnknown(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdUnknown(int narg, const char * const args[], int action, int detPos) { return std::string("Unknown command ") + std::string(args[0]) + std::string("\n") + helpLine(0, args, action, detPos); } -std::string slsDetectorCommand::cmdUnderDevelopment(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdUnderDevelopment(int narg, const char * const args[], int action, int detPos) { return std::string("Must still develop ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); } -std::string slsDetectorCommand::helpLine(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::helpLine(int narg, const char * const args[], int action, int detPos) { std::ostringstream os; @@ -2187,7 +2187,7 @@ std::string slsDetectorCommand::helpLine(int narg, char *args[], int action, int return executeLine(narg, args, HELP_ACTION, detPos); } -std::string slsDetectorCommand::cmdAcquire(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdAcquire(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); #endif @@ -2232,7 +2232,7 @@ std::string slsDetectorCommand::helpAcquire(int action) { return os.str(); } -std::string slsDetectorCommand::cmdData(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdData(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); @@ -2264,7 +2264,7 @@ std::string slsDetectorCommand::helpData(int action) { return std::string("data \t gets all data from the detector (if any) processes them and writes them to file according to the preferences already setup\n"); } -std::string slsDetectorCommand::cmdStatus(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdStatus(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); @@ -2317,7 +2317,7 @@ std::string slsDetectorCommand::helpStatus(int action) { return os.str(); } -std::string slsDetectorCommand::cmdDataStream(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdDataStream(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); @@ -2351,7 +2351,7 @@ std::string slsDetectorCommand::helpDataStream(int action) { return os.str(); } -std::string slsDetectorCommand::cmdFree(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdFree(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); @@ -2367,7 +2367,7 @@ std::string slsDetectorCommand::helpFree(int action) { return std::string("free \t frees the shared memory\n"); } -std::string slsDetectorCommand::cmdHostname(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdHostname(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); #endif @@ -2429,7 +2429,7 @@ std::string slsDetectorCommand::helpHostname(int action) { return os.str(); } -std::string slsDetectorCommand::cmdUser(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdUser(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); #endif @@ -2459,7 +2459,7 @@ std::string slsDetectorCommand::helpUser(int action) { return os.str(); } -std::string slsDetectorCommand::cmdHelp(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdHelp(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); #endif @@ -2472,7 +2472,7 @@ std::string slsDetectorCommand::cmdHelp(int narg, char *args[], int action, int return helpLine(0, args, action, detPos); } -std::string slsDetectorCommand::cmdExitServer(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdExitServer(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); #endif @@ -2520,7 +2520,7 @@ std::string slsDetectorCommand::helpExitServer(int action) { return os.str(); } -std::string slsDetectorCommand::cmdSettingsDir(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdSettingsDir(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); #endif @@ -2548,7 +2548,7 @@ std::string slsDetectorCommand::helpSettingsDir(int action) { return os.str(); } -std::string slsDetectorCommand::cmdTrimEn(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdTrimEn(int narg, const char * const args[], int action, int detPos) { std::vector energies; if (action == HELP_ACTION) return helpTrimEn(action); @@ -2579,7 +2579,7 @@ std::string slsDetectorCommand::helpTrimEn(int action) { return os.str(); } -std::string slsDetectorCommand::cmdOutDir(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdOutDir(int narg, const char * const args[], int action, int detPos) { myDet->setReceiverOnline(ONLINE_FLAG, detPos); if (action == HELP_ACTION) return helpOutDir(action); @@ -2599,7 +2599,7 @@ std::string slsDetectorCommand::helpOutDir(int action) { return os.str(); } -std::string slsDetectorCommand::cmdFileName(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdFileName(int narg, const char * const args[], int action, int detPos) { myDet->setReceiverOnline(ONLINE_FLAG, detPos); if (action == HELP_ACTION) return helpFileName(action); @@ -2635,7 +2635,7 @@ std::string slsDetectorCommand::helpFileName(int action) { return os.str(); } -std::string slsDetectorCommand::cmdEnablefwrite(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdEnablefwrite(int narg, const char * const args[], int action, int detPos) { int i; char ans[100]; @@ -2681,7 +2681,7 @@ std::string slsDetectorCommand::helpEnablefwrite(int action) { return os.str(); } -std::string slsDetectorCommand::cmdOverwrite(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdOverwrite(int narg, const char * const args[], int action, int detPos) { int i; char ans[100]; myDet->setReceiverOnline(ONLINE_FLAG, detPos); @@ -2707,7 +2707,7 @@ std::string slsDetectorCommand::helpOverwrite(int action) { return os.str(); } -std::string slsDetectorCommand::cmdFileIndex(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdFileIndex(int narg, const char * const args[], int action, int detPos) { myDet->setReceiverOnline(ONLINE_FLAG, detPos); if (action == HELP_ACTION) { return helpFileName(action); @@ -2727,7 +2727,7 @@ std::string slsDetectorCommand::helpFileIndex(int action) { return os.str(); } -std::string slsDetectorCommand::cmdRateCorr(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdRateCorr(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) { return helpRateCorr(action); @@ -2754,7 +2754,7 @@ std::string slsDetectorCommand::helpRateCorr(int action) { return os.str(); } -// std::string slsDetectorCommand::cmdThreaded(int narg, char *args[], int action, int detPos){ +// std::string slsDetectorCommand::cmdThreaded(int narg, const char * const args[], int action, int detPos){ // int ival; // char answer[1000]; @@ -2780,7 +2780,7 @@ std::string slsDetectorCommand::helpThreaded(int action) { return os.str(); } -std::string slsDetectorCommand::cmdImage(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdImage(int narg, const char * const args[], int action, int detPos) { std::string sval; int retval = FAIL; if (action == HELP_ACTION) @@ -2815,7 +2815,7 @@ std::string slsDetectorCommand::helpImage(int action) { return os.str(); } -std::string slsDetectorCommand::cmdCounter(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdCounter(int narg, const char * const args[], int action, int detPos) { int ival; char answer[100]; std::string sval; @@ -2876,7 +2876,7 @@ std::string slsDetectorCommand::helpCounter(int action) { return os.str(); } -std::string slsDetectorCommand::cmdNetworkParameter(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdNetworkParameter(int narg, const char * const args[], int action, int detPos) { char ans[100] = {0}; int i; @@ -3127,7 +3127,7 @@ std::string slsDetectorCommand::helpNetworkParameter(int action) { return os.str(); } -std::string slsDetectorCommand::cmdPort(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdPort(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpPort(action); @@ -3175,7 +3175,7 @@ std::string slsDetectorCommand::helpPort(int action) { return os.str(); } -std::string slsDetectorCommand::cmdLock(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdLock(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpLock(action); @@ -3226,7 +3226,7 @@ std::string slsDetectorCommand::helpLock(int action) { return os.str(); } -std::string slsDetectorCommand::cmdLastClient(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdLastClient(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpLastClient(action); @@ -3257,7 +3257,7 @@ std::string slsDetectorCommand::helpLastClient(int action) { return os.str(); } -std::string slsDetectorCommand::cmdOnline(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdOnline(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) { return helpOnline(action); @@ -3341,7 +3341,7 @@ std::string slsDetectorCommand::helpOnline(int action) { return os.str(); } -std::string slsDetectorCommand::cmdConfigureMac(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdConfigureMac(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) { return helpConfigureMac(action); @@ -3372,7 +3372,7 @@ std::string slsDetectorCommand::helpConfigureMac(int action) { return os.str(); } -std::string slsDetectorCommand::cmdDetectorSize(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdDetectorSize(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpDetectorSize(action); @@ -3489,7 +3489,7 @@ std::string slsDetectorCommand::helpDetectorSize(int action) { return os.str(); } -std::string slsDetectorCommand::cmdSettings(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdSettings(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpSettings(action); @@ -3607,7 +3607,7 @@ std::string slsDetectorCommand::helpSettings(int action) { return os.str(); } -std::string slsDetectorCommand::cmdSN(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdSN(int narg, const char * const args[], int action, int detPos) { char answer[1000]; @@ -3700,7 +3700,7 @@ std::string slsDetectorCommand::helpSN(int action) { return os.str(); } -std::string slsDetectorCommand::cmdDigiTest(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdDigiTest(int narg, const char * const args[], int action, int detPos) { char answer[1000]; @@ -3751,7 +3751,7 @@ std::string slsDetectorCommand::helpDigiTest(int action) { return os.str(); } -std::string slsDetectorCommand::cmdRegister(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdRegister(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpRegister(action); @@ -3869,7 +3869,7 @@ std::string slsDetectorCommand::helpRegister(int action) { return os.str(); } -std::string slsDetectorCommand::cmdDAC(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdDAC(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpDAC(action); @@ -4215,7 +4215,7 @@ std::string slsDetectorCommand::helpDAC(int action) { return os.str(); } -std::string slsDetectorCommand::cmdADC(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdADC(int narg, const char * const args[], int action, int detPos) { dacIndex adc; int idac; @@ -4342,7 +4342,7 @@ std::string slsDetectorCommand::helpADC(int action) { return os.str(); } -std::string slsDetectorCommand::cmdTempControl(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdTempControl(int narg, const char * const args[], int action, int detPos) { char answer[1000] = ""; int val = -1; @@ -4409,7 +4409,7 @@ std::string slsDetectorCommand::helpTempControl(int action) { return os.str(); } -std::string slsDetectorCommand::cmdTiming(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdTiming(int narg, const char * const args[], int action, int detPos) { #ifdef VERBOSE std::cout << std::string("Executing command ") + std::string(args[0]) + std::string(" ( ") + cmd + std::string(" )\n"); #endif @@ -4435,7 +4435,7 @@ std::string slsDetectorCommand::helpTiming(int action) { return os.str(); } -std::string slsDetectorCommand::cmdTimer(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdTimer(int narg, const char * const args[], int action, int detPos) { timerIndex index; int64_t t = -1, ret; double val, rval; @@ -4565,7 +4565,7 @@ std::string slsDetectorCommand::helpTimer(int action) { return os.str(); } -std::string slsDetectorCommand::cmdTimeLeft(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdTimeLeft(int narg, const char * const args[], int action, int detPos) { timerIndex index; int64_t ret; double rval; @@ -4635,7 +4635,7 @@ std::string slsDetectorCommand::helpTimeLeft(int action) { return os.str(); } -std::string slsDetectorCommand::cmdSpeed(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdSpeed(int narg, const char * const args[], int action, int detPos) { speedVariable index; int t = -1, ret = 0, mode = 0; @@ -4732,7 +4732,7 @@ std::string slsDetectorCommand::helpSpeed(int action) { return os.str(); } -std::string slsDetectorCommand::cmdAdvanced(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdAdvanced(int narg, const char * const args[], int action, int detPos) { char answer[1000] = ""; @@ -4970,7 +4970,7 @@ std::string slsDetectorCommand::helpAdvanced(int action) { return os.str(); } -std::string slsDetectorCommand::cmdConfiguration(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdConfiguration(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpConfiguration(action); @@ -5040,7 +5040,7 @@ std::string slsDetectorCommand::helpConfiguration(int action) { return os.str(); } -std::string slsDetectorCommand::cmdReceiver(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdReceiver(int narg, const char * const args[], int action, int detPos) { char answer[100]; int ival = -1; @@ -5288,7 +5288,7 @@ std::string slsDetectorCommand::helpPattern(int action) { return os.str(); } -std::string slsDetectorCommand::cmdPattern(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdPattern(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpPattern(action); @@ -5758,7 +5758,7 @@ std::string slsDetectorCommand::helpPulse(int action) { return os.str(); } -std::string slsDetectorCommand::cmdPulse(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdPulse(int narg, const char * const args[], int action, int detPos) { int retval = FAIL; if (action == HELP_ACTION) @@ -5820,7 +5820,7 @@ std::string slsDetectorCommand::helpProcessor(int action) { return os.str(); } -std::string slsDetectorCommand::cmdProcessor(int narg, char *args[], int action, int detPos) { +std::string slsDetectorCommand::cmdProcessor(int narg, const char * const args[], int action, int detPos) { if (action == HELP_ACTION) return helpProcessor(action); diff --git a/slsSupportLib/include/CmdLineParser.h b/slsSupportLib/include/CmdLineParser.h index 8066438d3..245f8ad26 100755 --- a/slsSupportLib/include/CmdLineParser.h +++ b/slsSupportLib/include/CmdLineParser.h @@ -10,14 +10,13 @@ class CmdLineParser { void Parse(const std::string &s); void Print(); - //getters int multi_id() const { return multi_id_; }; int detector_id() const { return detector_id_; }; int n_arguments() const { return arguments_.size(); } const std::string &command() const { return command_; } const std::string &executable() const { return executable_; } const std::vector &arguments() const { return arguments_; }; - std::vector argv(); + std::vector argv() const; private: void DecodeIdAndPosition(const char *c); diff --git a/slsSupportLib/src/CmdLineParser.cpp b/slsSupportLib/src/CmdLineParser.cpp index 9ede50612..23a6a8950 100755 --- a/slsSupportLib/src/CmdLineParser.cpp +++ b/slsSupportLib/src/CmdLineParser.cpp @@ -5,10 +5,11 @@ #include #include #include -//printing function for debugging + void CmdLineParser::Print() { std::cout << "\nCmdLineParser::Print()\n"; - std::cout << "\tmulti_id: " << multi_id_ << ", detector_id: " << detector_id_ << std::endl; + std::cout << "\tmulti_id: " << multi_id_ + << ", detector_id: " << detector_id_ << std::endl; std::cout << "\texecutable: " << executable_ << '\n'; std::cout << "\tcommand: " << command_ << '\n'; std::cout << "\tn_arguments: " << n_arguments() << '\n'; @@ -20,26 +21,21 @@ void CmdLineParser::Print() { }; void CmdLineParser::Parse(int argc, char *argv[]) { - //first element of argv is the command used to call the executable ->skipping - //and if this is the only command skip all - executable_ = argv[0]; + executable_ = argv[0]; //first arg is calling binary if (argc > 1) { - //second element is cmd string that needs to be decoded DecodeIdAndPosition(argv[1]); - //The rest of the arguments goes into a vector for later processing for (int i = 2; i < argc; ++i) { - arguments_.emplace_back(std::string(argv[i])); + arguments_.emplace_back(argv[i]); } } -}; +} void CmdLineParser::Parse(const std::string &s) { std::istringstream iss(s); auto it = std::istream_iterator(iss); - //read the first element and increment command_ = *it++; - arguments_ = std::vector(it, std::istream_iterator()); - ; + arguments_ = + std::vector(it, std::istream_iterator()); DecodeIdAndPosition(command_.c_str()); } @@ -51,19 +47,23 @@ void CmdLineParser::DecodeIdAndPosition(const char *c) { if (contains_id && contains_pos) { int r = sscanf(c, "%d-%d:%s", &multi_id_, &detector_id_, tmp); if (r != 3) { - throw(std::invalid_argument("Cannot decode client or detector id from: \"" + std::string(c) + "\"\n")); + throw(std::invalid_argument( + "Cannot decode client or detector id from: \"" + + std::string(c) + "\"\n")); } command_ = tmp; } else if (contains_id && !contains_pos) { int r = sscanf(c, "%d-%s", &multi_id_, tmp); if (r != 2) { - throw(std::invalid_argument("Cannot decode client id from: \"" + std::string(c) + "\"\n")); + throw(std::invalid_argument("Cannot decode client id from: \"" + + std::string(c) + "\"\n")); } command_ = tmp; } else if (!contains_id && contains_pos) { int r = sscanf(c, "%d:%s", &detector_id_, tmp); if (r != 2) { - throw(std::invalid_argument("Cannot decode detector id from: \"" + std::string(c) + "\"\n")); + throw(std::invalid_argument("Cannot decode detector id from: \"" + + std::string(c) + "\"\n")); } command_ = tmp; } else { @@ -71,12 +71,11 @@ void CmdLineParser::DecodeIdAndPosition(const char *c) { } } -std::vector CmdLineParser::argv() { - std::vector vec; - if (command_.empty()!=true){ +std::vector CmdLineParser::argv() const { + std::vector vec; + if (command_.empty() != true) { vec.push_back(&command_.front()); } - for (auto &arg : arguments_) { vec.push_back(&arg.front()); } diff --git a/slsSupportLib/tests/test-CmdLineParser.cpp b/slsSupportLib/tests/test-CmdLineParser.cpp index df4c3e27a..5cb4aaa9c 100755 --- a/slsSupportLib/tests/test-CmdLineParser.cpp +++ b/slsSupportLib/tests/test-CmdLineParser.cpp @@ -2,13 +2,124 @@ #include "catch.hpp" #include #include -//tests to add -//help for all docs -//command for all depreciated commands +// tests to add +// help for all docs +// command for all depreciated commands -TEST_CASE("Parse with no arguments results in no command and default id") { - //build up argc and argv - //first argument is the command used to call the binary +using vs = std::vector; + +SCENARIO("Construction", "[support]") { + GIVEN("A default constructed CmdLineParser") { + CmdLineParser p; + THEN("The state of the object is valid") { + REQUIRE(p.detector_id() == -1); + REQUIRE(p.multi_id() == 0); + REQUIRE(p.command().empty()); + REQUIRE(p.arguments().empty()); + REQUIRE(p.argv().empty()); + REQUIRE(p.argv().data() == nullptr); + } + } +} + +SCENARIO("Parsing a string with the command line parser", "[support]") { + GIVEN("A CmdLineParser") { + CmdLineParser p; + WHEN("Parsing an empty string") { + std::string s; + p.Parse(s); + THEN("command and arguments are empty") { + REQUIRE(p.detector_id() == -1); + REQUIRE(p.multi_id() == 0); + REQUIRE(p.command().empty()); + REQUIRE(p.arguments().empty()); + REQUIRE(p.argv().empty()); + } + } + WHEN("Parsing a string with a single command") { + std::string s = "vrf"; + p.Parse(s); + THEN("command is assigned and id's remain default") { + REQUIRE(p.command() == "vrf"); + REQUIRE(p.detector_id() == -1); + REQUIRE(p.multi_id() == 0); + REQUIRE(p.arguments().empty()); + REQUIRE(p.argv().size() == 1); + } + } + WHEN("Parsing a string with command and value") { + std::string s = "vthreshold 1500"; + p.Parse(s); + THEN("cmd and value are assigned and id's remain default") { + REQUIRE(p.command() == "vthreshold"); + REQUIRE(p.arguments()[0] == "1500"); + REQUIRE(p.arguments().size() == 1); + REQUIRE(p.detector_id() == -1); + REQUIRE(p.multi_id() == 0); + } + } + WHEN("Parsing a string with detector id and command") { + vs arg{"9:vcp", "53:vthreshold", "128:vtrim", "5:threshold"}; + std::vector det_id{9, 53, 128, 5}; + vs res{"vcp", "vthreshold", "vtrim", "threshold"}; + + THEN("Values are correctly decoded") { + for (size_t i = 0; i != arg.size(); ++i) { + p.Parse(arg[i]); + REQUIRE(p.detector_id() == det_id[i]); + REQUIRE(p.multi_id() == 0); + REQUIRE(p.command() == res[i]); + REQUIRE(p.arguments().empty()); + REQUIRE(p.argv().size() == 1); + } + } + } + WHEN("Parsing a string with multi_id detector id and command") { + vs arg{"8-12:vrf", "0-52:vcmp", "19-10:vtrim", "31-127:threshold"}; + std::vector det_id{12, 52, 10, 127}; + std::vector multi_id{8, 0, 19, 31}; + vs res{"vrf", "vcmp", "vtrim", "threshold"}; + + THEN("Values are correctly decoded") { + for (size_t i = 0; i != arg.size(); ++i) { + p.Parse(arg[i]); + REQUIRE(p.detector_id() == det_id[i]); + REQUIRE(p.multi_id() == multi_id[i]); + REQUIRE(p.command() == res[i]); + REQUIRE(p.arguments().empty()); + REQUIRE(p.argv().size() == 1); + } + } + } + + WHEN("Parsing string with cmd and multiple arguments"){ + std::string s = "trimen 5000 6000 7000"; + p.Parse(s); + THEN("cmd and args are correct"){ + REQUIRE(p.command() == "trimen"); + REQUIRE(p.arguments().size() == 3); + REQUIRE(p.arguments()[0] == "5000"); + REQUIRE(p.arguments()[1] == "6000"); + REQUIRE(p.arguments()[2] == "7000"); + } + } + + WHEN("Cliend id and or detector id cannot be decoded") { + vs arg{"o:cmd", "-5:cmd", "aedpva:cmd", + "5-svc:vrf", "asv-5:cmd", "savc-asa:cmd"}; + THEN("Parsing Throws") { + for (size_t i = 0; i != arg.size(); ++i) { + REQUIRE_THROWS(p.Parse(arg[i])); + } + } + } + } +} + +TEST_CASE("Parse with no arguments results in no command and default id", + "[support]") { + // build up argc and argv + // first argument is the command used to call the binary int argc = 1; char *argv[argc]; char a0[] = "call"; @@ -23,18 +134,9 @@ TEST_CASE("Parse with no arguments results in no command and default id") { REQUIRE(p.arguments().empty()); } -TEST_CASE("Parse empty string") { - std::string s; - CmdLineParser p; - p.Parse(s); - - REQUIRE(p.detector_id() == -1); - REQUIRE(p.multi_id() == 0); - REQUIRE(p.command().empty()); - REQUIRE(p.arguments().empty()); -} - -TEST_CASE("Parse a command without client id and detector id results in default") { +TEST_CASE( + "Parse a command without client id and detector id results in default", + "[support]") { int argc = 2; char *argv[argc]; char a0[] = "call"; @@ -51,18 +153,8 @@ TEST_CASE("Parse a command without client id and detector id results in default" REQUIRE(p.arguments().empty()); } -TEST_CASE("Parse a string without client id and detector id results in default") { - std::string s = "vrf"; - CmdLineParser p; - p.Parse(s); - - REQUIRE(p.detector_id() == -1); - REQUIRE(p.multi_id() == 0); - REQUIRE(p.command() == "vrf"); - REQUIRE(p.arguments().empty()); -} - -TEST_CASE("Parse a command with value but without client or detector id") { +TEST_CASE("Parse a command with value but without client or detector id", + "[support]") { int argc = 3; char *argv[argc]; char a0[] = "call"; @@ -81,18 +173,6 @@ TEST_CASE("Parse a command with value but without client or detector id") { REQUIRE(p.arguments().size() == 1); REQUIRE(p.arguments()[0] == "3000"); } -TEST_CASE("Parse a string with value but without client or detector id") { - std::string s = "vrf 3000\n"; - - CmdLineParser p; - p.Parse(s); - - REQUIRE(p.detector_id() == -1); - REQUIRE(p.multi_id() == 0); - REQUIRE(p.command() == "vrf"); - REQUIRE(p.arguments().size() == 1); - REQUIRE(p.arguments()[0] == "3000"); -} TEST_CASE("Decodes position") { int argc = 2; @@ -110,19 +190,8 @@ TEST_CASE("Decodes position") { REQUIRE(p.command() == "vrf"); REQUIRE(p.arguments().empty()); } -TEST_CASE("Decodes position from string") { - std::string s = "7:vrf\n"; - CmdLineParser p; - p.Parse(s); - - REQUIRE(p.detector_id() == 7); - REQUIRE(p.multi_id() == 0); - REQUIRE(p.command() == "vrf"); - REQUIRE(p.arguments().empty()); -} - -TEST_CASE("Decodes double digit position") { +TEST_CASE("Decodes double digit position", "[support]") { int argc = 2; char *argv[argc]; char a0[] = "call"; @@ -139,19 +208,7 @@ TEST_CASE("Decodes double digit position") { REQUIRE(p.arguments().empty()); } -TEST_CASE("Decodes double digit position from string") { - - std::string s = "73:vcmp"; - CmdLineParser p; - p.Parse(s); - - REQUIRE(p.detector_id() == 73); - REQUIRE(p.multi_id() == 0); - REQUIRE(p.command() == "vcmp"); - REQUIRE(p.arguments().empty()); -} - -TEST_CASE("Decodes position and id") { +TEST_CASE("Decodes position and id", "[support]") { int argc = 2; char *argv[argc]; char a0[] = "call"; @@ -167,18 +224,8 @@ TEST_CASE("Decodes position and id") { REQUIRE(p.command() == "vrf"); REQUIRE(p.arguments().empty()); } -TEST_CASE("Decodes position and id from string") { - std::string s = "5-8:vrf"; - CmdLineParser p; - p.Parse(s); - REQUIRE(p.detector_id() == 8); - REQUIRE(p.multi_id() == 5); - REQUIRE(p.command() == "vrf"); - REQUIRE(p.arguments().empty()); -} - -TEST_CASE("Double digit id") { +TEST_CASE("Double digit id", "[support]") { int argc = 2; char *argv[argc]; char a0[] = "call"; @@ -195,18 +242,7 @@ TEST_CASE("Double digit id") { REQUIRE(p.arguments().empty()); } -TEST_CASE("Double digit id from string") { - std::string s = "56-8:vrf"; - CmdLineParser p; - p.Parse(s); - - REQUIRE(p.detector_id() == 8); - REQUIRE(p.multi_id() == 56); - REQUIRE(p.command() == std::string("vrf")); - REQUIRE(p.arguments().empty()); -} - -TEST_CASE("Calling with wrong id throws invalid_argument") { +TEST_CASE("Calling with wrong id throws invalid_argument", "[support]") { int argc = 2; char *argv[argc]; @@ -218,13 +254,8 @@ TEST_CASE("Calling with wrong id throws invalid_argument") { CmdLineParser p; CHECK_THROWS(p.Parse(argc, argv)); } -TEST_CASE("Calling with string with wrong id throws invalid_argument") { - std::string s = "asvldkn:vrf"; - CmdLineParser p; - CHECK_THROWS(p.Parse(s)); -} -TEST_CASE("Calling with wrong client throws invalid_argument") { +TEST_CASE("Calling with wrong client throws invalid_argument", "[support]") { int argc = 2; char *argv[argc]; char a0[] = "call"; @@ -235,26 +266,9 @@ TEST_CASE("Calling with wrong client throws invalid_argument") { CmdLineParser p; CHECK_THROWS(p.Parse(argc, argv)); } -TEST_CASE("Calling with string with wrong client throws invalid_argument") { - std::string s = "lki-3:vrf"; - CmdLineParser p; - CHECK_THROWS(p.Parse(s)); -} -TEST_CASE("Parses string with two arguments") { - std::string s = "trimen 3000 4000\n"; +TEST_CASE("Build up argv", "[support]") { CmdLineParser p; - p.Parse(s); - - REQUIRE("trimen" == p.command()); - REQUIRE("3000" == p.arguments()[0]); - REQUIRE("4000" == p.arguments()[1]); - REQUIRE(p.arguments().size() == 2); -} - -TEST_CASE("Build up argv"){ - CmdLineParser p; - // p.argv(); REQUIRE(p.argv().empty()); REQUIRE(p.argv().data() == nullptr); @@ -262,5 +276,4 @@ TEST_CASE("Build up argv"){ p.Parse(s); REQUIRE(p.argv().data() != nullptr); REQUIRE(p.argv().size() == 3); - } \ No newline at end of file From 591ff53b84ca013a62337d451812281274d3d21e Mon Sep 17 00:00:00 2001 From: Erik Frojdh Date: Fri, 17 May 2019 09:08:13 +0200 Subject: [PATCH 2/8] fixed MacAddr 0 output --- slsSupportLib/src/network_utils.cpp | 18 ++++++------------ slsSupportLib/tests/test-network_utils.cpp | 4 ++-- 2 files changed, 8 insertions(+), 14 deletions(-) diff --git a/slsSupportLib/src/network_utils.cpp b/slsSupportLib/src/network_utils.cpp index 6147cfb19..6c3e25caa 100755 --- a/slsSupportLib/src/network_utils.cpp +++ b/slsSupportLib/src/network_utils.cpp @@ -20,9 +20,7 @@ IpAddr::IpAddr(const std::string &address) { inet_pton(AF_INET, address.c_str(), &addr_); } -IpAddr::IpAddr(const char *address) { - inet_pton(AF_INET, address, &addr_); -} +IpAddr::IpAddr(const char *address) { inet_pton(AF_INET, address, &addr_); } std::string IpAddr::str() const { char ipstring[INET_ADDRSTRLEN]{}; @@ -31,9 +29,9 @@ std::string IpAddr::str() const { } std::string IpAddr::hex() const { std::ostringstream ss; + ss << std::hex << std::setfill('0'); for (int i = 0; i != 4; ++i) { - ss << std::hex << std::setfill('0') << std::setw(2) - << ((addr_ >> i * 8) & 0xFF); + ss << std::setw(2) << ((addr_ >> i * 8) & 0xFF); } return ss.str(); } @@ -56,18 +54,14 @@ std::string MacAddr::to_hex(const char delimiter) const { for (int i = 32; i >= 0; i -= 8) { if (delimiter) ss << delimiter; - ss << ((addr_ >> i) & 0xFF); + ss << std::setw(2) << ((addr_ >> i) & 0xFF); } return ss.str(); } -std::string MacAddr::str() const { - return to_hex(':'); -} +std::string MacAddr::str() const { return to_hex(':'); } -std::string MacAddr::hex() const { - return to_hex(); -} +std::string MacAddr::hex() const { return to_hex(); } std::ostream &operator<<(std::ostream &out, const IpAddr &addr) { return out << addr.str(); diff --git a/slsSupportLib/tests/test-network_utils.cpp b/slsSupportLib/tests/test-network_utils.cpp index a9d68ae19..43a08795a 100755 --- a/slsSupportLib/tests/test-network_utils.cpp +++ b/slsSupportLib/tests/test-network_utils.cpp @@ -11,9 +11,9 @@ using namespace sls; TEST_CASE("Convert mac address using classes", "[support]") { - std::vector vec_addr{346856806822, 346856806852, 262027939863028}; + std::vector vec_addr{346856806822, 346856806852, 262027939863028,0, 281474976710655}; std::vector vec_ans{"00:50:c2:46:d9:a6", "00:50:c2:46:d9:c4", - "ee:50:22:46:d9:f4"}; + "ee:50:22:46:d9:f4", "00:00:00:00:00:00", "ff:ff:ff:ff:ff:ff"}; for (size_t i = 0; i != vec_addr.size(); ++i) { auto mac0 = MacAddr(vec_addr[i]); auto mac1 = MacAddr(vec_ans[i]); From 3e5d34647ef4de7a060c091365571bff1df94a56 Mon Sep 17 00:00:00 2001 From: Erik Frojdh Date: Fri, 17 May 2019 10:00:49 +0200 Subject: [PATCH 3/8] updated test for argument parser --- slsSupportLib/include/CmdLineParser.h | 2 +- slsSupportLib/src/CmdLineParser.cpp | 2 +- slsSupportLib/tests/test-CmdLineParser.cpp | 68 ++++------------------ 3 files changed, 13 insertions(+), 59 deletions(-) diff --git a/slsSupportLib/include/CmdLineParser.h b/slsSupportLib/include/CmdLineParser.h index 245f8ad26..af11254d3 100755 --- a/slsSupportLib/include/CmdLineParser.h +++ b/slsSupportLib/include/CmdLineParser.h @@ -6,7 +6,7 @@ class CmdLineParser { public: - void Parse(int argc, char *argv[]); + void Parse(int argc, const char * const argv[]); void Parse(const std::string &s); void Print(); diff --git a/slsSupportLib/src/CmdLineParser.cpp b/slsSupportLib/src/CmdLineParser.cpp index 23a6a8950..cc502978d 100755 --- a/slsSupportLib/src/CmdLineParser.cpp +++ b/slsSupportLib/src/CmdLineParser.cpp @@ -20,7 +20,7 @@ void CmdLineParser::Print() { std::cout << "\n\n"; }; -void CmdLineParser::Parse(int argc, char *argv[]) { +void CmdLineParser::Parse(int argc, const char * const argv[]) { executable_ = argv[0]; //first arg is calling binary if (argc > 1) { DecodeIdAndPosition(argv[1]); diff --git a/slsSupportLib/tests/test-CmdLineParser.cpp b/slsSupportLib/tests/test-CmdLineParser.cpp index 5cb4aaa9c..5a34e7bd5 100755 --- a/slsSupportLib/tests/test-CmdLineParser.cpp +++ b/slsSupportLib/tests/test-CmdLineParser.cpp @@ -92,10 +92,10 @@ SCENARIO("Parsing a string with the command line parser", "[support]") { } } - WHEN("Parsing string with cmd and multiple arguments"){ + WHEN("Parsing string with cmd and multiple arguments") { std::string s = "trimen 5000 6000 7000"; p.Parse(s); - THEN("cmd and args are correct"){ + THEN("cmd and args are correct") { REQUIRE(p.command() == "trimen"); REQUIRE(p.arguments().size() == 3); REQUIRE(p.arguments()[0] == "5000"); @@ -121,10 +121,7 @@ TEST_CASE("Parse with no arguments results in no command and default id", // build up argc and argv // first argument is the command used to call the binary int argc = 1; - char *argv[argc]; - char a0[] = "call"; - argv[0] = static_cast(a0); - + const char* const argv[]{"call"}; CmdLineParser p; p.Parse(argc, argv); @@ -138,12 +135,7 @@ TEST_CASE( "Parse a command without client id and detector id results in default", "[support]") { int argc = 2; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "vrf"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); - + const char*const argv[]{"caller", "vrf"}; CmdLineParser p; p.Parse(argc, argv); @@ -156,14 +148,7 @@ TEST_CASE( TEST_CASE("Parse a command with value but without client or detector id", "[support]") { int argc = 3; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "vrf"; - char a2[] = "3000"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); - argv[2] = static_cast(a2); - + const char* const argv[]{"caller", "vrf", "3000"}; CmdLineParser p; p.Parse(argc, argv); @@ -176,11 +161,7 @@ TEST_CASE("Parse a command with value but without client or detector id", TEST_CASE("Decodes position") { int argc = 2; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "7:vrf"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); + const char*const argv[]{"caller", "7:vrf"}; CmdLineParser p; p.Parse(argc, argv); @@ -193,12 +174,7 @@ TEST_CASE("Decodes position") { TEST_CASE("Decodes double digit position", "[support]") { int argc = 2; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "73:vcmp"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); - + const char* const argv[]{"caller", "73:vcmp"}; CmdLineParser p; p.Parse(argc, argv); @@ -210,12 +186,7 @@ TEST_CASE("Decodes double digit position", "[support]") { TEST_CASE("Decodes position and id", "[support]") { int argc = 2; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "5-8:vrf"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); - + const char* const argv[]{"caller", "5-8:vrf"}; CmdLineParser p; p.Parse(argc, argv); @@ -227,15 +198,9 @@ TEST_CASE("Decodes position and id", "[support]") { TEST_CASE("Double digit id", "[support]") { int argc = 2; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "56-8:vrf"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); - + const char *const argv[]{"caller", "56-8:vrf"}; CmdLineParser p; p.Parse(argc, argv); - REQUIRE(p.detector_id() == 8); REQUIRE(p.multi_id() == 56); REQUIRE(p.command() == "vrf"); @@ -243,26 +208,15 @@ TEST_CASE("Double digit id", "[support]") { } TEST_CASE("Calling with wrong id throws invalid_argument", "[support]") { - int argc = 2; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "asvldkn:vrf"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); - + const char *const argv[]{"caller", "asvldkn:vrf"}; CmdLineParser p; CHECK_THROWS(p.Parse(argc, argv)); } TEST_CASE("Calling with wrong client throws invalid_argument", "[support]") { int argc = 2; - char *argv[argc]; - char a0[] = "call"; - char a1[] = "lki-3:vrf"; - argv[0] = static_cast(a0); - argv[1] = static_cast(a1); - + const char *const argv[]{"caller", "lki-3:vrf"}; CmdLineParser p; CHECK_THROWS(p.Parse(argc, argv)); } From 1a1c6b9b4223d5913fbaeb650debcf0bcf0eaa8c Mon Sep 17 00:00:00 2001 From: Dhanya Thattil Date: Fri, 17 May 2019 19:19:03 +0200 Subject: [PATCH 4/8] jungfrau server: feature finish: switching between 2 interfaces --- .../jungfrauDetectorServer/RegisterDefs.h | 48 ++- .../bin/jungfrauDetectorServer_developer | Bin 0 -> 120136 bytes .../bin/jungfrauDetectorServer_refactor | Bin 115588 -> 0 bytes .../slsDetectorFunctionList.c | 308 ++++++++++++------ .../slsDetectorServer_defs.h | 57 ++-- .../slsDetectorServer/communication_funcs.c | 5 +- .../slsDetectorServer/communication_funcs.h | 1 + .../slsDetectorFunctionList.h | 7 + .../slsDetectorServer_funcs.c | 17 +- .../include/slsDetectorUsers.h | 2 +- slsDetectorSoftware/src/slsDetector.cpp | 2 +- .../src/slsDetectorCommand.cpp | 17 +- slsReceiverSoftware/include/GeneralData.h | 8 +- slsReceiverSoftware/src/Listener.cpp | 11 +- slsSupportLib/include/versionAPI.h | 5 +- 15 files changed, 312 insertions(+), 176 deletions(-) create mode 100755 slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_developer delete mode 100755 slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_refactor diff --git a/slsDetectorServers/jungfrauDetectorServer/RegisterDefs.h b/slsDetectorServers/jungfrauDetectorServer/RegisterDefs.h index 0129d8be9..e25b1942f 100755 --- a/slsDetectorServers/jungfrauDetectorServer/RegisterDefs.h +++ b/slsDetectorServers/jungfrauDetectorServer/RegisterDefs.h @@ -197,15 +197,16 @@ #define CONFIG_RDT_TMR_MSK (0x0000FFFF << CONFIG_RDT_TMR_OFST) #define CONFIG_OPRTN_MDE_2_X_10GbE_OFST (16) #define CONFIG_OPRTN_MDE_2_X_10GbE_MSK (0x00000001 << CONFIG_OPRTN_MDE_2_X_10GbE_OFST) -#define CONFIG_OPRTN_MDE_1_X_10GBE_VAL ((0x0 << CONFIG_OPRTN_MDE_2_X_10GbE_OFST) & CONFIG_OPRTN_MDE_2_X_10GbE_MSK) +// if 0, outer is the primary interface +#define CONFIG_INNR_PRIMRY_INTRFCE_OFST (17) +#define CONFIG_INNR_PRIMRY_INTRFCE_MSK (0x00000001 << CONFIG_INNR_PRIMRY_INTRFCE_OFST) #define CONFIG_READOUT_SPEED_OFST (20) #define CONFIG_READOUT_SPEED_MSK (0x00000003 << CONFIG_READOUT_SPEED_OFST) #define CONFIG_QUARTER_SPEED_10MHZ_VAL ((0x0 << CONFIG_READOUT_SPEED_OFST) & CONFIG_READOUT_SPEED_MSK) #define CONFIG_HALF_SPEED_20MHZ_VAL ((0x1 << CONFIG_READOUT_SPEED_OFST) & CONFIG_READOUT_SPEED_MSK) #define CONFIG_FULL_SPEED_40MHZ_VAL ((0x2 << CONFIG_READOUT_SPEED_OFST) & CONFIG_READOUT_SPEED_MSK) -#define CONFIG_TDMA_OFST (24) -#define CONFIG_TDMA_MSK (0x00000001 << CONFIG_TDMA_OFST) -#define CONFIG_TDMA_DISABLE_VAL ((0x0 << CONFIG_TDMA_OFST) & CONFIG_TDMA_MSK) +#define CONFIG_TDMA_ENABLE_OFST (24) +#define CONFIG_TDMA_ENABLE_MSK (0x00000001 << CONFIG_TDMA_ENABLE_OFST) #define CONFIG_TDMA_TIMESLOT_OFST (25) // 1ms #define CONFIG_TDMA_TIMESLOT_MSK (0x0000001F << CONFIG_TDMA_TIMESLOT_OFST) #define CONFIG_ETHRNT_FLW_CNTRL_OFST (31) @@ -234,6 +235,12 @@ #define CONTROL_ACQ_FIFO_CLR_MSK (0x00000001 << CONTROL_ACQ_FIFO_CLR_OFST) #define CONTROL_STORAGE_CELL_NUM_OFST (16) #define CONTROL_STORAGE_CELL_NUM_MSK (0x0000000F << CONTROL_STORAGE_CELL_NUM_OFST) +#define CONTROL_RX_ADDTNL_ENDPTS_NUM_OFST (20) +#define CONTROL_RX_ADDTNL_ENDPTS_NUM_MSK (0x0000003F << CONTROL_RX_ADDTNL_ENDPTS_NUM_OFST) +#define CONTROL_RX_ENDPTS_START_OFST (26) +#define CONTROL_RX_ENDPTS_START_MSK (0x0000003F << CONTROL_RX_ENDPTS_START_OFST) + + /* Reconfiguratble PLL Paramater Register */ #define PLL_PARAM_REG (0x50 << MEM_MAP_SHIFT) @@ -400,6 +407,32 @@ #define COORD_0_Z_OFST (0) #define COORD_0_Z_MSK (0x0000FFFF << COORD_0_Z_OFST) +/** Module row coordinates */ +/*#define COORD_ROW_REG (0x7C << MEM_MAP_SHIFT) + +#define COORD_ROW_OUTER_OFST (0) +#define COORD_ROW_OUTER_MSK (0x0000FFFF << COORD_ROW_OUTER_OFST) +#define COORD_ROW_INNER_OFST (16) +#define COORD_ROW_INNER_MSK (0x0000FFFF << COORD_ROW_INNER_OFST) +*/ +/** Module column coordinates */ +/*#define COORD_COL_REG (0x7D << MEM_MAP_SHIFT) + +#define COORD_COL_OUTER_OFST (0) +#define COORD_COL_OUTER_MSK (0x0000FFFF << COORD_COL_OUTER_OFST) +#define COORD_COL_INNER_OFST (16) +#define COORD_COL_INNER_MSK (0x0000FFFF << COORD_COL_INNER_OFST) +*/ + +/** Module column coordinates */ +/*#define COORD_RESERVED_REG (0x7E << MEM_MAP_SHIFT) + +#define COORD_RESERVED_OUTER_OFST (0) +#define COORD_RESERVED_OUTER_MSK (0x0000FFFF << COORD_RESERVED_OUTER_OFST) +#define COORD_RESERVED_INNER_OFST (16) +#define COORD_RESERVED_INNER_MSK (0x0000FFFF << COORD_RESERVED_INNER_OFST) +*/ + /* ASIC Control Register */ #define ASIC_CTRL_REG (0x7F << MEM_MAP_SHIFT) // tPC = (PCT + 1) * 25ns @@ -440,6 +473,13 @@ +/* Round Robin */ +#define RXR_ENDPOINTS_MAX (64) +#define RXR_ENDPOINT_OUTER_START_REG (0x1000 << MEM_MAP_SHIFT) +#define RXR_ENDPOINT_INNER_START_REG (0x2000 << MEM_MAP_SHIFT) + +#define RXR_ENDPOINT_OFST (0x10 << MEM_MAP_SHIFT) + diff --git a/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_developer b/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_developer new file mode 100755 index 0000000000000000000000000000000000000000..4ed0aa93cc99c6c020c29704c1b22141716868f5 GIT binary patch literal 120136 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

vuJ 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 literal 0 HcmV?d00001 diff --git a/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_refactor b/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_refactor deleted file mode 100755 index ab33ee12141a07fc122e4f0cda489f74cda48799..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 115588 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

vF1J>&4_=b(~LOa%4KVU6_^!`_IrYH zod3u7Fe_onDE0EF3U)L8{&?6@KpYD=*hRok_Wdm1ENs%KVdY1qJq&8tClWR88b%{} zKpWAcu@QY(8`0TJ(lFi*jLZCWz<6z_g5_i0=<{%!l1(!)yKrXrjA6`C!~2|Q_ti9` z@GS`^PgOrv;K!I9!U(4OEUHbt4!Def1euIdI_+n(M?>4$)KF`-QP?5gz??M?u$wUY zcS=>nH^*Run$23Y6=<`f}1^Rq0 z`(ZYlrJ?@AuHon<^}2%nESoT#$iF?j&_{EoIvbjz&n(>Pj*mmSM<0i%2Wu_(YxICK zJ{a5=><*mqfNC?GYKpoj+bra|cCzU#5%3SVblNYGa@4+KzT;gu1nU zP%nJI`dai)pE;^a$2ie-p?V>UV8t!x2)0?x%%*vi&7U1kn8oLmm`(HXbN2$~$4q-Z zR1x}o5R1jYVl}Y1Z4iqY+1lFX7fIXMiv`Y!d#jB0<*t6!Vc(>U!ZWe8@=bHE3-h2N zxLaGLH1Ea_;;ql6UD^7oUNw3;YhY)K(~1J+4NNN95GeI5W}}Oq34`! zZJZt*PkbPe|AqT9bsENV>bu#r25GF8jVD@t?4Hf)fZbEUsliQyD^|z9*_X_I4~(!Q-OY@vO%p7)9F{3*2i>N+6zrdi+RFHwq+h`n7#03UQ2-i=;Ue8X<0)Q@5@mDxswZ!y zRl2{d@ij-dAJVY#U^arm%?&nrQLI)ycMi51P= z`OHu*!VcL6J7nAaWP^mb8_w4%s8$9>fhhv1~cELq5A|#VEXjzxQ{WRf~E}-BKU5W3Ho?{^WZCHp5ea zUyO3Hwt^Q=_e3YMQSzFu#@Eb87I$&n`tGr?8P39H*p(&gL5@&&)LR2=CQeU3*8Q3qo$FYbnRhg&U>TpfT9Cj-|HjO*N?R~nN<1Q{5k2`6R zXMi%tVU5ZBXn*P|75d@}jVCLiryF>_MtB}YkLlTc356`)(;Pupff+)5R^*bc)c%vmq?vL`x@jUEQxadAcC!GW-${9^I2sqNh_bib9|(bZx1yT0h!)wM9V9qrH@ z=?vb(F4nHIdt9lGuq%}xFKrAN*d*UD_78P$?G0>ps1ZTQvRNzrua9?Y&u-J675m?s zwc2mY&f?Fyzv@bIMAA>edTlGHXOCoC9H&PU{Z2xA8191n<=42^_!1pKmjSwZf{#~c zu%-~{II?Gb*R(Qy#ieBDvsW?eHo%^e;5j(gbu+ZClfFyU3t;2criZfA9g|(@e3kpt zt`_@Eo^xG)^Yy7l`!tC(x=>6?-NM%RZH$qAgqVuKIK>~CWz;lY@&?#6jkgPZZwyXi zy91*wWnNQ9j5uyW`HE1(zLSY8Ufz{Oqy?|;E3Xx!vf^sDhIct6KY-bJ-Ir#|+CuF)3_;Ie`_OY&C@HWpajtti=xYK%%eVmw!5$UUr+u@bW1HNc78if;X zAHH!$g7aQFJclj=toq9qd#-TW&8z*s5X*9$cUQ9C*pF#8ziz+laDJP9uKEoh!J%)j z!6xgqFeb(1nxT{=njMl&QYbRh_?o@p{4Nf0pnPGptB_4Vy%x_@;qRlSvNyYN)|34W z+z0)9?P=8qDVI8itexu>lO}I+Amt?GgKlG;OOtXl`J1Jwti6CNywR}mbUA0P%Tz`d zf7Ja(rLnHB`a7DWvq91&g)ixn4qlL?hHOYWqmbpAi1rITX5q2$+l=)z7a06e z!{Marw!fD)77}lz-=blF8%ou5S;tzJc@a(KHQQRSpH{MMgM=a7!+{eJpN7oyghy$( z@tVwQgv@(@?VL3nvhFNo-P!wp#Ljh*ygM}8HZjBzE;>|B_1a|HhmcYh)vTWJIn0mrf$9OY+j1ODevb!w%^LFDr!8qVr_;}S=qEdTZU#{)U^L8d6rTJWeqLA7ZPEmN0Q*9&6hFlKj|y3*^CS!xV5sf^s#4Qsz~N z9~uCEEXOI2?SI11wEwyc>>NYOPs%O@J0nWQ#Bo)&RL)_IY(>%A!H3zOf|8>z53;DS z6&7-C&}t<3b@={ISRtbv_XqFAcboC?;4nxNi!l-Z8;rYyx#eyLYBl5rCF29o8t)H! z%X1-*3L2&t?*m7@qoJU6I^@6m3RxT4{AJ)5o-ezs6K`ZcX8-c-K7BFzMOO;;f>^XCJobt3 zxb008MoE(J{zzRTIaKyLXd|V{l!-U7TcFQ;;x>R6+SK3p+^9*APT`w@(c2Tgct3s# ze*B~K6TZgRtb4IivCRKq?*?$9zMj4ch_ z2%l1szq~wCS>ZoBo}RkUhoz8ZMgHNlR{7Jj^&VIHnw2%+>1N`l@=5t!6@o=&`$={@ukw=6)N|!xO>BWYLU0arHvBAHTrM!b# zRkez|OuNb`qtveP{}hFXziBkzE9Ein4pAxNf310*#(>Yi=bFwYfhY87zNcRgtAO9B zgDqu0xyttx9O8Q#r}>^PTDf^+;d^qy_oVqmH1E@~G#x@N8{xQp(EGGv)Kl;wbik^P zd!H7@yidn8@6(&sxc8}Qi1*2*d7sF)vRCs}eEfg(KK*it_vw}3FvO7`f)#HqBM(&T zfAK&?Vjif5vUjiWK)pZ21NBVt*ZH4*74tv64~j1I=pLd5X*N7W3Ch7L#V(AxpWOy3 z>vrD~))m|^XxZxir}jbr)9nB1fBLEB7fN@J)MS9b7Y%8p)kRv%cham?3V$IsBk$A$Rdj#aPFrqiy#C=r``*(+3 zP)FDgY9stcY=oOMtSe&Ps3zd8`_I;fX2TZGkJ;i2HE-0eL2neNd87USZ&Z#n0lLAH znm1}SMl%iGD62XS>&WH1awOJN1#!5X#ObDfhZ@ z9;t>hn|kUhkJJ+}j}&t+{SS{+XEu%3c8SJoe5~hRKVBbXH^Fy99;rt(PY(5bHfxH( z{>$(?G>_D5cncEXk-FL4!2+6pN%oXzzBdjY!l!~XVx6GnPp$gPe$pWkLT-rQd5Wcq>2Yi&c4DYl?z`+fi?sDu6R%4KB?L4THu|Q-HaZNKo7s` z(nl!Kl?fm4P@j~Xt@~U~4=2px-WyBIC*@~rFgwER+<(C#Kjx8IEM1;|%Uv}8eyMq+ zw#Qb@H_g8;%!8pGscQ$Z)>n2%w!TtUj1B-3-6Iu_d8F=-d8Bd&JyHw5(Id5KyuOC6 zg&*ssP?&uAu{qxz$oKpnymU6}i1E^Wp@lJ@R5<37S_hv~oI2l!PwJg)T8ZS7S`_n1 zfmY~Am~HgMseZLbDu5ade!3Nfyo)palID{NV;pb8Xx*s!q&CHTQr}#*4$|x{-@EWi zS=CwN&sQ(DoP8xe4ZkkRh+Hy}z2dN2U7QwQqgd4Kh!l=88|`)v=@ZfA z)*x9H^dkZHXCdr;(aDzcr4zh#m0mr7qy$n;w@9mFW&OUv6$c0?M8fcnjEKi z*d&ViJ!;Wne&i{+)0Ba>auET$(aeX=tD^k|4I&>}9D zG0zm832g$^E$T@h#qWp~hTycTApdPhye>_I#iyELahG>X4QevmQn;mfV=VUaO!3Cj z-Q^Aqe*X+Tig(_4bsv&qeW2Kz-itlA*`Y z{HT0%Ol)@a7Y(!9;mt>nu&*UDnw|FHo)F}`7!qL>;(qU$f~mi{zxYBS z>FjMYUz$0z7Ujk%=FJ5bdxkcqXF>f``*$?Vz1mEocDCVWEVFT9NglG?bchrK`JepN zSHQBWmr4W^;?gB!B7eTHF4(7zz}$|m5JRR~AN#pK*S|t|!k;l~y??BAh2Unxt$D&b zZX@%uiEJoNG(MJKGW)K-(LaH?%jd!xd^u+4^5t}!#3an2-vN_z-3`KDr0WzPvkBL_ zNGJZb5m{20xwl~+d6g{8r!xCBt~^$V$jAj%vLBLuj2@?&b3&_QG+#~8dE23~7op3W z)wMFsM;D-63FAb1R^(fNb*pDgyqI|7h0gZxrfgU2naPH42aU@3wxn$Ecc_ z6YcN8F-j&$z>NJ7yErSKjZ>z=qWzY+kR1+{GLthw>&1r`Y(Xdc5o_~L^B2$B=wG6a zVn%qmx@V9N#sNQ93;ZdsfRfz-o5u-Ti9FTwrS2Kf!=a1+v(YfiSx<4tyC~PhmRdTn zh<7536I>>VYbcw_j%rk~$Y#s|8?YI=^8Qm3jITR$Y~7JZ7#e&?Fxgef_-VJn*qMKL zro!~`%1pn*cOCplD`V^Nc8teMv#4c#MD}TIAMy#1gQ-Jwn7i2OvNyDMUGOB+nCaTg zE?8)<$41c#+X_uv$m7p22k&kmUF+>Ky=TVKq?!|0RgQy$lRblUG%kZ;OorD36I@2-&rfA(MZEJ{u^2mL62#;BcVCsELpc~G(6jO2 zx5B)UVl4(^E-aBz;Z*40xQz^%3ggrq{*ClhjFqG2FNoDsu7Ovg+^*MW_z}BVa zpNTS0_=>B$`Sa=L)QZrp$WVN_z+jgk?+yGIDRrKWZSa3SUxbEyu38G|c>)y6{*6y> zd0#1~K8#!du?8#Kzb2MBV=J#Hr&1dr;Z7p^!KD5G)?VMLN9@%1{xz0^Cadva8a(Yw zR~nI>78XRwa*#8c4y2h=6yrfY{BY4~)0Q5i%;z}{ia3?~SYE2ahaN84j|?ius=n#* zx5k4bRyvTiB?d*I>KlxAb7n9x$vlB1eJWOEu`P z$Qc}*QG~GM&gc|!Ake{yJ?0W($0cNxK!ZEmqANy!eoxB;0j67KTV{d2%e zlgKouiRa=s3rC_+nmGx{aAZ0Cf430W&fdD-T_=6UN(s6P~|XTAGKHs(a%;LC@EME9;6S#Y~ zScGA&95!vlWaib^pv%pXHJD=l2_PXx9zH{xIYCGO=e z!>sYI=6WTLp#LwminT{4rQ_`5)jVkT!s=N}Y`MDzdC8{u7*d(ZJ8=#>o<_AbLG{dd zmdtQ-dd;UD{ndykX)yIUb10uXo603QKChl+P3>M1ye4v#`{9|MD4pr;?+$j;d1BzS zY#Q6Wc||ujAN%l4B6J^zl-tF+uv5|1Uz^)qfIMDt6JcRwG{e5Y`rtW+TCtITjOeM> z#>Spb;nqhU&j&~TvAenHk-o?5_!P9{fqubu##>z&kJg1svRtNcTv^LhdkjnJ6m3?mWQ^OG@qDhMTPR)?$xyDknT4wsjSFUq+;H;a~2K+MO7xLwkDGL|zo0LV$)J3!^rw*=4f`9Cy&3T#Jkq+l zz)?>=sFR*}M7F9erwxenj)~mOCG&huv#lAwXIEjgUDkrcntUM{($G`O4uh&MBAHXSZ&^Zjuz>&LO9N zqLXJEI^YK->be zkb~2>gA-zOiKFT~nK*bMo;dL#4nB{&%zY1I_8bPUry4cj^@mquFBVD^L=J!t9zZM7 zu0p`Hv6-!Q)roKOI4fqrJkBVa>X0`Ap7I-Q%s;}2n>g%Ay(lY%k&ED`7guMm|ZsLj5cxG+r68cLPo*j$=pdLpGc+>-p$+F`Oqq}i1-DSvvHYh47+cO_5WL*^Dcs# zh*@g#M5}F(>`vywlR~UGt6+!BrL|0QS6|P%o=ARpJzv+19SoD0!UlFs3fQ&2Wb>Y2b( zt-vFZ(c9|eLnV5fy6!{yRz)1$>9S;(drl@ia#K+1Gea0X|IVq-C|TGa+jwwDi-_EC z+>LTP!^W0vK`wuCfAu8%{#!xs9!VfpLb7XJaV!R&$PvG zG2q@;f-ovMhu@Vv33sjJ1_=_?c`mJxWmVa0Z~_zf(dJQv+3w0oXF8+A@4si%f7AD~ zhOSfAr~zl1zZB)1eT%HFtO$$luFPY0c{^_?2_1pLXmymL7K(-*M>cRCs^QJuV58W)+xIpxWynFU@mi>s>2u}uOeQUW;zIo1V`=Y z-%?HTbNO@CoKsy<+Noh$V3v2E{`aL33cUqiG27%dbCXZ)kK%ihp>!CFfP-fylU+QG zebMplot==0_asj~wKpm&S&1%>+IA1A~?7mI2ST| z&5A0uP2!VXUe#)^08EEqbIpiUfQwbE9$z<2HUNgDE?+KV$qv5m(`UxMqo^6 z{PM6%<6OswxW(bzCmcR>$1~ke&-E@%4htR9k$9_f=D`YzKHF%~{3fRrGg>vS~rEt@F$hoB)&+SrY9$votz+ z4%KqjO=YvymBB>#T&`C~+mlt;i`K?q&Z*r|5j$t#HIaie2^&Yy8>HEejG+7#pt8wz zLx}}rwgj>D_!p}4aw}fQ=S{G@=g;-q#d36%}V*Ci#H@E%JVB0p=t*1Mqh3wXB ztmy3X)wC+(cN%G)9&P}94xTyU*YKEZ;BaoaW!vVy+HE@v6<=%ay?(WzZdVVi{GYiM zmz;^&Ai5m&LDJP#dI2yGV_U~38t=7n&+jDeOJ#ZGRWsREO*k#IslCiaUQnJ-a5+w=a%1WpAEa_8 z7eUK8eO@V~4y6bfAye^J;g6^P4*O%~An3gWt(j1vE;K z1j0~QWYEpdacX;a2XbhF5%a@GyL-By*<97a)sc7nbhU_QrI@XSN}#QT)~d8XaX=e7 z>qjn;xswIQ!fW)|zgj=7HYu4ir&kqKj^&6DRmW9y$Hr^?&lLF`5P2g#w za{Yozz$sBC%QAA!6Gekl@DwWcdYdpQZC|(Tz@$W@Yy)gTwmDgHq2qjdpsle=*2@b1yfFiDQ$f5X>w!H@|nbZ`DErQ6Ud&8#Qg z1~u3g0wgzfMJ2%o9E0ysv_F7-duRPTdb74N`ONvK1+#1+|CzW@A-Y=y!Sz5@T^saP zk3qRqZH3&Szu)&wfRrr-E~O809B^qPYs*$3Dg$c7N_w7KGC3hJF0 z+vd}D_@MkNNgnO-OppBhK|4N>fm{HPCPEhc9I$`>VDc2?Y^b2DCzpi+=W2QD^hguR zHa(cJtACNb9;NLAXln`DTJoTz;3h@XYeKz;D`!^bM(Q36;C8FJ2knYj-cnhzjxVLQ z&UI637MbdE!a;XkTTe%7prHzWKdZWvWP`CZb%sHa2?IIO2-BFh$(rDFSG_l zrKIiCMS*o9p3lbfv?;l<=hO4yL$jM*3Cd%0f3}OSKlz-aem~#kPLQ#~^vreK6xi1O zd6C*N(CN%3XMNA+XLinO6>E&(?Zg>$UPU}4Zku1evmRC(?C*2cVz(UG%q@ZCO*iRG zV-r{wEIr&WcAiti-P5|qbrbJ>)MN`X%_^V9e$Y)PjFCm2qicWQKNRn>!S3dSZ0ut` z0A2gQYAg80aHUN1>fH8!^y*MtBiE3_EJEUc=z12cPsk~})ip4Rb)B|kY5JxYcbV(@ z=H&llOBN=;*MU93fcM`uOY*t#+`tZMV~nD=LYnqv`}mu^RA20&c1UwH8vk26q)mQd zArA}Dk$fy=E%0Y;LDrrpbMx8F4R))Tto$H<_{OXkCx8xxfcQ8tzh2Y%FJnU1PPo<$ zFAe!QhFZHr-{PF#fvneI!M=&XIlTJo?6Z;EF9ajiz# zw~L3JXa@h_dY4#}lw8P9y)T^RtFWs?1MYF0??L`G+;bPltFJchx4CRf(298heeQ+a zjax=E8fCmyx)yfpRAgZoWwSaJG_c?^Oj*v>4BDq;l@j%B@Kci2Mz$GQW<-^mp%j5< zu@JSL_>iA(9yd&hQ-tapVfpDWbc>bh>K5zF7QMVx9k2MIHAwJ(PWF)ftXs{Z;6%=O zd|v9K8sodMOq4$Pb$cTPxc8uRa|bkEh$(VS56acfD2BJ($FeXg-<1CnjMf z8IV2bRdC7-m$A8>X1FU^32yLi9P?s=JOv|K?8rAMlQbu8P{fs?6otn zikQO;jmW#n2rr7>0*xLAy(tq}apZlB&3V9GlJCaKxjBZdRkJdWIXGd0OY`Ij*L(ia zzOCKBkMekNPC32D-5Tgk2Hs~q=icaDm-V7QAbFN(IJmU;KfwDWl<%wc?sUq<>}BY* zQ?YZv0dAZO*d}R7ew-7Nj`p$E_aB3gOu()tqMDA!dXyb4T9Kq~gXgfXIuUKZ^_k6) z;QGpMfvrbeYMg_f9{DUm>w#3@h1X@yzxDWs9;10q>-!xBPDxWzl*x&bWSF?G{PSYY zG)#PbO8=sf>c-L(#qdkSoiE<$x~7lf@b_#kT;4Vmx`Q`jiD3;en>zv%7%@A zGF?V=o>%l1VI2}_?q#8CFHXhevmb{Xz^xeakp97Yo#O*z9&fc8TjC?I_8a~N< zlGtC$9g&2TW?*A_r-HuQ@m)5VAyG5x$JFmzw0}`J!g2NuDI2!*Bye`4`AG8Zb|~b2 z)6r0_$tb35co=(3l0y`s#6PTYkzvOY7u>)J1Mbfj*%e29V1u}c!_M*xh|m)kpm^8$ zTDwvZqVkR!gA&*Py;Li6ey|M1um~E@M#4j2hbBp9)7fj%u)6x)(;}BHGn$G}sK3|XfJi$Mm^(pn#T3CBZ5__sr zpz!tNGtf)gQSut>qqWzh)UUu(DgRL_i!*rb3avhS{omb^+E{9bMtDb?l%KkZ6A~nQ zJ?(t^$}NGCv@!`6VH##M`#EhNJh&EvwJUP!ZE^s6Bl@a&TPjNj{ZbUtEq#)sX0k@V z+d;o+pjwJz1^sOJHd-bMvS1G0yOH-n6g&wE4#W2kYnx9GL}@)bYMSBe<^+fK4KYj1 z>tu#Za(g7*;V{|^Rz!P&73J(u>`J%daJM7)yJh+4(*qbF-OZ6XVSwRN264uBP3+@zMi#tWv65mT= zKdS<77}^rx<7CaXI9XGRhjAz0Op(~f7CG`G%+(b5(IzvKBULPn9A4(cCxIdMAQ)gT z^EPPfLS0)w&NU!^giCY!4_%;SF^(3hkM^Y6P4kuI;YjR z4e+D8*yvmn+UY^mBbw5j6u3-f7JTG}(vx`qrZtBx?((*VyXrccyS8<-cb)C%#2%+@ zXGHGt`eHVfEvVfHu6Z!ope|H#M&p1!7W%vaNNwGk4}!|^^P99M$bUhb4F~r%G#t!r z%q=$`wEMMH{{K~;Vn$}ppcp5L!X$Y6ij~eYSeuKCbtct@yPPv*o;A!bQYSc)U3}Y7 zzafZxM2>e{FY=pA@Nqlp$JQ;hUn?fSCcYo`Sh{F}M;_0xQ^Q`Lw8^9bZ*ZIU+?CE` zPcicENMpxYp#wauOWbAisi??^7*HhJDC^vubT9HP@?6)h^SeahF=$a|Vf~zaP+Yg< z%$Lz=Y%xy$Sfql*&cFuB6DG8T~69n6#D09zvY^bWT)y)C9S2i-7080g8sbjb}Rb zbjs;AkDg!PjZ8KSjpgGkE0n%E!ysPv=Bvv7=D(Enqb$cRX9?ge!>=i=pBZQ3ypd^! zi@0m0os+e^1T*pyqP;&vjrRPD$VkR)+V%82xH zHoILkEEpg89(;HFg07xKP5_N=M{UZK7!Rv>?c85i_Ae4!`xj-Q)T}v^&b$Y$MXsUq zk#gXZ8VUO?(1u_5pUy3!?Da@7Xlu)goW0c3y}r^04iQ4>SHv(l9{K);YB?NyQT?@z z2j6MH89QojDIy|RqfP#nxydbjDUV#bIG-3=j>_bgI@FfAV#_0bu^e|aXb}=x%|pw@ z;kC?d@+Y_K&F4!mm!xx6Y`}NEw6B_XREzMLcKaiH*N_$D&@}PAYe+ZWvxe>#;P4ms zXMle3G91cMxw|==@ExqTz*+}B=epc2ov`t9f;d+&|8N;!b+ka|vx|2ou@P9uJO9O4 zj&MEb_H}K!5jlvrb!FQxe?!|=k6Ss{B|v&3iKwU;J7XQuEsyDPOOLad5c6Mu zMZ3OJka)o3ZtnCVY7KTG{&!=vUIHECeM0Q3*xu4$ce>&@6YO~Ze`N`Axvb#X!!v7Z zs*uB1Q-eGcPg8qy2eNve4YcEz6zs6d1%T|phwQ4@H{2MWm~Mb8Lk7^C7~U@&oVYCOT3* z6ScRt!BG)gR?nnzFKFdJ;oc&QtWN)UKknvkbMT&@gmhW*D+_mWo0hLY(V|x&-#H~x zP4mv%BGm*+D^!C+g?~SCQzUS(QEvY0v+Jh ztqx|A9U-x`lBI^!n#@*6XD;+?9(F(K^Oro5|J3}E95OjAbybLf=Q6d%27b0cnGU%9 z?mRhH@JsX61?;V$y(KYZ!Jf1nS3!^>22%xwTmqEmZ*cwkSue5^;9=Zjl&e~EgOBVP zgVqAi`f(oz2YL)wnk$#Fo8fC)(G7~H05AN{WVQ-+{U4d*vUc!mH@Lb?b09k;~ z8F7?)E0brC-gZ5c;N7TeD~I3QBwf!E0imwVi;Tu4+?Tb8n@IOEvwSa0EOyq1RoekJ z!-~5Wld)26b|oT5GTJMCl!L!y9lrQa>^oIc7c7U>c`sYgmc~}hufQDwfx0}0;K?iq z3==c~5HR4nO9ErB#KN-(Rg|_bu-)rpR5+R>%s^WKFg?QCF;TGf^wooG)65 znnp&_ndXoUyf5wvI^Lwmban5?@h07O<&V(wIOjgzM4p^mz>#lR8=_UnEnV|CI z#krfq`OYY{?OzUj@&uy?oE)5C1xyz`AAgqOW#@NJU?=NsY5{VXl4>$)FbYz#((g;E zX*}o-8!%IPlQ^YViPT4HMa9}WF=FO&CyuEPKY`z^HrR*-ktx7q%32F{+oT}Id8?L( zMczniXDVghQQjT$^q7|6d<+>f>x(|sYpT@rI-V1Gx>s>qu zDK{cN?8nD|4~Nfyg@-L_f?xeyQl?@>+$>3X9J_l-R-Fe%Gl0olpFR03e4z#MddHMJK|+RIj$^&GL`8n!CO@n?s#{?d+f zx1g&;d;f_$#KuVsK84$?w}qybPzlmN523_J>Bqs`&`)Q2H)GGrPM1u6Vv>+Xf{S|O z$*^l#Kf^VApR+_y-V?p-bBO05Wv$B!2(Y2v`3K}1RvLMs$t&7doh3`E5gwwEo|Hhc zYr$sn=bBs&?7j~Lc$~x~!s|i2w!+Eb1d2$tcU^Ajw)RZqN>Qd1xSJ_+-GlG@U}zlHm9MixG71-FFp;UE4GF@c&&|OdV}0K zF?QZM@mLFY%T}*Ke&v<$>_45~h!Zk7wFX!p|k{6jP8UJsLOzzO%{GZ!@7;c46( z*H=xp^v54aNBbX(d*z#LK9eAnWhD@Lm5l{{t_Zt`00pa+tBN zJUq`NFWs6H^lpMKf}I@)+&GyRTzp_rU6pqeMhui8-GTb*<8q!~vWxoaZ_hdN_h@cQ zL%STAhnuU;Mh(nc&~-+Qa>#vzM}_Y`twtx*Bv|(eOl`7pD!rTZ!JEiw>5J}dr%ay; z=t3M~NR$`S2dlaBOn=m(4%_`z$8hw6te1o&VB+zs;_h4JFOYeyKjrXrxC@>j({T0` zbkxnoI4k^JdXL<$q%b_WbsEI$U_o8Dr+Y|EAKuzr>8!5m!X4D+&F~2fnA(f!el>y} z?fvO{pLU3`){nr1AMMI{o~z1;s2qnGx|qv3b0R9K-0n{Fjz@f0?38Q7-MNvAOT|tD z{?83&MVg|?yJyWw7*n9qe8N5?CBJU+nRlW$<36yQQ}0A`BkObf5P@6yRt}ziI@qtC z#IQi`rQ*>p9+FvH#^Y1Snks|P#YtizfBe0I$e(i^k$HcXStg^sTwLz~)EncG?Vj-kl_)e=muq@^pE^gm1O_YJxyu4FAwKl&0&1KS)RiZYJ!?K*uX7R z2s6UaS&t(=Tw8_gQMt@yzkZk$$~p69bR6(=#IQ6=FQcrSLI1D7Io*AW!d2X+1O;B9 z-E{B6m`DdV8M9g3?cYFNS8QaP(uusALbgwk;n7;m-OuFRf!#mlhkFu3x9;Yg7FYj0 zS-8_NK~{HTXVFp)pV02byXk2={80jKgPJ$GrLy>|$#KrDfpjZEen{w|d+3 z)_{Cl!qwZlpkv#fdG(h^&w`b^7wx5bN8J3b)X#rO415p z59Wkfx|!WoWs;xDzqhIu)ZeqH^UPP#;jke`t2Rhgu6MH#o_BGPyh;CcyO3Cu!$u3A zrgOqMcd7C#`0mdy`Z@k5?9MOpw%*tAYv7j^3FFpFl1-CNfq#bXuAc-x`l0W>6z8t?x+<$CIMM@@aAJn8urRs3cN zGKA~ogWPVj>_8Uad(nAHR%CJ1rp}tP}O_rR22z z({$ZeL!91FM|}F1+2b%ihPt!a9C*JB{pum?D9eiYfzLbW!vr=$$%C{VQx)yq{;65< z@9?vn57vTv40GKw7z@|!OR^Km#=Lqb(KM#c7r^IVHE?RSLii@C4`<+Ri!&>=HM9yh zCPt7Q!*@Dn0dxmhMVHGkqHaM8)9-@$4>=SIfvsiV;iXc=5b^+(3z zMzj-A-p>U_x|Xxr`D7cfLQ4q}^@e&fsVlFg;7%T%i_efpp(1iK+mM4gU5LA1kc^!V zbQ^`J)S(g_1AkgF2%<~J@gvXOT_ce9n{(<|bkeE!qof(PU5Loo_i0aZ>Agd)5~~8t zdyP55aVadk?y{!rfI{Nadn|gJLTZ|h59`|gQ+W}*gYY|IQ=gqf+7sTt)9$)hu3(A^N zYw;Bnctjhu57Xzt7vpWqh|C4IHAyzrgx^Wn9p}H4Q@ND(Rv7${C->ZbF8N1(_t`2FHs;Yue|QgPy>GK`Fjq8`|irPLS(5fTc>m z&bIS4XFKZJy_%j*o?!e_C~5=Gp=x=)t}Q$tmK$WONln5oP7{2N(;`O%TjWniZl;sx zpHE<~`^636`G7^CfKtNP2&Mj^m^BKz;^hm)+yv5*9jL=c-L-M9#mf2zHxf9ygoy!_g%ie}8Lg*3U(^EOTEjPX#J~Ng3#AmPPY3?Ae^k2U4si~Zdo%5U; zJ~IX0&zWk5Yzz3eSUq8!hJ3Etzw1jM6IMzlM4qRqIgaJ7@UD-cj~x*>U~8~DU>&~g zFUb$j$N8MVzyNFr<4~J1hVh5#(<3TyQkTKTd7f`e22N(gPK_^9t|npfZ{&L7Ek4t= zyiz+TaJgJAN@Da+@swNo)9I1#EnD+jJN~~6Z33bL-&^LuCwae!EKaSEb#f!OWLH7t>1BJLci{gtrLi*SgEykI>meXy zB98w8;`lEtqui@Q*r|$rG;LCgfyX%{c(UaZG5~?&3(Lw7^Ei}2{D;H(UAm*`)D+Cb zy`utK`I^9Q4{v#Rt5N-|<0YADZM`J5guw&)s&{74&M}*`5PFF0H;UrY}t=Gi_268`dSv>N*PzWvb_4B}!<~42 zec(rE?&SfgrLhVp>+<~?O+3`ph(Jpt=jDW`^9sExf!IL>V7E7Fx&>YaE&KT^&qW{%jOQW#-b`MUPG}tQ7=2t0r6|*J(}_)@^CL_f{$G3VA0Jh9?SJnH2bjbVB1VW9 z@dyb93So$dF(S=xk{FVh1c*pUCYebxFqy>61Or7H5d#8ZM6{GrN|91ZDWw!GBDK^~ zF7Vq?OS!1jrW7fqTtrNn?|YpyGnoKZ`#i7L^ZfC>!R2SpKKsYoYp=cc+H3D~ z&P}w7QuwSD-+`%*<*Zh!;Z03L2LJizj|0!VnZCWhm)81%MNC6I*0dtE?GV!=e?_oa^JH&`HLKlb6tJ0qGD~4 z?w_1WjvcAXGb;Tmf03=1W>&fwi4zh!PxoOw(s-*)ydw!&bs|0UI@WQAacv1)TOGG@ z9Sawc@gLMHH9y;`UulX(TlhHuo*&Idsb447liElr9#5 zrP{`B@qoUutoqVy@LSZ5+W=~m&&i=rhL}%Y zXq>-`wOtx#)b3@ zntL)fb&&nqnl&v%Q*MYjC)x_ZsgFog7*?LBB_!122CGd z|9`)qHycUJ_By_A_`9HQ)c=9)u=x3+-PPZ)WLr{y{aU=S3XjkK&5&l+*^#lwU&~-e z!ON4P(e4wke>Coi=;FBFy~dlT@LpOti|-J;So)3jEQ|Fwcix`*1Ia%%_fZ3*-yHHy{h5ZTk^K@b zZ)#)TdE3k@Z~Xo>Bov>N^U0=MTW0Aey9|$b!W~Ar+03vi`z~f%S###3Zv2Ds)&S;L ztFh|Ds^_%973Qp{YO6b+6Ra~B+w}J;EasDJmwA${vNV#@ySJzQ+iTyV4de6wI^?$* zmp5fvt)=hvySz(IPna#BK3LvIMHeP~vgt|2$Wf^p=kMCHSue5jxEs%_is)DU^^$mI zFWw`Hrz;zK%o->DbF=+^`gVWzz=Bu$JJM!66+3lQYS72da|rLqGXc4ro9Xd|o2jku zNPEj~&gjC2yoKZB3DM-(7rI}U9?>WMlh-miLpLC_OTae|7;(l+eewNEV_j#y7b3WCn*84HRqvhCW$=3KiNoODX7YPGuG?>HzF~a4!|XWT z%v04@rt-al&|dvV#`rH!UYT#tx&I6Lys$ccxb26(#Wyn<|M|A<5A%hGhi%VbCp2eY z;q4K9;zs{CN$+jde98=VC({^~j;s{(Z;RW?>@1$P$+A}7xRodBM!hI@O{7D-W!BVD zUw?MyOCMtIyco-KAQAf2+P*hf`}gebDdQQ5NVRBFa_W1pUwD0RjEq}<{4ZH+$y=cc znGbLDmLT)ZBscQy3Aa3FVLYAk?f;gYlo(EHi+%J9?8AJ#Be%wzSF(q>i|YYA%gS^6 z*mLH-pzI3DdlYz9IgI;^Yu-R0=b?jplhigpF7|Tm;%I!NUyJQ8ZzcL0--_g$m2rIW z^F{V+u_zdN_rz@Idm9?B zl$B=#W@5?VcL~^+59*PQ`>`!Q9wKvR?DR;i%l5^&Se1EVRnF*(RoM@#a%MKEJNsiz zCSy%LhBbNl&WBT%o#vT=Ceyl#N1B~@=ER=l?X2~&#z+TwO(H@dSwQ_dfyt#QJSt%+m~})jLC;W)Q3QQTQ9wnGSz8_&bult2DMU zbGlf)7w^onJrAF!>Tk0q;A6dwz5cHH=Xsj+Hol;Ue}e1tTwmonn(IieFLUkZnz=Xn zXu!f1Uaf{djI+S{Ev!Pz)<#5k58(|5jzWI%3=MB`yktDBAai|N-yGhv)|YdNQMM}E zFYA-vTdBIgGbHRCVA31)cV#@2v+A<)?~AXHuN+V9qn~>1uf_?w37v9=?oj38?EVKL z)N=kG6=A+1FDL#cWO3~~@)BbE9#opV&#upbp}Zqc-geac9eGb?|00@qvnp0m#0p;h z^Y6q9rj$41J(>NKk!QWdd_UgzuX#US`+jTuQ^vPct$9!Gw^Yh+`I732{VGjlRZUOr z{jH64)8t+H^6vHdd=Ww&n!ib@v`tYwm$R66v#+brc`M^5@-2>~e3dQ!w^{NQ%A0vI zIEJSSt;Q%IE0PC!-$#~Bvwl3}VcWymmD%#m%zo_UjNv_nD&nJYN$idPX-F{j`$Nij zXQ+xkHRSiK2~HZ%R9(xLaP@iL07(md17t9zCE$;Yh`y5*wS2qduFy9??oG&y9v1eM zPWdj!pNwyI#2Vk+?D_V`2Vvj-c#qZjEpe9U(_!EKFk^l&mla1Mt(J9lJ)HE`y$WZk{SIAa-ptRq;bzgLQ(kDe#M&)`lto0WnHPi zYN}CZIv4O{m-N=aT9>9s9RyU(d7d3A47?Odl%f86D3(3_iDe0q{2MbC6|-!WfzdGuDVQ?GH> zHMKZX_crF_W=#t#r6+8BsFa>CUcC@tv?uJI8-z`` zLD;>auo_LN7HBcF8rlTyg5HGQf!>EMKoNZz!J(d(_B!3pT3_-gQ^Jy=v{%o4du^?= zIdnfo&u;Q~NZ@Mn=q=7V)WIRL&o!E-xV5py*+L$UG5S=qsR9`~AD70haid+j(_U|P zd6aV2*d2AGb)u9WdkxCwbV%9GI(w_z7p0siL5tjXdFI*OTsPLa+)mIF#3rAptC6Op zw78_Ad|GK~l*%nG$(oi|F2VA9YVK4cth|hn+|sg=ijpYR>Y3|ldfa1Hn(#gSc^8wl zH_Z-&Wq`{A_txDYUU<4=+#f{Ti=PuOJk9^tzqejf&uhy+_&N8ljenzS+ds&o_#fPp zycPyz=jL~|yUFYF)T5QU*V!`9Df-YePCVY?VrXC#38`y}UfSgKx@z3c;7C^6V)r%} zy6}(FWwqATIa~C)R<}DvFLU}@=8GOn!Y`ceF1@0uNw2eeeRt`_O?qQskSy`I=j+Y( z7N5)R)^EgeZd)@w%IT1rnD>($dd+;F(>sRiCK;H8kuqnk(=|_|F}2CjDm_6dghH;K zCiq%#uNOq(JSGj0Yd;;C)0OQ*d)qH!l!UB#8F`Lp7=ntS3o?6o(J#*IL%7H9np zqYxg-$JOL;y6y9C7%y-y6xU~Oyhe7SX_T%`?y5~abVStKW~Yk@QxDe7HbA8M7<7Nv5S$7+4dVloQS+BNgd z!4_5NJ-aoxG|h84h`}_=Jm>PFQ!aOFi!twodP0gm!{v4xQ=;D5tXE{0G7yiIiQVie zf%3>k!g{)o8tZV*bGmuX&)|pq#&uIOY*GV5tyD>~(<7P|uonWUbq4)_QJ_c39FfG! zb_BzU9T`d+R&4KtMxQe55WU>!)buyZi@w^CD@ znjAIrorHw<)Bm*}Xc@!!>9HyPvHh_4HtYsy6SNC@6M6@FAG!cV3}s$}hC`_kK9s62+f4%KntMd&^pM` z+SoWhXfo4Yo+ghIFmOCLEnoxHwR%i@&dE?{PBp6JA*J#%3yLIuUP)PYZq>BXoXm<` zxt>x|l9TmFt}4sTDk-T@L0d}Iwb&b-RpxLi@$9vawYt16F%_$Pu12G5GY&%y1G~gA zM*b>$9b;sbufszos zCI7Jdp)3s^yj7yGRbC(SGV!hpt7@*7^j^EHKfKD@T4S<)gGz<&Ip_+3iZb@Kuu!S0 zb-LZbs`LsoDjt%Z!FvnkZNEdQz0e`(7<3xC0I6Y0#Xt$rXebTJgDRjJXc5#5tqagf zuvX@oDhDQm1F6y;j@l|CEbzOz!S0ntk?>|$v(xP|^}|u)@&zLrzXK7?-#rl;&ET*E@O?`OqAv1wHDd}?S|fjjzA}& zysF&F-0Z6ClBrWOi*w|9N^V6}PHshRc11~9RmCHvxrCJymRnhoTUMM|R8?LuMIf&z zbBe_8bx-n{R$P#sSy50@Ts5^MM>>p|X92m(@0@}u1r?;P$StSunCWveajXU6W#*W_ zXOtCG-b3D5om7 zIJa!dBL)u@nPnAKnb{9dD=04z)`hQ%lG0v5MwrACE=s0V1j;L$R!rQ?ifNP(mRGSb z3b&a><`@!oW%6B7FqLYVvXS3aMY(yBr|_KfNO9)Wg6yiY%;G6Q`3FihMVaLlRoO)axy2P#1*HML2`?=vGup%) z>jE*zGrOcXuVBiwvfQevw3OsY%?hSw!kkgQQPb>_X~ncuRhE<(442wmdjlSeGqZ|v zQGw#BDFst9jXWeK!m6q$E0~&9P+_!}gq3Dih~kCf1g_zvT*hcaU#|@dOIJl+H;fw| zZt5DEC(1>hy|^wwB!rbtD=N>eDlMqYl?Lr~T}9VH*{36oV0dB7RQjOk2MhKoTvg?jilFk~P-2=_MtLPO5PDB}nb{Qu9Eme| zDa$3R+}>(T9zA`aB6n(_{pFW5bVXSS6(o*a=T1jOs4mx;(<(~1Phd_#xilYP^pP@@ zpej3;hNBaR_DJ09{9Kd{4J;4zrINe~oKLiPS;3SkqL}Cq+A0_v4+=^cc8W5M{+L}- z`iKld;d*P%wm}Yy$Rs#_=LP0(DSM=@)C4FCDurf4ZfF6t40;LL4DEvULvKSTpfk{A zsNY>m#X-X%8#Eazf@VSu&^%}fv>Mt7?SS?{Z$ZZ)j#Q|NP{eS2m(Vb143rM#L(?G# z)B?3btDyDJHfRrY5IPFI51oguLeV3b8=z!pB9sG_LDi54S_mzN)Y<#RBO>=1vnEJstK;7zQw z8^!Z9wKU>Xk$8Ht_^g|dz1=fkx3|={N=wuDI8|g7>+-akE^AfcY80VJBITvkFxf)a z1vz?w$Kh-f8RfX@T|RQJpnP$;I3*01M=*k$DcF8wy+<; z*g|J8)4C-s+eT)e6n-4@J@!Tyu166%b<4Ttx`!E)dvk0K_vTTbfM3~kGeyzP;#@X7 zb4IPC@`12ckLj;7+9co)Gu9T;{)}*jL(JUyFl*<-2}~b1;+F^dVKAOZOvdIUMi?32 zjXYQo1@x2b>s1(7vKi=T<^o)AJNsLudiXQSM+NFJT6v$^d?y^G}OeF(x8#<*p z6&ZFTGh6qzva93u;_T*TZ+V4A<7PbXvUWG>A^VE|=&#i7V+rpuM`EM3KEI`dB}oAl z<{A#yJuXI5H_^d>VlsKK;b$~AV~R0eN}2*5FqAu@8q(4pr|bD zfW6Te;KgPXA0xqGbql&#HX{5;bEo33Xuv(J_3LS`B~y@s>F z-pJS|qZT)!)C_hdBnEArCwZnPIg*kFpr`m>n2MU`%gsPKVJ6TRN?Ob0&D`^J1S9En z&Gq)+ByMia%ADQIJko+^bzDyMg%jRw^W$!@9%ewX@w52oLyJ%rVhuL2N-+OXK5q>RaAa=QDm} zlhE#S)wtX)-+Vp0!O5;9l^hMrkkpd)+H?Q|x5!>}9G(}#&2h&28BNCixSCbMoQ6O?He z)f%OU(>pW{ki!j9ebT%?_xrDFPXO4Bu}<6K0a=rLWG1MzATs zwg>+={AdB;qWvx>x)K_G-1DPUZ39!ke&2of5uIj49~}BvkAC;KVCBrj;~uGli^Vw_6crN|!B!}agJ0cf3HGr*2+lgNbLlhg(PEz_t?|fx!3D4IUADp!fP5N-3 zZ+^KgJsnkVwmJZ>SckwDR#wdX|k@EYVd%_q@&|FHgho#dq}}O^Thx9 z?rGM4YJX+$Jl5vWL?{oM4%I>PpbqFIXbbczbP$RR8V)#R^m4|JU~7dL;kF5FI`b6m z$}buyIK_)Tk?j7|d+$q^c8fG71#@afm7N@|=oMye_qG}nePou)V@IQyQjCa^C9S?@ zW;(-ftQ(GCSxr-Hz?x0h$EVq%RAkXShj*;Y>0}~wwAMOhIodlX%4F$7vUx5{57`hj z%0)5FsWWhzC$LmC_@2%I6McNjJ@=45o22Xt7^?&^bP7De)pTQ31wTy2UcB6TO;fAK z!J;b3=zo}+!A;?C*%Vb|r%p_TY5rtAXPPS{F*A}`J(!P8Iu6+waT}-OyCA-?%pz^D zi6jqFGuB<3f!LMiIt&jlafBOVNhS=k;*+t|H29>=@?|YK-CRo=^-pq4*OMs`D?P{r zYvDkSO>(NBw5Z5fy9dI!WcBMnSs3jML(-VU$Sg8wlt`3PaoFqS;;=W$2{KvAuq2Gg zT36C!3&%xGk7K}$F}O2+lsFt9_l+^~KAq9fJKsC57E{MNuD;pTG>#dO!#w8w`#b9E2@gJ~51%!hJr+5|lo+pq8H2B&euRkL__Pb zl!&f7S~vn?*dcWU$$^D`CXF%4P+mIJGu8+5Hbf-qqRe_3WpP4*4u@LHB=ipjGS-~3mj1zdE*_pPMu6;Fq|PeCGH@|Q)fviSbkLesJcgf@-RQ7Cy|C3&&(343 z9l6xWZ`ubaW;~pPdKJIbD62AU!nUjrT<_-P&%*|SuX6)Ed0b)>xvI!bCJ>vN1 zei`j1K0c#62i6K>gZ8em$Ox?!jQJG%E8yUrXWHul1K3z!23?~8OT8|TpL9yYH+r2x z9kQ&0ON7u0L8cS&fd$R~l&FB)HIVo9StYa1O$o@uaD1|I?n!U19L@7YVQiUv1sVOP zxdi=k3LbuiVUU=mYLP+HFRXE z%Nt17<1-z@c-*rqfc+4*3NpqBxMW}u8v&QJ(^xl1zG7K?f$a;mV>Nr*&@t$0fDVIa zAXlAf5$H}|gH2zkb3me5&!1tZ-*d$_fj-uu59i-lEG{+%g1)Ixx?q~SnNVpC887Y* zWHWZ2e)ss)`%-ND8-I5wyL9qOmH8qCO0uPzzApZc-!gc@VkcmLP++2#(vXHya@r^)>o->5j@7+ zN2ya5_Q#-W(~6B}%s`|y{3SA2WcD0zVd$!B;$Dw^md)wU@as|r;N}Lb0dcv7^1t3+ zVOp%g@<*5lQwTKobb{gNyy%D-Zn|nid77tddTs^N7;d$m;86S#<^h}Q$`}#OoHukk zlrH=>rWQvydonkDw*}&x`+VIcnHWg>*75YyH)#iG*?QJQ8`$&vmWlHFv&eT%oNlhC z1T5m7!=0ueb#W*6R3#M8lv&u_fK0E?#}rmrOk=DH#xu_*8U0sJmKHKs;f5zl79(aW z_V5>WJ}E2_(Hon`nI1?oz?*5@49g%`UZ7Uy;X7lOjMFbcA48zHGG}AJ@nN=#x!(EQ z5hc(noIgVL?Hk!M{I-em+sE%s(50}jV#0-j`WEPs#-k)&vpr;RGvq}aTxjP03=Z9# z`F4-E^ryh+7(FNRVOj46_m4g!uCZK_1iJ0IB*H^@{tWF#-un3Kqkd-G)GrXXNeszy zs>nQI@N$C!uI1&rG&d;780$g;3QU55P>oY*^F!~Yv_C=>tMKl~8h zahc@>*`E_Jz>~QK4(z9j0_v=}MSf^5ET`+4_MBQv`ZJWGG12%`kit<>oqqyv?u_ z_IHi{^vFnY^I|HZ|LJDJ@iq+V@U*4!D3&3R$liJ9U?8N334a3~ z!kCCO;~6ac(>$1I4HmBFAzTirUsMjM|1=K)Sql^L#FPUOhgDAn>Q_(-3kHwjZ4nl+ zM-C>h|5RJ_$id+MS{``v#Mm&Cfk#$|kBZwQ$zdG0=(R7Cj`s__xHhbghoMBj4U;{% zuVJXLncy?;Ny2M%S-PBb5b-jH`j*{Yre*xlglEkzma8pJ5_9QV$J*JosMF0^=x$&ayrkgjv`Qy!=6 z6(*-fOLKF2g~{nioslQMpg330npXY@ccmD~w;-n|S0V?mgX6c?+@lEWOo+VkoBHgA z^F%BhY){$api)>=ritV=Y%($nH_O9!nq(`*I5bS0sQuXeKgYI#cJf#};?g>el zT(^bM6~ZqZ<}GQ^66j0--wC^xdqNT>_cw=8C%;qwo%3q{VNx5oDnJQf@LGOLxLg;9 zQ98esB_g5^e_G(L?=^q@KIgCh|I0t#+4BGE9})=tv0MxNeMyZ~y0Wz?TP2_Th_y!H zmTPbq%~{}kY^I9f)9)-X5S~@t*;lE7{dqv0ujt9sEU{dx{wj2B=|3>`=0Uf_5$b7f zt88jzTQAR{IGrvW*>acL5ppB?rlem7dMt7^-B?H~O+ZoU3r@A&^=?fLgB>lgbMp2IO~ z&%cA#FZM5(UWxAfU;Wqaf6~9$|CE1;|7m}Rf2n_&{~7;s{|f&~|Fiy8{^$Ii{^$Lx z{V({}_+RwD6Wi&%f3Geg8K9 z5B%HxKlJbL|H!}7|6~6y|4;n8{jd06_5akr$N!ptum5%bKL5}BZ}@-i-|zp0|4sid z{RjNN@*nj7i~o@S*Z#Ns|LQ;N|2O~J{@?hI_Nf8amu|AYTS{~!Hb{y+K8`2Xxb>;K4q&i@zxdH-Mi7yN(o zU-bWv|C0Y>|7HIt{ww}Z{oVe*`>%4iig5`gkddUX>c5mg zPTACWm8$Mh6V$zGqPkC|sr%XMc|c84530%P%PK?JRgJ1u4&_vJs$MlHmztyIDz|D> z9@V6HuRZ%wUgcA*Y96~iZEC(+pdMAT)K}DORi&!`AEp1QTBx2-i`3UtyLwVBR!^xV z>S@)Xma1jy8MR!kP%G85YL$9Ub*kspYW0Fzqh3@msjsWG>KkgE`led1zNI#(Z>x>! zJ8F}9S#4I|Ra?~e)K>LMixJ>ahAZ^|tzrI--87-ckRqj;jAq$JBqS zkoP~IeECm(O46pL-eLPB|MA5$C;i;}wcnTA+A2QS z(acqWxiB;pG85ile)H6NA4MCP0tel4E1DHc>n!B|o#@`0z`UxMT8%%I>~Xo}j4f=l z>CEAr`Pg%&Z(E)P=CGL@>Jxtx7xJ8z(;@a8rdb0fnLIGv!fHphdO6Dyx+8m_@(`b~ z@NQ{smeV}!GjmXkGv#hK;hX>%$67!R0+^481v53z7)Z9_r46x+%D%`w*Jw$ABPT{t=*o<%W*yrKN zHcq2uo9B&T)I9KPZXv2t5kSx=_i#)|Nr6Ewv*e&@;DiLu8FN#NqfByQLTW=*%u?AU zn9sHbqI0%UArTVJX_tfdxbXG^dA?gxu$MnKBu+DoOW8~5k#+%RIl?ak`2>&8D|w*- zj}CAkME0OXGRBUs*$_9n3oD!(YH4CSTNW6urdprda99NxsE}8-7!vNOgwY-p=`^@) z#_wX7@^VHbkg9<5QuS2;c4)YaD+t^0}55skT>TwKUCzV|lJoaX1&}J6aQZ zEFgG#)6pcZ(Xa@JnCBpZx6KpAp~jZyJB=o?&ufzB^UWsUFtY3=%b8zP3T2Tfh&7}O zp~oSvak=tr&K)2YTJ|<^ZFovxjdgqd5o!` zH_lvzx@@3t8xCYsPKF{DOQ(>k!3T{dT{&<(+w3$wO(@P2UIZkY9aNXS3VGj2U_@lx zl_M7@F)uDL8pSxaPTP3!V#$QiV3%_PZdVOs@O)POGG&N+Lyk+g1ZR!jky40_EX+sV zDcqhSeIgWHWtx%*cz2}F35!x;V<7BRq>H&AFx1QAO`HdM3WGgVv~;xO0$CxuL3ZBBnX05}|>FS2VSF zRk^%#gsvZ&kEKPLJe+foa1>w8KbQ&=6n=ty;+Ff97#h5T59d`BCYT^#`~~jdm@;~NMZ2rL^&9gYRnfFaWt9vvS%`b z>U8(!CKsauoCXi|2Dm_FZX8cU*%K$A+A?tH#yc8x!>`yocW*3ZRTfj5e&d^t-V5->+ZiDw+xl0)WUMrE*CG#$-qzV#to zYaW-b8@f}@AnVkN8Q%=Ufw4v2FhJi4%t$h*a8Mkds`37SVq+Gl%q=dc)Mb+AScakK z7(pU`^M;qr)#e8F`om}Z00hcck*UvTyZ%!!E&#+n&DF#frIFZacl!WnNU{!P}!MjUOa zr6PJ@^mBb)mbRDsOQ2=kKMiKZSaYHW#y+RL+-GS7^^p6UA@?uw{Tuf+?i;DmK80^a zsRK|3|J&71(#LaOf6n@H|7ZKH3~_DL>n!muzGb`@T*6OASWacl#}q-K-}HOh;Q&1M}7&<^?$kFvppP|vgjn< zvfuLzK524dtRe$)GUQ>%Vkh^tlk8#K;J!}S5$-SK{ziUh#Y9t1+;e?j)|U3^hBE`e7xHIjObq+TP3fx|)02#%Zx=7ELaOmH?x_Z!&)E(SY5L_KmHxDDI^ zQlF93XC&Qh0lvP49*5?z!q>G*a0pF*MS?r z9pEnTP4FOi415tDtQn%7#sixGWg?Rkgz|( z8=ntQUDUY?Ub^6=i*DIPSzYVFjT+uab|Ygz9Zb~JpL3M@a}hWbtOhTD=)&2-^ne6S zeRPPo+aueLy1=vG6;4W8HFfSZct%ryS*6rp)`OeDZJPRIjZ&Xbr%$$l=-emB=t{Jv zuEfck%RqGXN(;CEYzNPQmo)XM##dpYKxFpmEYJha1J{9@HPzj~DCh&*!6hI%-Mt&^ zR_gB&n#CHWEY=t>1)K=Z0~dhXz+K=u@PcNE9IY&o+>g8jUPY#xktz2F8~_h#mIU_f z5(b0Az(mcG(yc7xqBP66L0~+18YG`_SCqx3kUP5Z$3w_B2Kgedt}L(+Tmr5JnP$57 zBX2A69t^rc>hb4%L{$7M!E0D`}E@n7yMWb)WECxF?b?YgmZaq!D4)SdP-vv*Se>?f3H+|NT{|53$ z&V7%P|332HPyXmJiV*O31?^1nd7@L_=u%X#o3`M*T| z>&Sm6`R~@0mdwbGTs8R6;6w9)ZQv4c8Aw0TXjg4BxE0(D?g0;ghrpxYaqu+Q1zrR% z!?y9YHr0Y+* zC>^;bBF{C*b1ley^hm`_LY^5Qe8j-V&13jNy$wYEHzWU>Pk^U1HOR)SJ^@?;E(76n z5PaT3{9A~B3+;Lf?Rv{m@VKVpkWU=)iJJ+|20Osz;9KC^wBHrl@2aK-FH~x9J4ihS zQ;)$1z(XMU3?`o;lsklShctk05dMe2{}9I8A#Z9bekc~#Ffa|A1a1Mhfk(ijApFO} z|84n7-Btv`|84Mp8~NNuKDTWKw}QLDJs{=ZM)|i<{%w?h+i9>1ya-;_)KHB#AX&jU zFdj?1O2!I{kY>p@CMc`r(eHnqi zj6h#Tpf4k~g4@AY!M)%C@DS}2Px~bBMM&z+H?q{I1>hnOzDB{f>27Wk$2`CjCQni><$Ti#;9WN-|)9^44N2_Dqc*nFkN7J+BLbDFXtcN=oI5#L69 z+fneirp7lYHQueMRPswDzf{ttk}efFry}Q6(x;OC9`xWI^k70U=0usM?u}FG-guDq zznAu(h(1q5pVQW`@>{E^`y!OOuOGMyTn&B*o?)D%9qy+c(%~l^e$tV1I&w}Y|8(+y zpiZd==4k3c^!7pY_JJ#0U)9u?;rGk%J9oEIbN6T}1O3fFe>2g8O!Ochx#uJIEcnZU zzwE7?G~ceN9O{)ry>hmJJ3!hYhjz%PUis9kz`>L44UCr+jF*)l?NLa3Jaka0hu+du z(P-Yrm%=sWKScRO@LL4G50U;M(ii1%U8t!t_$q_1vLoP8O_k@cBcBhFUpe`e)4t`j zZw2zNK>ih_UJOWec!E0vTnnxTk&6?#$a83Q6G7Uk zj&`am0!uYjPrd7@cRlS^PrJF$6Bl~oLXIxv=z?Dt{Lb<5cI7tO8-C`(&)l=%c}=;u z;_2D0sm2c8G`t+V40da(nRv~_Yew$P$h{eUn&GE;FZc!s-_7v-82a%T`tjIsa3r`G zM9&}F3~mMA0^inD3;eghzYo5B@a<~=-5~LO#P^*7Piv|bxwj(sR^-u&JYIi?Z(1JH z)IQ4DM>+c#ANDQgKJ{s(KCRTRmHN$#=S>s|AnE6keqI_l3CstJz)ElyNV)SUcU~K~ z5L^bX1lNM=!L8tSa1Xc-JOmyFtzfjK7PRvw$|c|x@T#W1I#{W%(yzXn4o(JVgEb)a z`YQGM>IQHVcmO;Eo(C^#YGEASnRt+TETkUoSCx7)LQ_w6foCE=6ybO~m7q4(9xcpN+do(8)#^$hiThI&1d0;YoK(=+JPGcSSbK;-ib@_FV0cnL%v&mfN# zgs&j{1^9dcK3{~77vW=h3~#s`1m=T9;Bs&kh02+_*nrzD`tYT!JXi45WZKy_lj=uvT17NWH1Xn2VMXPf0poP+rWij1L)S& zstKG>P6M}s+d=ej6?*s_d_M=@&z%I{*HkC%+e!O&(jJ|(N9U{HUXc7d$^Uuk_dNA` zJ_pPP(fjAo`_)#SSc(Q`fz{wfa5M6G8~MCLec^Kre7;D(c#(ebBKq~>67UW1O_2C6 z68}ZUffpGEUK+zwgf@`+zeN4N4*y?=|Fy_xE%N#LC9bb<{Sw#fK;*X;`F(?OzCk(0 z+qH*-l)sMhzd2N?Zw>>mfLArOejRT!-Jq#&r7QKV$zTV#TvHpU-v;WpVJ*0x^gBqu zOXJL%Qs34<gdZjRIN@6e z-^Mla-i^F>(_dbpzq~@dUZGyEz~?LQ`D%;2;RoCf?gY{ESJCsIBB!4sr#*|=nds2e zYw-OVe7}YsyoMg^rM>pjUaxcib?(1T`L9#{KIFa+x$lFIeem(K2&I1352T%bHUX>z zXMqdAMId~=0bg%S0Mj(}^Ce3Ce3_;WM=NzWR#Wd>X4j%yQ-AO&^@le6Q1pXy^n-Id z!95`So})g0A^uk{?444;?b^D^ymIbXB%!OzzRKc994@8?m? zGWdeB48E*cZab|ktd}iAtCeM_1KbL3*DSYleY;#|ah<1GhU6*BkV3E>T!J6#6n?DJ znnk~=EO+5YylXZ161W@O1D*uAf7eBja%f)5a1F#C$hyHY96#ak;ow4WG58X=4ty2F zZ3<%EyOpNooMynkC|GWr=u4vy37An2}%|h~9P4K7XQp{?reQ0%^xTrQ;{u zfuC@nX1R%UH=z%IMm~Su&-FW8pXB;gt`Bg1jO+LD5pTptyqWfirG03pfzy>5I1@hz za*spqw|B8FKZ|`i2>Ws{I2ud=X}3b!t&nyvTnApou8hF0L?4UL$D;k<0ZmOU;%#B2 znku1vN@$;fS>&Gw&IW79pL7YND;!Eb!@v#TCgM*beukzj`3SNId;@$_QxOiO_}a4S zvk3p$V*FX?NniA&ANA-*JtEP|Nc3`m8~;%=NV)-}i;2U36c75qHvBtz_;(6H>Uk^m z9K02O&UXAZ3HWVv{4(fmJbHdR^16L5cJm(Uw~u;pzli&F$hmG8b{*xoDaVosfArfv z&G6+zex!>d-L3T3Tj{U2R)Cct_iyF?tqZ|+a4oo=@`*Q?ctb8w{w4e#V~~pt+yZU` zkAO$PcR|`Qfp`hTlPAnZ#ej9-9B?1FA3P48U>#P&I;;*{33js1y2v`~GV7~O)>msZ zm11M3YXZ0%+ykBk&*L9T!#^|$+zIYx-G$t3$bG!Vy2}dE565p{ofXeID*^O?Eg*cR z!sk5`S$Cy_lz$K9-_s2Gz|&wC>#>=v$7X}*&jj>m!d2E|5v$a52X=zHLE7g5+UEi4 z`2h8tl%v$7d~gZ43_J`T0WX19ST9n~2dU?S8DI{GUOb3iJh%zm0v-oXu#Vi%I`RPP z$1$uQZQycn73;=i){SF8?q_j7oARuLH&BK;#7 z+z#%fpRA^zyaZBy5#<-11(wQ!SEM>_0xSRDV@|ugh=57QxGrrLdZrZ`U23!js1&@Olz)P%S zlUc`(0b9U%AmuhvuBVby5wpOx;Cf9pX-YL&K_A%0x^^Dx+6Amv<5;i8Gj7K)ZVzH! zC}dtJW;{)2Je|yVN`3lJpT5YUFLLO2h;jZf_9*p!nR;(QzFUy*mPO!Va3$CYGCpnD z0B!}hgXqf^^kvHd@DTV8cnoBG_+AA256jtqSjD)H+~bk^n4yf5!;t@O_vOzS|=9&-Sp7M*MF2S2z8u8@{{W z)+{5LpGUsKJ|5+tqx^H!{~Yx{hkl)VgLE56w-ww0?jjxS(+wZp=ubEL(-p;*8T!&S z983Xe&#q-4^6sMDK03_);JYC0@e%EP?jZRhuTQDRr`6ybu!a2GV7H|=`1>6Ci0k05$B=NZ)c>&~l0Cw7dSHb<@VfMPQ>jq-i z4aD9Wh`lwC{0DxBJ&0T`4bv>q4rPg^{Dj%ck^nz-IayiRgAqg9D8ewX1N#p?%wxN;+cwp0;~b+z)j#5 z@EFKme9Rlro5~V%5PD0q#KtL0Y&@6%BDdH)5W6zA7%U@QKIw`;+CkACJSN1^9P9%6 z#jW&<1TX}-Tj4VyjeI77 z@Sgzx2@RkdTmYh{3A;erebiv3Mh(S2n23Fl4$@D?(oZ6eVs{;K zn>Mf=WIX9pN%$=KEA{D%UPV^WuPZ?Z*Z>kglK4Z=uOaAHJbD#B6I=zZW}euBIJSYi z!9CbT=dp_};zvlwk1!d(!AkrF^zRnx+d_R?h~Gl|7W!Wc{m(myw*u2IeAL%ReSHVO zL*NncD1NL6{8;_K7;uoL<|D`X$Z`HD!c+~$1>c5EgT@(eL1ksnTQNOQIzjpF%mweX} zZ$0xunbcW}L&_|&(Z`ab!VQcp7eJW07vQto0K{hV+t z*E!%0a2MgoVF_}0ihQ0TpQrYMZxFtT@GV?day<(~&QBrdCEE$#$+d%P^mWOrT<_(& znQI?-1-wf5M8ea#UdVMj*Ku6OgUR3+5I&Z`$CC5lMf`uKcGfnIc= z7ai50gYYqg+qkB^JN9!8zfTLl)Te{`EZc&Aa~u9jg}+h*X{Tpsr{yj98RvnE!4B{^ zcmg~JUcj$Nzg$7TT!DO7Am5d=^Ge!zCGE13c6k>5o`t_>*Ml4J8&d!0sQ+^>f$Q)S za=(-ND=B9s<*eKT?jt_@J`2CkZUwh9j;v!G*+9C%q#FvN56^8OJ@Gn;*Et=Wi9hQS z{;VtbuV|NT{qXbU;pZ#F{-B*-rk!6d2Ft(&;37?ZF9Ulb2ZW#R!O!=0g1hk}&clzm z0RIi`@Kf61r*l9Lh@5|loPW9&T+g{5jdMTL|4af%d;B?__4;Ja{UFD)$ni`H;i-hL zB)pSw+U+dyx+XC1r!lWDWL`%fyJ_EU+P8ZZxSIR4OBe0(>2mI`A{@Qw#y=9VjCqcE zJYpNj{5t?Y!GL4Tr>mGxS2LG!J||{2*W0iua$`6zHBfP%{05TWz;rN+b5gX+AGuD!K1fLc zCxB^S6iB)h=Ft?L`Gt1qOFQ&M?tPJaKiZ=o?a>eY?uUN&qrdi}zec>zy!9dT67uMS zJo?zc38bUl`qFOL87gu#m<8s6JHTDwVekm^S`PDCK3D_RVV9y;7WB%3TrJ4e(gmKS z9NI0y3KAYcIPz4;Q}x+OdFWf81K=V20&n6MI0&8u-)DX%-mS#Dbuah^{)Tt(HyqQ{ zDEJx$U!!RMQMCUk${j_yqdLJg;2H27>-t#M^>HBWKbrO*y#?F`9tDqsm%(o4ar9>_ z`ZG2jOaRf-vFPd83a}ESKaHh7jol6I0g>BS-X z7x4#d!Y{A|e?T<;fLJgEOa;;Jd)x5?5I&LciIw0i&;z!BSHP?I1qR_47z}2CdEh#5 z1O5Q`PJ{0>`cE4DCyjE_DChoJ_yMZH6W}TE0(gmaKm4V`U-}wwEqDq%&H5gFdjNfV zU^Z9-`oK02c|3qT9w7Y#q@QGEogWRBf)!vVxCT59o?v|+!}@*@m2NdBCQ1}Bh&{~_W(bQSw80y_?UDeA^fU5K69&iZ~c>-(+X9&jJ)_bk@$d0-_t z3p@ZG0^bEsvaWAuUB85NJ>@+@c{9&rf?s4kU%`6565J0SU|m0kb-j&syoPyh1&4ye zKmw?Ma!m9|cE@E9@3c^=4eAyFO&nJVO;2Q8Ec$szmEKL7u za4Wc-^*s62l3(p4Faw0oTKII(E)Lqo;Q$+0pRZxLu$FZ>a;`_t^~=DO;AU_uNWJQ* zR|EMskblE^a3hF5H(X`CPB|{hajgV9S+B$29Qd2F58Tgs9eK<}9&@*YJHa=>gRIjh zvb0DCH-ei%>gT3@jquS3AC1vqEQp>rqUVkD+eZ3rBm6YNk0+k>djd#3Jk-MjzaIE) zie()i2eyMtSkEtJJ>P*Hu49KMvYvpi1o#?plJg_)gXA}Y{1PLSO6&*5f$`u-a5R_( zP67+TVsI8%4bra@>DP&rlSnyXC^#BS0Vji5U>P_atOMtO3&2I-DsVNp3ETowpOMsO;PW^*MZx>9pD?_o8UX(G3>GB*kh}} z1K=U>L+}iCnTB0v1*<^^NP9m^d#^fN4 z&>uUZe}>hPmIh6N`r6)shaT zpXPov*K7Grn)D_7UI?{A@_QN739W}VLtCNk&`xMKvXQA`ZMd&irjhq!^wOTUTpoLI7v;=~W4EV@^j|}+8SPQL(HbU@`l>q5bB9sh` zfo#wOC=HqfWk5MlzSWYWAPu6doM5PmojoGBew#ogl0k2kOOLf+*V5=`4o~*A$b-SL8TD! z3yEJy{6gXv62Fl6g%ZCR@eWXf3oJ+6ZliwnE#XozQM*53~>3 z4;_FGL5HCu&{60(bOJgBorb!gv(S0yB6Jz*wpt!ikOoZ?-9y-gz_GtyhkYS5z2dn@*bhQM<{P5<;|o#2WcIob(BJ+ zcT_<6P?6PAN4$FC)f2BCzUtwro-*r+R}YW%aS;5~CqO!s2*F=H{MEx>J-pSEe?9p( ztbx`;TcPdHPG}#rA6g4-gf>IFp*>d19Ma8!r#Tf+B{U1FhRACU<+H8(Idf zgqoo?s2w7&#~L8=evEP-Bmc)1LY;UiXe-oZWmyA7Ly1s4lmO}6y9jDf9KSC^-TbyfvHU&@owr(^A?-87d4}+3 z$YU94mJxRuaXa9rgK|44uVXi~-)dP(-W_|uSrGS@l6EQSmXhaE%2`VJOUY|#4pan{ zLKRRYlusFHkONu> DETECTOR_TYPE_OFST); - if (type != BOARD_JUNGFRAU_TYPE){ - FILE_LOG(logERROR, ("This is not a Jungfrau Server (read %d, expected %d)\n", type, BOARD_JUNGFRAU_TYPE)); + if (type != JUNGFRAU){ + FILE_LOG(logERROR, ("This is not a Jungfrau Server (read %d, expected %d)\n", type, JUNGFRAU)); return FAIL; } @@ -423,11 +422,11 @@ void setupDetector() { resetCore(); alignDeserializer(); - - configureASICTimer(); bus_w(ADC_PORT_INVERT_REG, ADC_PORT_INVERT_VAL); + initReadoutConfiguration(); + //Initialization of acquistion parameters setSettings(DEFAULT_SETTINGS); @@ -654,12 +653,12 @@ int64_t getTimeLeft(enum timerIndex ind){ retval = get64BitReg(GET_PERIOD_LSB_REG, GET_PERIOD_MSB_REG) / (1E-3 * CLK_SYNC); FILE_LOG(logINFO, ("Getting period left: %lldns\n", (long long int)retval)); break; -/* + case DELAY_AFTER_TRIGGER: - retval = get64BitReg(xxx) / (1E-3 * CLK_SYNC); + retval = get64BitReg(GET_DELAY_LSB_REG, GET_DELAY_MSB_REG) / (1E-3 * CLK_SYNC); FILE_LOG(logINFO, ("Getting delay left: %lldns\n", (long long int)retval)); break; -*/ + case CYCLES_NUMBER: retval = get64BitReg(GET_CYCLES_LSB_REG, GET_CYCLES_MSB_REG); FILE_LOG(logINFO, ("Getting number of cycles left: %lld\n", (long long int)retval)); @@ -983,40 +982,106 @@ enum externalCommunicationMode getTiming() { /* configure mac */ +void setNumberofUDPInterfaces(int val) { + uint32_t addr = CONFIG_REG; + // enable 2 interfaces + if (val > 1) { + FILE_LOG(logINFOBLUE, ("Setting #Interfaces: 2\n")); + bus_w(addr, bus_r(addr) | CONFIG_OPRTN_MDE_2_X_10GbE_MSK); + } + // enable only 1 interface + else { + FILE_LOG(logINFOBLUE, ("Setting #Interfaces: 1\n")); + bus_w(addr, bus_r(addr) &~ CONFIG_OPRTN_MDE_2_X_10GbE_MSK); + } +} -long int calcChecksum(int sourceip, int destip) { - ip_header ip; - ip.ip_ver = 0x4; - ip.ip_ihl = 0x5; - ip.ip_tos = 0x0; - ip.ip_len = IP_PACKETSIZE; - ip.ip_ident = 0x0000; - ip.ip_flag = 0x2; //not nibble aligned (flag& offset - ip.ip_offset = 0x000; - ip.ip_ttl = 0x40; - ip.ip_protocol = 0x11; - ip.ip_chksum = 0x0000 ; // pseudo - ip.ip_sourceip = sourceip; - ip.ip_destip = destip; +void selectPrimaryInterface(int val) { + uint32_t addr = CONFIG_REG; - int count = sizeof(ip); + // inner (user input: 1) + if (val == 1) { + FILE_LOG(logINFOBLUE, ("Setting Primary Interface: 1 (Inner)\n")); + bus_w(addr, bus_r(addr) | CONFIG_INNR_PRIMRY_INTRFCE_MSK); + } + // outer (user input: 2) + else { + FILE_LOG(logINFOBLUE, ("Setting Primary Interface: 2 (Outer)\n")); + bus_w(addr, bus_r(addr) &~ CONFIG_INNR_PRIMRY_INTRFCE_MSK); + } +} - unsigned short *addr; - addr = (unsigned short*) &(ip); /* warning: assignment from incompatible pointer type */ +void setupHeader(int iRxEntry, enum interfaceType type, uint32_t destip, uint64_t destmac, uint32_t destport, uint64_t sourcemac, uint32_t sourceip, uint32_t sourceport) { + + // start addr + uint32_t addr = (type == INNER ? RXR_ENDPOINT_INNER_START_REG : RXR_ENDPOINT_OUTER_START_REG); + // calculate rxr endpoint offset + addr += (iRxEntry * RXR_ENDPOINT_OFST); + // get struct memory + udp_header *udp = (udp_header*) (CSP0BASE + addr * 2); + memset(udp, 0, sizeof(udp_header)); + // mac addresses + // msb (32) + lsb (16) + udp->udp_destmac_msb = ((destmac >> 16) & BIT32_MASK); + udp->udp_destmac_lsb = ((destmac >> 0) & BIT16_MASK); + // msb (16) + lsb (32) + udp->udp_srcmac_msb = ((sourcemac >> 32) & BIT16_MASK); + udp->udp_srcmac_lsb = ((sourcemac >> 0) & BIT32_MASK); + + // ip addresses + udp->ip_srcip_msb = ((sourceip >> 16) & BIT16_MASK); + udp->ip_srcip_lsb = ((sourceip >> 0) & BIT16_MASK); + udp->ip_destip_msb = ((destip >> 16) & BIT16_MASK); + udp->ip_destip_lsb = ((destip >> 0) & BIT16_MASK); + + // source port + udp->udp_srcport = sourceport; + udp->udp_destport = destport; + + // other defines + udp->udp_ethertype = 0x800; + udp->ip_ver = 0x4; + udp->ip_ihl = 0x5; + udp->ip_flags = 0x2; //FIXME + udp->ip_ttl = 0x40; + udp->ip_protocol = 0x11; + // total length is redefined in firmware + + calcChecksum(udp); +} + +void calcChecksum(udp_header* udp) { + int count = IP_HEADER_SIZE; long int sum = 0; - while( count > 1 ) { + + // start at ip_tos as the memory is not continous for ip header + uint16_t *addr = (uint16_t*) (&(udp->ip_tos)); + + sum += *addr++; + count -= 2; + + // ignore ethertype (from udp header) + addr++; + + // from identification to srcip_lsb + while( count > 2 ) { sum += *addr++; count -= 2; } + + // ignore src udp port (from udp header) + addr++; + if (count > 0) sum += *addr; // Add left-over byte, if any - while (sum>>16) + while (sum >> 16) sum = (sum & 0xffff) + (sum >> 16);// Fold 32-bit sum to 16 bits - long int checksum = (~sum) & 0xffff; - FILE_LOG(logINFO, ("IP checksum is 0x%lx\n",checksum)); - return checksum; + long int checksum = sum & 0xffff; + checksum += UDP_IP_HEADER_LENGTH_BYTES; + FILE_LOG(logINFO, ("\tIP checksum is 0x%lx\n",checksum)); + udp->ip_checksum = checksum; } @@ -1034,6 +1099,7 @@ int configureMAC(int numInterfaces, int selInterface, FILE_LOG(logINFO, ("\t#Interfaces : %d\n", numInterfaces)); FILE_LOG(logINFO, ("\tInterface : %d\n\n", selInterface)); + FILE_LOG(logINFO, ("\tInner\n")); FILE_LOG(logINFO, ("\tSource IP : %d.%d.%d.%d \t\t(0x%08x)\n", (sourceip>>24)&0xff,(sourceip>>16)&0xff,(sourceip>>8)&0xff,(sourceip)&0xff, sourceip)); FILE_LOG(logINFO, ("\tSource MAC : %02x:%02x:%02x:%02x:%02x:%02x \t(0x%010llx)\n", @@ -1059,6 +1125,7 @@ int configureMAC(int numInterfaces, int selInterface, FILE_LOG(logINFO, ("\tDest. Port : %d \t\t\t(0x%08x)\n\n",udpport, udpport)); uint32_t sourceport2 = DEFAULT_TX_UDP_PORT + 1; + FILE_LOG(logINFO, ("\tOuter\n")); FILE_LOG(logINFO, ("\tSource IP2 : %d.%d.%d.%d \t\t(0x%08x)\n", (sourceip2>>24)&0xff,(sourceip2>>16)&0xff,(sourceip2>>8)&0xff,(sourceip2)&0xff, sourceip2)); FILE_LOG(logINFO, ("\tSource MAC2 : %02x:%02x:%02x:%02x:%02x:%02x \t(0x%010llx)\n", @@ -1083,35 +1150,16 @@ int configureMAC(int numInterfaces, int selInterface, (long long unsigned int)destmac2)); FILE_LOG(logINFO, ("\tDest. Port2 : %d \t\t\t(0x%08x)\n",udpport2, udpport2)); - long int checksum=calcChecksum(sourceip, destip); - bus_w(TX_IP_REG, sourceip); - bus_w(RX_IP_REG, destip); + // default one rxr entry (others not yet implemented in client yet) + int iRxEntry = 0; + // top + setupHeader(iRxEntry, INNER, destip, destmac, udpport, sourcemac, sourceip, sourceport); + // bottom + setupHeader(iRxEntry, OUTER, destip2, destmac2, udpport2, sourcemac2, sourceip2, sourceport2); - uint32_t val = 0; + setNumberofUDPInterfaces(numInterfaces); + selectPrimaryInterface(selInterface); - val = ((sourcemac >> LSB_OF_64_BIT_REG_OFST) & BIT_32_MSK); - bus_w(TX_MAC_LSB_REG, val); - FILE_LOG(logDEBUG1, ("Read from TX_MAC_LSB_REG: 0x%08x\n", bus_r(TX_MAC_LSB_REG))); - - val = ((sourcemac >> MSB_OF_64_BIT_REG_OFST) & BIT_32_MSK); - bus_w(TX_MAC_MSB_REG,val); - FILE_LOG(logDEBUG1, ("Read from TX_MAC_MSB_REG: 0x%08x\n", bus_r(TX_MAC_MSB_REG))); - - val = ((destmac >> LSB_OF_64_BIT_REG_OFST) & BIT_32_MSK); - bus_w(RX_MAC_LSB_REG, val); - FILE_LOG(logDEBUG1, ("Read from RX_MAC_LSB_REG: 0x%08x\n", bus_r(RX_MAC_LSB_REG))); - - val = ((destmac >> MSB_OF_64_BIT_REG_OFST) & BIT_32_MSK); - bus_w(RX_MAC_MSB_REG, val); - FILE_LOG(logDEBUG1, ("Read from RX_MAC_MSB_REG: 0x%08x\n", bus_r(RX_MAC_MSB_REG))); - - val = (((sourceport << UDP_PORT_TX_OFST) & UDP_PORT_TX_MSK) | - ((udpport << UDP_PORT_RX_OFST) & UDP_PORT_RX_MSK)); - bus_w(UDP_PORT_REG, val); - FILE_LOG(logDEBUG1, ("Read from UDP_PORT_REG: 0x%08x\n", bus_r(UDP_PORT_REG))); - - bus_w(TX_IP_CHECKSUM_REG,(checksum << TX_IP_CHECKSUM_OFST) & TX_IP_CHECKSUM_MSK); - FILE_LOG(logDEBUG1, ("Read from TX_IP_CHECKSUM_REG: 0x%08x\n", bus_r(TX_IP_CHECKSUM_REG))); cleanFifos(); resetCore(); alignDeserializer(); @@ -1121,20 +1169,20 @@ int configureMAC(int numInterfaces, int selInterface, int setDetectorPosition(int pos[]) { int ret = OK; - FILE_LOG(logDEBUG1, ("Setting detector position: (%d, %d)\n", pos[0], pos[1])); + FILE_LOG(logDEBUG1, ("Setting detector position: (%d, %d)\n", pos[X], pos[Y])); bus_w(COORD_0_REG, bus_r(COORD_0_REG) & (~(COORD_0_X_MSK))); - bus_w(COORD_0_REG, bus_r(COORD_0_REG) | ((pos[0] << COORD_0_X_OFST) & COORD_0_X_MSK)); - if ((bus_r(COORD_0_REG) & COORD_0_X_MSK) != ((pos[0] << COORD_0_X_OFST) & COORD_0_X_MSK)) + bus_w(COORD_0_REG, bus_r(COORD_0_REG) | ((pos[X] << COORD_0_X_OFST) & COORD_0_X_MSK)); + if ((bus_r(COORD_0_REG) & COORD_0_X_MSK) != ((pos[X] << COORD_0_X_OFST) & COORD_0_X_MSK)) ret = FAIL; bus_w(COORD_0_REG, bus_r(COORD_0_REG) & (~(COORD_0_Y_MSK))); - bus_w(COORD_0_REG, bus_r(COORD_0_REG) | ((pos[1] << COORD_0_Y_OFST) & COORD_0_Y_MSK)); - if ((bus_r(COORD_0_REG) & COORD_0_Y_MSK) != ((pos[1] << COORD_0_Y_OFST) & COORD_0_Y_MSK)) + bus_w(COORD_0_REG, bus_r(COORD_0_REG) | ((pos[Y] << COORD_0_Y_OFST) & COORD_0_Y_MSK)); + if ((bus_r(COORD_0_REG) & COORD_0_Y_MSK) != ((pos[Y] << COORD_0_Y_OFST) & COORD_0_Y_MSK)) ret = FAIL; if (ret == OK) { - FILE_LOG(logINFO, ("Position set to [%d, %d]\n", pos[0], pos[1])); + FILE_LOG(logINFO, ("Position set to [%d, %d]\n", pos[X], pos[Y])); } return ret; } @@ -1143,6 +1191,42 @@ int setDetectorPosition(int pos[]) { /* jungfrau specific - powerchip, autocompdisable, asictimer, clockdiv, pll, flashing fpga */ +void initReadoutConfiguration() { + + FILE_LOG(logINFO, ("Initializing Readout Configuration:\n" + "\t Reset readout Timer\n" + "\t 1 x 10G mode\n" + "\t outer interface is primary\n" + "\t half speed\n" + "\t TDMA disabled, 0 as TDMA slot\n" + "\t Ethernet overflow disabled\n" + "\t Reset Round robin entries\n")); + + uint32_t val = 0; + // reset readouttimer + val &= ~CONFIG_RDT_TMR_MSK; + // 1 x 10G mode + val &= ~CONFIG_OPRTN_MDE_2_X_10GbE_MSK; + // outer interface + val &= ~CONFIG_INNR_PRIMRY_INTRFCE_MSK; + // half speed + val &= ~CONFIG_READOUT_SPEED_MSK; + val |= CONFIG_HALF_SPEED_20MHZ_VAL; + // tdma disable + val &= ~CONFIG_TDMA_ENABLE_MSK; + // tdma slot 0 + val &= ~CONFIG_TDMA_TIMESLOT_MSK; + // no ethernet overflow + val &= ~CONFIG_ETHRNT_FLW_CNTRL_MSK; + bus_w(CONFIG_REG, val); + + val = bus_r(CONTROL_REG); + // reset (addtional round robin entry) rx endpoints num + val &= CONTROL_RX_ADDTNL_ENDPTS_NUM_MSK; + // reset start of round robin entry to 0 + val &= CONTROL_RX_ENDPTS_START_MSK; + bus_w(CONTROL_REG, val); +} int powerChip (int on){ @@ -1191,62 +1275,56 @@ void setClockDivider(int val) { if(runBusy()) stopStateMachine(); - uint32_t txndelay_msk = 0; + switch(val) { - switch(val){ + case FULL_SPEED: + FILE_LOG(logINFO, ("Setting Full Speed (40 MHz):\n")); - // todo in firmware, for now setting half speed - case FULL_SPEED://40 - FILE_LOG(logINFO, ("Setting Half Speed (20 MHz):\n")); + bus_w(SAMPLE_REG, SAMPLE_ADC_FULL_SPEED); + FILE_LOG(logINFO, ("\tSet Sample Reg to 0x%x\n", bus_r(SAMPLE_REG))); - FILE_LOG(logINFO, ("\tSetting Sample Reg to 0x%x\n", SAMPLE_ADC_HALF_SPEED)); - bus_w(SAMPLE_REG, SAMPLE_ADC_HALF_SPEED); + bus_w(CONFIG_REG, (bus_r(CONFIG_REG) & ~CONFIG_READOUT_SPEED_MSK) | CONFIG_FULL_SPEED_40MHZ_VAL); + FILE_LOG(logINFO, ("\tSet Config Reg to 0x%x\n", bus_r(CONFIG_REG))); - txndelay_msk = (bus_r(CONFIG_REG) & CONFIG_TDMA_TIMESLOT_MSK); // read config tdma timeslot value - FILE_LOG(logINFO, ("\tSetting Config Reg to 0x%x\n", CONFIG_HALF_SPEED | txndelay_msk)); - bus_w(CONFIG_REG, CONFIG_HALF_SPEED | txndelay_msk); - - FILE_LOG(logINFO, ("\tSetting ADC Ofst Reg to 0x%x\n", ADC_OFST_HALF_SPEED_VAL)); - bus_w(ADC_OFST_REG, ADC_OFST_HALF_SPEED_VAL); - - FILE_LOG(logINFO, ("\tSetting ADC Phase Reg to 0x%x\n", ADC_PHASE_HALF_SPEED)); - setAdcPhase(ADC_PHASE_HALF_SPEED, 0); + bus_w(ADC_OFST_REG, ADC_OFST_FULL_SPEED_VAL); + FILE_LOG(logINFO, ("\tSet ADC Ofst Reg to 0x%x\n", bus_r(ADC_OFST_REG))); + setAdcPhase(ADC_PHASE_FULL_SPEED, 0); + FILE_LOG(logINFO, ("\tSet ADC Phase Reg to 0x%x\n", ADC_PHASE_FULL_SPEED)); break; + case HALF_SPEED: FILE_LOG(logINFO, ("Setting Half Speed (20 MHz):\n")); - FILE_LOG(logINFO, ("\tSetting Sample Reg to 0x%x\n", SAMPLE_ADC_HALF_SPEED)); bus_w(SAMPLE_REG, SAMPLE_ADC_HALF_SPEED); + FILE_LOG(logINFO, ("\tSet Sample Reg to 0x%x\n", bus_r(SAMPLE_REG))); - txndelay_msk = (bus_r(CONFIG_REG) & CONFIG_TDMA_TIMESLOT_MSK); // read config tdma timeslot value - FILE_LOG(logINFO, ("\tSetting Config Reg to 0x%x\n", CONFIG_HALF_SPEED | txndelay_msk)); - bus_w(CONFIG_REG, CONFIG_HALF_SPEED | txndelay_msk); + bus_w(CONFIG_REG, (bus_r(CONFIG_REG) & ~CONFIG_READOUT_SPEED_MSK) | CONFIG_HALF_SPEED_20MHZ_VAL); + FILE_LOG(logINFO, ("\tSet Config Reg to 0x%x\n", bus_r(CONFIG_REG))); - FILE_LOG(logINFO, ("\tSetting ADC Ofst Reg to 0x%x\n", ADC_OFST_HALF_SPEED_VAL)); bus_w(ADC_OFST_REG, ADC_OFST_HALF_SPEED_VAL); + FILE_LOG(logINFO, ("\tSet ADC Ofst Reg to 0x%x\n", bus_r(ADC_OFST_REG))); - FILE_LOG(logINFO, ("\tSetting ADC Phase Reg to 0x%x\n", ADC_PHASE_HALF_SPEED)); setAdcPhase(ADC_PHASE_HALF_SPEED, 0); - + FILE_LOG(logINFO, ("\tSet ADC Phase Reg to 0x%x\n", ADC_PHASE_HALF_SPEED)); break; + case QUARTER_SPEED: FILE_LOG(logINFO, ("Setting Half Speed (10 MHz):\n")); - FILE_LOG(logINFO, ("\tSetting Sample Reg to 0x%x\n", SAMPLE_ADC_QUARTER_SPEED)); bus_w(SAMPLE_REG, SAMPLE_ADC_QUARTER_SPEED); + FILE_LOG(logINFO, ("\tSet Sample Reg to 0x%x\n", bus_r(SAMPLE_REG))); - txndelay_msk = (bus_r(CONFIG_REG) & CONFIG_TDMA_TIMESLOT_MSK); // read config tdma timeslot value - FILE_LOG(logINFO, ("\tSetting Config Reg to 0x%x\n", CONFIG_QUARTER_SPEED | txndelay_msk)); - bus_w(CONFIG_REG, CONFIG_QUARTER_SPEED | txndelay_msk); + bus_w(CONFIG_REG, (bus_r(CONFIG_REG) & ~CONFIG_READOUT_SPEED_MSK) | CONFIG_QUARTER_SPEED_10MHZ_VAL); + FILE_LOG(logINFO, ("\tSet Config Reg to 0x%x\n", bus_r(CONFIG_REG))); - FILE_LOG(logINFO, ("\tSetting ADC Ofst Reg to 0x%x\n", ADC_OFST_QUARTER_SPEED_VAL)); bus_w(ADC_OFST_REG, ADC_OFST_QUARTER_SPEED_VAL); + FILE_LOG(logINFO, ("\tSet ADC Ofst Reg to 0x%x\n", bus_r(ADC_OFST_REG))); - FILE_LOG(logINFO, ("\tSetting ADC Phase Reg to 0x%x\n", ADC_PHASE_QUARTER_SPEED)); setAdcPhase(ADC_PHASE_QUARTER_SPEED, 0); - + FILE_LOG(logINFO, ("\tSet ADC Phase Reg to 0x%x\n", ADC_PHASE_QUARTER_SPEED)); break; + } } } @@ -1410,22 +1488,38 @@ void alignDeserializer() { int setNetworkParameter(enum NETWORKINDEX mode, int value) { - if (mode != TXN_FRAME) - return -1; + switch(mode) { - if (value >= 0) { - FILE_LOG(logINFO, ("Setting transmission delay: %d\n", value)); - bus_w(CONFIG_REG, (bus_r(CONFIG_REG) &~CONFIG_TDMA_TIMESLOT_MSK) - | (((value << CONFIG_TDMA_TIMESLOT_OFST) & CONFIG_TDMA_TIMESLOT_MSK))); - if (value == 0) - bus_w(CONFIG_REG, bus_r(CONFIG_REG) &~ CONFIG_TDMA_MSK); - else - bus_w(CONFIG_REG, bus_r(CONFIG_REG) | CONFIG_TDMA_MSK); - FILE_LOG(logDEBUG1, ("Transmission delay read %d\n", - ((bus_r(CONFIG_REG) & CONFIG_TDMA_TIMESLOT_MSK) >> CONFIG_TDMA_TIMESLOT_OFST))); - } + case TXN_FRAME: + if (value >= 0) { + FILE_LOG(logINFO, ("Setting transmission delay: %d\n", value)); + bus_w(CONFIG_REG, (bus_r(CONFIG_REG) &~CONFIG_TDMA_TIMESLOT_MSK) + | (((value << CONFIG_TDMA_TIMESLOT_OFST) & CONFIG_TDMA_TIMESLOT_MSK))); + if (value == 0) { + FILE_LOG(logINFO, ("Switching off transmission delay\n")); + bus_w(CONFIG_REG, bus_r(CONFIG_REG) &~ CONFIG_TDMA_ENABLE_MSK); + } else { + FILE_LOG(logINFO, ("Switching on transmission delay\n")); + bus_w(CONFIG_REG, bus_r(CONFIG_REG) | CONFIG_TDMA_ENABLE_MSK); + } + FILE_LOG(logDEBUG1, ("Transmission delay read %d\n", + ((bus_r(CONFIG_REG) & CONFIG_TDMA_TIMESLOT_MSK) >> CONFIG_TDMA_TIMESLOT_OFST))); + } + return ((bus_r(CONFIG_REG) & CONFIG_TDMA_TIMESLOT_MSK) >> CONFIG_TDMA_TIMESLOT_OFST); + + case FLOW_CONTROL_10G: + if (value == 0) { + FILE_LOG(logINFO, ("Switching off 10G flow control\n")); + bus_w(CONFIG_REG, bus_r(CONFIG_REG) &~ CONFIG_ETHRNT_FLW_CNTRL_MSK); + } else { + FILE_LOG(logINFO, ("Switching on 10G flow control\n")); + bus_w(CONFIG_REG, bus_r(CONFIG_REG) | CONFIG_ETHRNT_FLW_CNTRL_MSK); + } + return ((bus_r(CONFIG_REG) & CONFIG_ETHRNT_FLW_CNTRL_MSK) >> CONFIG_ETHRNT_FLW_CNTRL_OFST); - return ((bus_r(CONFIG_REG) & CONFIG_TDMA_TIMESLOT_MSK) >> CONFIG_TDMA_TIMESLOT_OFST); + default: + return -1; + } } diff --git a/slsDetectorServers/jungfrauDetectorServer/slsDetectorServer_defs.h b/slsDetectorServers/jungfrauDetectorServer/slsDetectorServer_defs.h index f90873e5e..18ab6eb82 100755 --- a/slsDetectorServers/jungfrauDetectorServer/slsDetectorServer_defs.h +++ b/slsDetectorServers/jungfrauDetectorServer/slsDetectorServer_defs.h @@ -4,24 +4,36 @@ #define MIN_REQRD_VRSN_T_RD_API 0x171220 -#define REQRD_FRMWR_VRSN 0x181206 // temp bug fix from last version, timing mode is backwards compatible +#define REQRD_FRMWR_VRSN 0x190509 -#define BOARD_JUNGFRAU_TYPE (8) #define CTRL_SRVR_INIT_TIME_US (300 * 1000) /* Struct Definitions */ -typedef struct ip_header_struct { - uint16_t ip_len; - uint8_t ip_tos; - uint8_t ip_ihl:4 ,ip_ver:4; - uint16_t ip_offset:13,ip_flag:3; - uint16_t ip_ident; - uint16_t ip_chksum; - uint8_t ip_protocol; - uint8_t ip_ttl; - uint32_t ip_sourceip; - uint32_t ip_destip; -} ip_header; +typedef struct udp_header_struct { + uint32_t udp_destmac_msb; + uint16_t udp_srcmac_msb; + uint16_t udp_destmac_lsb; + uint32_t udp_srcmac_lsb; + uint8_t ip_tos; + uint8_t ip_ihl: 4, ip_ver: 4; + uint16_t udp_ethertype; + uint16_t ip_identification; + uint16_t ip_totallength; + uint8_t ip_protocol; + uint8_t ip_ttl; + uint16_t ip_fragmentoffset: 13, ip_flags: 3; + uint16_t ip_srcip_msb; + uint16_t ip_checksum; + uint16_t ip_destip_msb; + uint16_t ip_srcip_lsb; + uint16_t udp_srcport; + uint16_t ip_destip_lsb; + uint16_t udp_checksum; + uint16_t udp_destport; +} udp_header; + +#define IP_HEADER_SIZE 20 + /* Enums */ enum CLK_SPEED_INDEX {FULL_SPEED, HALF_SPEED, QUARTER_SPEED}; @@ -36,7 +48,7 @@ enum DACINDEX {VB_COMP, VDD_PROT, VIN_COM, VREF_PRECH, VB_PIXBUF, VB_DS, VREF 480, /* VREF_DS */ \ 420 /* VREF_COMP */ \ }; -enum NETWORKINDEX { TXN_FRAME }; +enum NETWORKINDEX { TXN_FRAME, FLOWCTRL_10G }; /* Hardware Definitions */ #define NCHAN (256 * 256) @@ -46,7 +58,6 @@ enum NETWORKINDEX { TXN_FRAME }; #define DYNAMIC_RANGE (16) #define NUM_BYTES_PER_PIXEL (DYNAMIC_RANGE / 8) #define DATA_BYTES (NCHIP * NCHAN * NUM_BYTES_PER_PIXEL) -#define IP_PACKETSIZE (0x2052) #define CLK_RUN (40) /* MHz */ #define CLK_SYNC (20) /* MHz */ @@ -77,19 +88,21 @@ enum NETWORKINDEX { TXN_FRAME }; #define MAX_STORAGE_CELL_DLY_NS_VAL ((ASIC_CTRL_EXPSRE_TMR_MSK >> ASIC_CTRL_EXPSRE_TMR_OFST) * ASIC_CTRL_EXPSRE_TMR_STEPS) #define ACQ_TIME_MIN_CLOCK (2) +#define SAMPLE_ADC_FULL_SPEED (SAMPLE_ADC_HALF_SPEED) #define SAMPLE_ADC_HALF_SPEED (SAMPLE_DECMT_FACTOR_2_VAL + SAMPLE_DGTL_SAMPLE_0_VAL + SAMPLE_ADC_DECMT_FACTOR_0_VAL + SAMPLE_ADC_SAMPLE_0_VAL) /* 0x1000 */ #define SAMPLE_ADC_QUARTER_SPEED (SAMPLE_DECMT_FACTOR_4_VAL + SAMPLE_DGTL_SAMPLE_8_VAL + SAMPLE_ADC_DECMT_FACTOR_1_VAL + SAMPLE_ADC_SAMPLE_0_VAL) /* 0x2810 */ -#define CONFIG_HALF_SPEED (CONFIG_TDMA_DISABLE_VAL + CONFIG_HALF_SPEED_20MHZ_VAL + CONFIG_OPRTN_MDE_1_X_10GBE_VAL) /**0x100000 */ -#define CONFIG_QUARTER_SPEED (CONFIG_TDMA_DISABLE_VAL + CONFIG_QUARTER_SPEED_10MHZ_VAL + CONFIG_OPRTN_MDE_1_X_10GBE_VAL) + +#define ADC_OFST_FULL_SPEED_VAL (0x20)//(0x1f) //(0x20) #define ADC_OFST_HALF_SPEED_VAL (0x20)//(0x1f) //(0x20) #define ADC_OFST_QUARTER_SPEED_VAL (0x0f) //(0x0f) + +#define ADC_PHASE_FULL_SPEED (0x2D) //45 #define ADC_PHASE_HALF_SPEED (0x2D) //45 #define ADC_PHASE_QUARTER_SPEED (0x2D) //45 + #define ADC_PORT_INVERT_VAL (0x5A5A5A5A)//(0x453b2a9c) #define MAX_PHASE_SHIFTS (160) -/* MSB & LSB DEFINES */ -#define MSB_OF_64_BIT_REG_OFST (32) -#define LSB_OF_64_BIT_REG_OFST (0) -#define BIT_32_MSK (0xFFFFFFFF) +#define BIT16_MASK (0xFFFF) +#define UDP_IP_HEADER_LENGTH_BYTES (28) \ No newline at end of file diff --git a/slsDetectorServers/slsDetectorServer/communication_funcs.c b/slsDetectorServers/slsDetectorServer/communication_funcs.c index 11de0f631..153b4c719 100755 --- a/slsDetectorServers/slsDetectorServer/communication_funcs.c +++ b/slsDetectorServers/slsDetectorServer/communication_funcs.c @@ -524,7 +524,8 @@ int Server_SendResult(int fileDes, intType itype, int update, void* retval, int void getMacAddressinString(char* cmac, int size, uint64_t mac) { memset(cmac, 0, size); - sprintf(cmac,"%02x:%02x:%02x:%02x:%02x:%02x",(unsigned int)((mac>>40)&0xFF), + sprintf(cmac,"%02x:%02x:%02x:%02x:%02x:%02x", + (unsigned int)((mac>>40)&0xFF), (unsigned int)((mac>>32)&0xFF), (unsigned int)((mac>>24)&0xFF), (unsigned int)((mac>>16)&0xFF), @@ -535,4 +536,4 @@ void getMacAddressinString(char* cmac, int size, uint64_t mac) { void getIpAddressinString(char* cip, uint32_t ip) { memset(cip, 0, INET_ADDRSTRLEN); inet_ntop(AF_INET, &ip, cip, INET_ADDRSTRLEN); -} \ No newline at end of file +} diff --git a/slsDetectorServers/slsDetectorServer/communication_funcs.h b/slsDetectorServers/slsDetectorServer/communication_funcs.h index cfe4b5637..ab6ebd8e2 100755 --- a/slsDetectorServers/slsDetectorServer/communication_funcs.h +++ b/slsDetectorServers/slsDetectorServer/communication_funcs.h @@ -67,4 +67,5 @@ void getMacAddressinString(char* cmac, int size, uint64_t mac); */ void getIpAddressinString(char* cip, uint32_t ip); + #endif diff --git a/slsDetectorServers/slsDetectorServer/slsDetectorFunctionList.h b/slsDetectorServers/slsDetectorServer/slsDetectorFunctionList.h index c54a96777..c18fec0dc 100755 --- a/slsDetectorServers/slsDetectorServer/slsDetectorFunctionList.h +++ b/slsDetectorServers/slsDetectorServer/slsDetectorFunctionList.h @@ -13,6 +13,7 @@ Here are the definitions, but the actual implementation should be done for each ****************************************************/ +enum interfaceType {OUTER, INNER}; // basic tests int isFirmwareCheckDone(); @@ -213,6 +214,11 @@ int getExtSignal(); // configure mac #ifdef GOTTHARDD void calcChecksum(mac_conf* mac, int sourceip, int destip); +#elif JUNGFRAUD +void setNumberofUDPInterfaces(int val); +void selectPrimaryInterface(int val); +void setupHeader(int iRxEntry, enum interfaceType type, uint32_t destip, uint64_t destmac, uint32_t destport, uint64_t sourcemac, uint32_t sourceip, uint32_t sourceport); +void calcChecksum(udp_header* udp); #endif #if defined(CHIPTESTBOARDD) || defined(MOENCHD) long int calcChecksum(int sourceip, int destip); @@ -285,6 +291,7 @@ int resetCounterBlock(int startACQ); // jungfrau specific - powerchip, autocompdisable, clockdiv, asictimer, clock, pll, flashing firmware #elif JUNGFRAUD +void initReadoutConfiguration(); int powerChip (int on); int autoCompDisable(int on); void configureASICTimer(); diff --git a/slsDetectorServers/slsDetectorServer/slsDetectorServer_funcs.c b/slsDetectorServers/slsDetectorServer/slsDetectorServer_funcs.c index b5aeaca75..3689a6061 100755 --- a/slsDetectorServers/slsDetectorServer/slsDetectorServer_funcs.c +++ b/slsDetectorServers/slsDetectorServer/slsDetectorServer_funcs.c @@ -1719,13 +1719,6 @@ int get_time_left(int file_des) { // only get // check index -#ifdef JUNGFRAUD - if (ind == DELAY_AFTER_TRIGGER) { - ret = FAIL; - sprintf(mess,"Timer Left Index (%d) is not implemented for this release.\n", (int)ind); - FILE_LOG(logERROR,(mess)); - } -#endif if (ret == OK) { switch(ind) { #ifdef EIGERD @@ -2417,9 +2410,9 @@ int configure_mac(int file_des) { #endif #if defined(JUNGFRAUD) || defined(EIGERD) int pos[2] = {0, 0}; - sscanf(args[12], "%x", &pos[0]); - sscanf(args[13], "%x", &pos[1]); - FILE_LOG(logDEBUG1, ("Position: [%d, %d]\n", pos[0], pos[1])); + sscanf(args[12], "%x", &pos[X]); + sscanf(args[13], "%x", &pos[Y]); + FILE_LOG(logDEBUG1, ("Position: [%d, %d]\n", pos[X], pos[Y])); #endif @@ -3227,10 +3220,12 @@ int set_network_parameter(int file_des) { if ((value == -1) || (Server_VerifyLock() == OK)) { // check index switch (mode) { -#ifdef EIGERD + case FLOW_CONTROL_10G: serverIndex = FLOWCTRL_10G; break; + +#ifdef EIGERD case DETECTOR_TXN_DELAY_LEFT: serverIndex = TXN_LEFT; break; diff --git a/slsDetectorSoftware/include/slsDetectorUsers.h b/slsDetectorSoftware/include/slsDetectorUsers.h index 3b74cec0b..c92323ac6 100755 --- a/slsDetectorSoftware/include/slsDetectorUsers.h +++ b/slsDetectorSoftware/include/slsDetectorUsers.h @@ -521,7 +521,7 @@ public: int setHighVoltage(int i = -1, int detPos = -1); /** - * Set 10GbE Flow Control (Eiger) + * Set 10GbE Flow Control (Eiger and Jungfrau) * @param enable 1 to set, 0 to unset, -1 gets * @param detPos -1 for all detectors in list or specific detector position * @returns 10GbE flow Control diff --git a/slsDetectorSoftware/src/slsDetector.cpp b/slsDetectorSoftware/src/slsDetector.cpp index d505b3eba..58ebf45e1 100755 --- a/slsDetectorSoftware/src/slsDetector.cpp +++ b/slsDetectorSoftware/src/slsDetector.cpp @@ -1438,7 +1438,7 @@ int slsDetector::configureMAC() { // 2d positions to detector to put into udp header { int pos[2] = {0, 0}; - int max = shm()->multiSize[1] * (shm()->numUDPInterfaces); + int max = shm()->multiSize[Y] * (shm()->numUDPInterfaces); // row pos[0] = (detId % max); // col for horiz. udp ports diff --git a/slsDetectorSoftware/src/slsDetectorCommand.cpp b/slsDetectorSoftware/src/slsDetectorCommand.cpp index 4208c0c25..560487e48 100755 --- a/slsDetectorSoftware/src/slsDetectorCommand.cpp +++ b/slsDetectorSoftware/src/slsDetectorCommand.cpp @@ -676,19 +676,12 @@ slsDetectorCommand::slsDetectorCommand(multiSlsDetector *det) { ++i; /*! \page timing - - delayl gets delay left. Used in GOTTHARD only. Only get! \c Returns \c (double with 9 decimal digits) + - delayl gets delay left. Used in GOTTHARD, JUNGFRAU, MOENCH and CTB only. Only get! \c Returns \c (double with 9 decimal digits) */ descrToFuncMap[i].m_pFuncName = "delayl"; descrToFuncMap[i].m_pFuncPtr = &slsDetectorCommand::cmdTimeLeft; ++i; - /*! \page timing - - gatesl gets number of gates left. Used in GOTTHARD only. Only get! \c Returns \c (double with 9 decimal digits) - */ - descrToFuncMap[i].m_pFuncName = "gatesl"; - descrToFuncMap[i].m_pFuncPtr = &slsDetectorCommand::cmdTimeLeft; - ++i; - /*! \page config - framesl gets number of frames left. Used in GOTTHARD and Jungfrau only. Only get! \c Returns \c (double with 9 decimal digits) */ @@ -1700,7 +1693,7 @@ slsDetectorCommand::slsDetectorCommand(multiSlsDetector *det) { ++i; /*! \page network - - flowcontrol_10g [delay] Enables/disables 10 GbE flow control. 1 enables, 0 disables. Used for EIGER only. \c Returns \c (int) + - flowcontrol_10g [delay] Enables/disables 10 GbE flow control. 1 enables, 0 disables. Used for EIGER and JUNGFRAU only. \c Returns \c (int) */ descrToFuncMap[i].m_pFuncName = "flowcontrol_10g"; descrToFuncMap[i].m_pFuncPtr = &slsDetectorCommand::cmdNetworkParameter; @@ -3076,7 +3069,7 @@ std::string slsDetectorCommand::helpNetworkParameter(int action) { os << "txndelay_left port \n sets detector transmission delay of the left port" << std::endl; os << "txndelay_right port \n sets detector transmission delay of the right port" << std::endl; os << "txndelay_frame port \n sets detector transmission delay of the entire frame" << std::endl; - os << "flowcontrol_10g port \n sets flow control for 10g for eiger" << std::endl; + os << "flowcontrol_10g port \n sets flow control for 10g for eiger and jungfrau" << std::endl; os << "zmqport port \n sets the 0MQ (TCP) port of the client to where final data is streamed to (eg. for GUI). The default already connects with rx_zmqport for the GUI. " "Use single-detector command to set individually or multi-detector command to calculate based on port for the rest." "Must restart streaming in client with new port from gui/external gui" @@ -3116,7 +3109,7 @@ std::string slsDetectorCommand::helpNetworkParameter(int action) { os << "txndelay_left \n gets detector transmission delay of the left port" << std::endl; os << "txndelay_right \n gets detector transmission delay of the right port" << std::endl; os << "txndelay_frame \n gets detector transmission delay of the entire frame" << std::endl; - os << "flowcontrol_10g \n gets flow control for 10g for eiger" << std::endl; + os << "flowcontrol_10g \n gets flow control for 10g for eiger and jungfrau" << std::endl; os << "zmqport \n gets the 0MQ (TCP) port of the client to where final data is streamed to" << std::endl; os << "rx_zmqport \n gets the 0MQ (TCP) port of the receiver from where data is streamed from" << std::endl; os << "zmqip \n gets the 0MQ (TCP) ip of the client to where final data is streamed to.If no custom ip, empty until first time connect to receiver" << std::endl; @@ -4581,8 +4574,6 @@ std::string slsDetectorCommand::cmdTimeLeft(int narg, char *args[], int action, index = FRAME_PERIOD; else if (cmd == "delayl") index = DELAY_AFTER_TRIGGER; - else if (cmd == "gatesl") - index = GATES_NUMBER; else if (cmd == "framesl") index = FRAME_NUMBER; else if (cmd == "cyclesl") diff --git a/slsReceiverSoftware/include/GeneralData.h b/slsReceiverSoftware/include/GeneralData.h index b7c955ed1..c3bda3ef9 100755 --- a/slsReceiverSoftware/include/GeneralData.h +++ b/slsReceiverSoftware/include/GeneralData.h @@ -27,9 +27,6 @@ public: /** Number of Pixels in y axis */ uint32_t nPixelsY; - /** emptybuffer (mainly for jungfrau) */ - uint32_t emptyHeader; - /** Size of header in Packet */ uint32_t headerSizeinPacket; @@ -95,7 +92,6 @@ public: myDetectorType(slsDetectorDefs::GENERIC), nPixelsX(0), nPixelsY(0), - emptyHeader(0), headerSizeinPacket(0), dataSize(0), packetSize(0), @@ -228,7 +224,6 @@ public: FILE_LOG(level) << "myDetectorType: " << slsDetectorDefs::detectorTypeToString(myDetectorType); FILE_LOG(level) << "Pixels X: " << nPixelsX; FILE_LOG(level) << "Pixels Y: " << nPixelsY; - FILE_LOG(level) << "Empty Header: " << emptyHeader; FILE_LOG(level) << "Header Size in Packet: " << headerSizeinPacket; FILE_LOG(level) << "Data Size: " << dataSize; FILE_LOG(level) << "Packet Size: " << packetSize; @@ -506,8 +501,7 @@ class JungfrauData : public GeneralData { myDetectorType = slsDetectorDefs::JUNGFRAU; nPixelsX = (256*4); nPixelsY = 512; - emptyHeader = 6; - headerSizeinPacket = emptyHeader + sizeof(slsDetectorDefs::sls_detector_header); + headerSizeinPacket = sizeof(slsDetectorDefs::sls_detector_header); dataSize = 8192; packetSize = headerSizeinPacket + dataSize; packetsPerFrame = 128; diff --git a/slsReceiverSoftware/src/Listener.cpp b/slsReceiverSoftware/src/Listener.cpp index 8760d6dba..4ffccbd32 100755 --- a/slsReceiverSoftware/src/Listener.cpp +++ b/slsReceiverSoftware/src/Listener.cpp @@ -353,7 +353,6 @@ uint32_t Listener::ListenToAnImage(char* buf) { uint32_t numpackets = 0; uint32_t dsize = generalData->dataSize; uint32_t hsize = generalData->headerSizeinPacket; //(includes empty header) - uint32_t esize = generalData->emptyHeader; uint32_t fifohsize = generalData->fifoBufferHeaderSize; uint32_t pperFrame = generalData->packetsPerFrame; bool isHeaderEmpty = true; @@ -397,13 +396,13 @@ uint32_t Listener::ListenToAnImage(char* buf) { //check if its the current image packet // -------------------------- new header ---------------------------------------------------------------------- if (standardheader) { - old_header = (sls_detector_header*) (&carryOverPacket[esize]); + old_header = (sls_detector_header*) (&carryOverPacket[0]); fnum = old_header->frameNumber; pnum = old_header->packetNumber; } // -------------------old header ----------------------------------------------------------------------------- else { - generalData->GetHeaderInfo(index, &carryOverPacket[esize], + generalData->GetHeaderInfo(index, &carryOverPacket[0], *dynamicRange, oddStartingPacket, fnum, pnum, snum, bid); } //------------------------------------------------------------------------------------------------------------ @@ -515,7 +514,7 @@ uint32_t Listener::ListenToAnImage(char* buf) { // -------------------------- new header ---------------------------------------------------------------------- if (standardheader) { - old_header = (sls_detector_header*) (&listeningPacket[esize]); + old_header = (sls_detector_header*) (&listeningPacket[0]); fnum = old_header->frameNumber; pnum = old_header->packetNumber; } @@ -523,10 +522,10 @@ uint32_t Listener::ListenToAnImage(char* buf) { else { // set first packet to be odd or even (check required when switching from roi to no roi) if (myDetectorType == GOTTHARD && !measurementStartedFlag) { - oddStartingPacket = generalData->SetOddStartingPacket(index, &listeningPacket[esize]); + oddStartingPacket = generalData->SetOddStartingPacket(index, &listeningPacket[0]); } - generalData->GetHeaderInfo(index, &listeningPacket[esize], + generalData->GetHeaderInfo(index, &listeningPacket[0], *dynamicRange, oddStartingPacket, fnum, pnum, snum, bid); } //------------------------------------------------------------------------------------------------------------ diff --git a/slsSupportLib/include/versionAPI.h b/slsSupportLib/include/versionAPI.h index 4a39bc3a9..689b78438 100644 --- a/slsSupportLib/include/versionAPI.h +++ b/slsSupportLib/include/versionAPI.h @@ -2,9 +2,10 @@ #define GITBRANCH "refgui" #define APIGOTTHARD 0x190108 #define APIMOENCH 0x181108 -#define APIJUNGFRAU 0x190405 #define APILIB 0x190405 #define APIRECEIVER 0x190405 #define APIGUI 0x190405 -#define APICTB 0x190514 #define APIEIGER 0x190516 +#define APICTB 0x190516 + +#define APIJUNGFRAU 0x190517 From 452fd1e457bf5e57b52fb4e82ae3e41aeb05778c Mon Sep 17 00:00:00 2001 From: Erik Frojdh Date: Wed, 22 May 2019 09:45:08 +0200 Subject: [PATCH 5/8] new defaults for CMake --- CMakeLists.txt | 35 +++++++++-------------------------- 1 file changed, 9 insertions(+), 26 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index f6e49c817..70c2019ba 100755 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,13 +1,9 @@ cmake_minimum_required(VERSION 3.9) project(slsDetectorPackage) + set(PROJECT_VERSION 5.0.0) - -include(CheckIPOSupported) - - - - include(cmake/project_version.cmake) +include(CheckIPOSupported) # Include additional modules that are used unconditionally include(GNUInstallDirs) @@ -35,11 +31,11 @@ if (CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) endif() option (SLS_USE_HDF5 "HDF5 File format" OFF) -option (SLS_USE_TEXTCLIENT "Text Client" OFF) -option (SLS_USE_RECEIVER "Receiver" OFF) +option (SLS_USE_TEXTCLIENT "Text Client" ON) +option (SLS_USE_RECEIVER "Receiver" ON) option (SLS_USE_GUI "GUI" OFF) -option (SLS_USE_TESTS "TESTS" ON) -option (SLS_USE_INTEGRATION_TESTS "Integration Tests" ON) +option (SLS_USE_TESTS "TESTS" OFF) +option (SLS_USE_INTEGRATION_TESTS "Integration Tests" OFF) option(SLS_USE_SANITIZER "Sanitizers for debugging" OFF) option(SLS_USE_PYTHON "Python bindings" OFF) set(CMAKE_EXPORT_COMPILE_COMMANDS ON) @@ -91,12 +87,10 @@ elseif ("${CMAKE_CXX_COMPILER_ID}" STREQUAL "GNU") -Wno-misleading-indentation # mostly in rapidjson remove using clang format -Wduplicated-cond -Wnull-dereference ) - endif() if (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER 8.0) target_compile_options(slsProjectWarnings INTERFACE -Wno-class-memaccess ) - endif() endif() @@ -106,11 +100,10 @@ if(SLS_USE_SANITIZER) target_link_libraries(slsProjectOptions INTERFACE -fsanitize=address,undefined) # target_compile_options(slsProjectOptions INTERFACE -fsanitize=thread) # target_link_libraries(slsProjectOptions INTERFACE -fsanitize=thread) - - endif() +endif() -# Install fake the library +# Install fake the libraries install(TARGETS slsProjectOptions slsProjectWarnings EXPORT "${TARGETS_EXPORT_NAME}" LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} @@ -122,8 +115,6 @@ set(CMAKE_POSITION_INDEPENDENT_CODE ON) set(CMAKE_INSTALL_RPATH "$ORIGIN") set(CMAKE_BUILD_WITH_INSTALL_RPATH TRUE) - - find_package(Doxygen) find_package(ZeroMQ 4 REQUIRED) @@ -132,15 +123,13 @@ if (SLS_USE_TESTS) add_subdirectory(tests) endif(SLS_USE_TESTS) -# Support library containing functionallity common to -# detector and receiver +# Common functionallity to detector and receiver add_subdirectory(slsSupportLib) if (SLS_USE_TEXTCLIENT) add_subdirectory(slsDetectorSoftware) endif (SLS_USE_TEXTCLIENT) - if (SLS_USE_RECEIVER) if (SLS_USE_HDF5) find_package(HDF5 1.10 COMPONENTS CXX REQUIRED) @@ -157,8 +146,6 @@ if (SLS_USE_GUI) endif() endif (SLS_USE_GUI) - - if (SLS_USE_INTEGRATION_TESTS) add_subdirectory(integrationTests) endif (SLS_USE_INTEGRATION_TESTS) @@ -173,13 +160,9 @@ configure_file( .clang-tidy if (DOXYGEN_FOUND) - # set input and output files set(DOXYGEN_IN ${CMAKE_CURRENT_SOURCE_DIR}/doxygen/Doxyfile.in) set(DOXYGEN_OUT ${CMAKE_CURRENT_BINARY_DIR}/Doxyfile) - - # request to configure the file configure_file(${DOXYGEN_IN} ${DOXYGEN_OUT} @ONLY) - message("Doxygen build started") # note the option ALL which allows to build the docs together with the application add_custom_target( docs From 10f89599e02686d2349b5b093c712600793a9fe9 Mon Sep 17 00:00:00 2001 From: Dhanya Thattil Date: Wed, 22 May 2019 19:11:35 +0200 Subject: [PATCH 6/8] bug fix: hdf5 printError still called once. replcaed with printErrorStack --- slsReceiverSoftware/include/HDF5FileStatic.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/slsReceiverSoftware/include/HDF5FileStatic.h b/slsReceiverSoftware/include/HDF5FileStatic.h index 7f89a3348..0a7955d4f 100755 --- a/slsReceiverSoftware/include/HDF5FileStatic.h +++ b/slsReceiverSoftware/include/HDF5FileStatic.h @@ -284,7 +284,7 @@ public: } catch(Exception error){ FILE_LOG(logERROR) << "Could not extend dataset in object " << ind; - error.printError(); + error.printErrorStack(); return 1; } return 0; From 43dc9df6dbf38e906c1ea12f1fd601e874f0d43c Mon Sep 17 00:00:00 2001 From: Erik Frojdh Date: Fri, 24 May 2019 10:25:34 +0200 Subject: [PATCH 7/8] removed unused scripts --- examples/ang.off | 24 --- examples/bad.chans | 5 - .../config_gen_script/generic_example.config | 39 +++++ .../generic_example.config_gen | 47 ++++++ examples/mythen.config | 32 ---- examples/receiver.config | 1 - examples/remove_shm.sh | 10 -- examples/scripts/HeaderBeforeAfter.awk | 142 ------------------ examples/scripts/ScanScript.awk | 87 ----------- examples/scripts/ScriptBeforeAfter.awk | 100 ------------ examples/scripts/StartStopScript.awk | 79 ---------- examples/two_no_receiver.config | 64 -------- 12 files changed, 86 insertions(+), 544 deletions(-) delete mode 100755 examples/ang.off delete mode 100755 examples/bad.chans create mode 100644 examples/config_gen_script/generic_example.config create mode 100755 examples/config_gen_script/generic_example.config_gen delete mode 100755 examples/mythen.config delete mode 100755 examples/receiver.config delete mode 100755 examples/remove_shm.sh delete mode 100755 examples/scripts/HeaderBeforeAfter.awk delete mode 100755 examples/scripts/ScanScript.awk delete mode 100755 examples/scripts/ScriptBeforeAfter.awk delete mode 100755 examples/scripts/StartStopScript.awk delete mode 100755 examples/two_no_receiver.config diff --git a/examples/ang.off b/examples/ang.off deleted file mode 100755 index 819a60667..000000000 --- a/examples/ang.off +++ /dev/null @@ -1,24 +0,0 @@ - module 0 center 6.395E+02 +- 0.00E+00 conversion 6.5660E-05 +- 7.10E-09 offset 0.00000 +- 0.00015 - module 1 center 6.395E+02 +- 0.00E+00 conversion 6.5650E-05 +- 7.09E-09 offset 5.00211 +- 0.00015 - module 2 center 6.395E+02 +- 0.00E+00 conversion 6.5625E-05 +- 7.09E-09 offset 10.00733 +- 0.00015 - module 3 center 6.395E+02 +- 0.00E+00 conversion 6.5618E-05 +- 7.09E-09 offset 15.00742 +- 0.00015 - module 4 center 6.395E+02 +- 0.00E+00 conversion 6.5642E-05 +- 7.15E-09 offset 20.00620 +- 0.00015 - module 5 center 6.395E+02 +- 0.00E+00 conversion 6.5612E-05 +- 7.09E-09 offset 25.00281 +- 0.00015 - module 6 center 6.395E+02 +- 0.00E+00 conversion 6.5623E-05 +- 6.93E-09 offset 30.00704 +- 0.00015 - module 7 center 6.395E+02 +- 0.00E+00 conversion 6.5605E-05 +- 7.10E-09 offset 34.99715 +- 0.00015 - module 8 center 6.395E+02 +- 0.00E+00 conversion 6.5643E-05 +- 7.21E-09 offset 39.99533 +- 0.00015 - module 9 center 6.395E+02 +- 0.00E+00 conversion 6.5638E-05 +- 7.09E-09 offset 44.99969 +- 0.00015 - module 10 center 6.395E+02 +- 0.00E+00 conversion 6.5638E-05 +- 6.94E-09 offset 49.99859 +- 0.00015 - module 11 center 6.395E+02 +- 0.00E+00 conversion 6.5644E-05 +- 7.10E-09 offset 54.99499 +- 0.00015 - module 12 center 6.395E+02 +- 0.00E+00 conversion 6.5618E-05 +- 7.09E-09 offset 59.99120 +- 0.00015 - module 13 center 6.395E+02 +- 0.00E+00 conversion 6.5607E-05 +- 7.11E-09 offset 64.98880 +- 0.00015 - module 14 center 6.395E+02 +- 0.00E+00 conversion 6.5609E-05 +- 7.09E-09 offset 69.98205 +- 0.00015 - module 15 center 6.395E+02 +- 0.00E+00 conversion 6.5611E-05 +- 7.09E-09 offset 74.98379 +- 0.00015 - module 16 center 6.395E+02 +- 0.00E+00 conversion 6.5619E-05 +- 4.72E-09 offset 79.98559 +- 0.00015 - module 17 center 6.395E+02 +- 0.00E+00 conversion 6.5604E-05 +- 7.09E-09 offset 84.98376 +- 0.00015 - module 18 center 6.395E+02 +- 0.00E+00 conversion 6.5605E-05 +- 7.09E-09 offset 89.98307 +- 0.00015 - module 19 center 6.395E+02 +- 0.00E+00 conversion 6.5616E-05 +- 7.09E-09 offset 94.98907 +- 0.00015 - module 20 center 6.395E+02 +- 0.00E+00 conversion 6.5634E-05 +- 7.08E-09 offset 99.97965 +- 0.00015 - module 21 center 6.395E+02 +- 0.00E+00 conversion 6.5608E-05 +- 4.16E-09 offset 104.99732 +- 0.00016 - module 22 center 6.395E+02 +- 0.00E+00 conversion 6.5608E-05 +- 7.09E-09 offset 109.98646 +- 0.00015 - module 23 center 6.395E+02 +- 0.00E+00 conversion 6.5649E-05 +- 7.09E-09 offset 114.98765 +- 0.00015 diff --git a/examples/bad.chans b/examples/bad.chans deleted file mode 100755 index 6e7db22a2..000000000 --- a/examples/bad.chans +++ /dev/null @@ -1,5 +0,0 @@ -15 -1528 -5000 -6513 - diff --git a/examples/config_gen_script/generic_example.config b/examples/config_gen_script/generic_example.config new file mode 100644 index 000000000..9f34ef551 --- /dev/null +++ b/examples/config_gen_script/generic_example.config @@ -0,0 +1,39 @@ +hostname hostname1+hostname2+hostname3+hostname55+ +header_var1 wow +header_var2 great +header_var3 very nice + +0:counter1 100 +0:counter2 1024 +0:counter3 1500 +0:forallmodules val_mod1 +0:constant1 const1 +0:constant2 const2 +0:constant3 const3 /path/to/something + +1:counter1 101 +1:counter2 1036 +1:counter3 1503 +1:forallmodules val_mod2 +1:constant1 const1 +1:constant2 const2 +1:constant3 const3 /path/to/something + +2:counter1 102 +2:counter2 1048 +2:counter3 1506 +2:forallmodules val_mod3 +2:constant1 const1 +2:constant2 const2 +2:constant3 const3 /path/to/something + +3:counter1 103 +3:counter2 1060 +3:counter3 1509 +3:forallmodules val_mod4 +3:constant1 const1 +3:constant2 const2 +3:constant3 const3 /path/to/something + +footer1 foot1 +footer2 somethingelseathebottom diff --git a/examples/config_gen_script/generic_example.config_gen b/examples/config_gen_script/generic_example.config_gen new file mode 100755 index 000000000..fc703169b --- /dev/null +++ b/examples/config_gen_script/generic_example.config_gen @@ -0,0 +1,47 @@ +#!/bin/bash + +# local variables +a_variable=/path/to/something + +# HOSTNAMES is special +# Beside of the hostname line it also defines the amount of modules +# for the body part +# take care for the last space +HOSTNAMES="hostname1 hostname2 hostname3 hostname55 " + +## header contains constant values at the beginning of the file +header=( +header_var1="wow" +header_var2="great" +header_var3="very nice" +) + +## the body part is for each half module +# counters will count automatically +# the number behind ':' indicates the incrementation value + +counters=( +counter1="100:1" +counter2="1024:12" +counter3="1500:3" +) + +# constant values +constants=( +constant1="const1" +constant2="const2" +constant3="const3 ${a_variable}" +) + +# lists contains space separated lists each value for each half module +lists=( +forallmodules="val_mod1 val_mod2 val_mod3 val_mod4" +) + + +## footer contains constant values for the end of the file +footer=( +footer1=foot1 +footer2=somethingelseathebottom +) + diff --git a/examples/mythen.config b/examples/mythen.config deleted file mode 100755 index 3390c61c8..000000000 --- a/examples/mythen.config +++ /dev/null @@ -1,32 +0,0 @@ -type Mythen+ -0:hostname mcs1x21 -0:port 1952 -0:stopport 1953 -0:settingsdir /afs/psi.ch/user/b/bergamaschi -0:outdir /afs/psi.ch/user/b/bergamaschi -0:angdir 1.000000 -0:moveflag 1.000000 -0:lock 0 -0:caldir /afs/psi.ch/user/b/bergamaschi -0:ffdir /afs/psi.ch/user/b/bergamaschi -0:nmod 1 -0:waitstates 13 -0:setlength 3 -0:clkdivider 6 -0:extsig:0 gate_in_active_high -0:extsig:1 trigger_in_rising_edge -0:extsig:2 off -0:extsig:3 off -master -1 -sync none -outdir /afs/psi.ch/user/b/bergamaschi -ffdir /afs/psi.ch/user/b/bergamaschi -headerbefore none -headerafter none -headerbeforepar none -headerafterpar none -badchannels none -angconv none -globaloff 0.000000 -binsize 0.001000 -threaded 1 diff --git a/examples/receiver.config b/examples/receiver.config deleted file mode 100755 index fa4586e14..000000000 --- a/examples/receiver.config +++ /dev/null @@ -1 +0,0 @@ -dataport 1955 diff --git a/examples/remove_shm.sh b/examples/remove_shm.sh deleted file mode 100755 index 439bc839c..000000000 --- a/examples/remove_shm.sh +++ /dev/null @@ -1,10 +0,0 @@ -#!/bin/csh -f -#set l = `ipcs -m | grep "$USER"| cut -c12-19` -set l = `ipcs -m | cut -c0-10` -foreach s ( $l ) - echo $s - ipcrm -M $s -end -#if ($#l != 0 ) -echo $#l shared memory\(s\) for $user removed - diff --git a/examples/scripts/HeaderBeforeAfter.awk b/examples/scripts/HeaderBeforeAfter.awk deleted file mode 100755 index 9b1354471..000000000 --- a/examples/scripts/HeaderBeforeAfter.awk +++ /dev/null @@ -1,142 +0,0 @@ -#! /bin/awk -f - -# this is an awk script to start a run -# you first need to run inimodule.awk to initialize -# the pattern, set Vc and set the trimbits -# - -##################################################################### -# revision history # -##################################################################### -# 31.10.2001 first version # -##################################################################### -# # -# Bernd Schmitt # -# # -# bernd.schmitt@psi.ch # -# # -##################################################################### -# # -# modifications: # -# # -# 1.3.2002 BS adapted for use with DCB # -# # -# 25.5.2002 BS adapted to new convert program # -# # -# 29.5.2002 sleep -> usleep for meas. time , TS # -# # -##################################################################### - -BEGIN { - -# initialize variables - NPAR=3 - - PAR[1]="nrun" - PAR[2]="fn" - PAR[3]="par" - -# initialize default values - - - - PARVAL[1] = 100 - PARVAL[2] = "microstrip_july2007" - PARVAL[3]=0 - - - - - - printf("\n\nnumber of command line arguments: %i (incl. command)\n\n", ARGC); - -# read command line defined variables - if (ARGC>1) { - printf("\n\nnumber of command line arguments: %i (incl. command)\n\n", ARGC); - for (i=1; i<=ARGC; i++) { - printf("%s \n", ARGV[i]); - nsplit=split(ARGV[i],array,"=") - VAR = array[1]; - VAL = array[2]; - - for (j=1; j<=NPAR; j++) { - if ( VAR==PAR[j] ) { - PARVAL[j] = VAL - } - } - } - } - run=PARVAL[1] - fn=PARVAL[2] - par=PARVAL[3] - - -# print command line arguments - for (i=1; i<=NPAR; i++){ - printf("\t... %2i.\t%7s = %s\n", i, PAR[i], PARVAL[i] ); - } - printf("\n\n"); - -# generate parameter file - - fnamep=fn".parab" - printf("header before\n")>> fnamep - system("date >>"fnamep) - printf("run=%i \n", run ) >> fnamep - -#print detector parameters to file - if (par==1) { - - command="sls_detector_get exptime| awk -F \" \" '{print $2}'" - command | getline var - printf("acquisition time = %11.6f second(s)\n", var) >> fnamep - - command="sls_detector_get settings| awk -F \" \" '{print $2}'" - command | getline var - printf("settings = %s\n", var) >> fnamep; - - command="sls_detector_get threshold| awk -F \" \" '{print $2}'" - command | getline var - printf("threshold energy = %d eV\n", var) >> fnamep; - - command="sls_detector_get badchannels| awk -F \" \" '{print $2}'" - command | getline var - printf("bad channel list = %s\n",var) >> fnamep; - - - command="sls_detector_get angconv| awk -F \" \" '{print $2}'" - command | getline var - printf("angle calibration conversion = %s\n",var) >> fnamep; - - - command="sls_detector_get globaloff| awk -F \" \" '{print $2}'" - command | getline var - printf("beamline offset = %f deg\n", var) >> fnamep; - - command="sls_detector_get fineoff| awk -F \" \" '{print $2}'" - command | getline var - printf("fine offset = %f deg\n", var) >> fnamep; - - command="sls_detector_get flatfield| awk -F \" \" '{print $2}'" - command | getline var - printf("Flat field corrections = %s\n",var) >> fnamep; - - command="sls_detector_get ratecorr| awk -F \" \" '{print $2}'" - command | getline var - printf("Dead time corrections tau = %d ns\n",var) >> fnamep; - - } - - -#print beamline parameters to file - -#read detector position - system("caget X04SA-ES2-TH2:RO.RBV >>"fnamep) -#read I0 - system("caget X04SA-ES2-SC:CH6>>"fnamep) -} - - - - - diff --git a/examples/scripts/ScanScript.awk b/examples/scripts/ScanScript.awk deleted file mode 100755 index 7617e340c..000000000 --- a/examples/scripts/ScanScript.awk +++ /dev/null @@ -1,87 +0,0 @@ -#! /bin/awk -f - -# this is an awk script to start a run -# you first need to run inimodule.awk to initialize -# the pattern, set Vc and set the trimbits -# - -##################################################################### -# revision history # -##################################################################### -# 31.10.2001 first version # -##################################################################### -# # -# Bernd Schmitt # -# # -# bernd.schmitt@psi.ch # -# # -##################################################################### -# # -# modifications: # -# # -# 1.3.2002 BS adapted for use with DCB # -# # -# 25.5.2002 BS adapted to new convert program # -# # -# 29.5.2002 sleep -> usleep for meas. time , TS # -# # -##################################################################### - -BEGIN { - -# initialize variables - NPAR=4 - - PAR[1]="nrun" - PAR[2]="fn" - PAR[3]="var" - PAR[4]="par" - - -# initialize default values - PARVAL[1] = 100 - PARVAL[2] = "myfname" - PARVAL[3] = 0 - PARVAL[2] = "none" - - - -# read command line defined variables - if (ARGC>1) { - printf("\n\nnumber of command line arguments: %i (incl. command)\n\n", ARGC); - for (i=1; i<=ARGC; i++) { - - nsplit=split(ARGV[i],array,"=") - VAR = array[1]; - VAL = array[2]; - - for (j=1; j<=NPAR; j++) { - if ( VAR==PAR[j] ) { - PARVAL[j] = VAL - } - } - } - } - - run=PARVAL[1] - fn=PARVAL[2] - var=PARVAL[3] - par=PARVAL[4] - - - - -# print command line arguments - for (i=1; i<=NPAR; i++){ - printf("\t... %2i.\t%7s = %s\n", i, PAR[i], PARVAL[i] ); - } - -#execute you command hereafter e.g. change temperature etc. - - -} - - - - - diff --git a/examples/scripts/ScriptBeforeAfter.awk b/examples/scripts/ScriptBeforeAfter.awk deleted file mode 100755 index 14838e280..000000000 --- a/examples/scripts/ScriptBeforeAfter.awk +++ /dev/null @@ -1,100 +0,0 @@ -#! /bin/awk -f - -# this is an awk script to start a run -# you first need to run inimodule.awk to initialize -# the pattern, set Vc and set the trimbits -# - -##################################################################### -# revision history # -##################################################################### -# 31.10.2001 first version # -##################################################################### -# # -# Bernd Schmitt # -# # -# bernd.schmitt@psi.ch # -# # -##################################################################### -# # -# modifications: # -# # -# 1.3.2002 BS adapted for use with DCB # -# # -# 25.5.2002 BS adapted to new convert program # -# # -# 29.5.2002 sleep -> usleep for meas. time , TS # -# # -##################################################################### - -BEGIN { - -# initialize variables - NPAR=7 - - PAR[1]="nrun" - PAR[2]="fn" - PAR[3]="par" - PAR[4]="sv0" - PAR[5]="sv1" - PAR[6]="p0" - PAR[7]="p1" - -# initialize default values - PARVAL[1] = 100 - PARVAL[2] = "myfname" - PARVAL[3] = 1 - PARVAL[4] = 0 - PARVAL[5] = 0 - PARVAL[6] = "none" - PARVAL[7] = "none" - - - -# read command line defined variables - if (ARGC>1) { - printf("\n\nnumber of command line arguments: %i (incl. command)\n\n", ARGC); - for (i=1; i<=ARGC; i++) { - - nsplit=split(ARGV[i],array,"=") - VAR = array[1]; - VAL = array[2]; - - for (j=1; j<=NPAR; j++) { - if ( VAR==PAR[j] ) { - PARVAL[j] = VAL - } - } - } - } - - run=PARVAL[1] - fn=PARVAL[2] - "par"PAR[3]= - sv0=PAR[4] - sv1=PAR[5] - p0=PAR[6] - p1=PAR[7] - - - -# print command line arguments - for (i=1; i<=NPAR; i++){ - printf("\t... %2i.\t%7s = %s\n", i, PAR[i], PARVAL[i] ); - } -# printf("\n\n"); - # system("close_shutter_g95") - -# execute your actions hereafter - if (par==1) { - #open shutter - } else { - #close shutter - } - -} - - - - - diff --git a/examples/scripts/StartStopScript.awk b/examples/scripts/StartStopScript.awk deleted file mode 100755 index f8e53917c..000000000 --- a/examples/scripts/StartStopScript.awk +++ /dev/null @@ -1,79 +0,0 @@ -#! /bin/awk -f - -# this is an awk script to start a run -# you first need to run inimodule.awk to initialize -# the pattern, set Vc and set the trimbits -# - -##################################################################### -# revision history # -##################################################################### -# 31.10.2001 first version # -##################################################################### -# # -# Bernd Schmitt # -# # -# bernd.schmitt@psi.ch # -# # -##################################################################### -# # -# modifications: # -# # -# 1.3.2002 BS adapted for use with DCB # -# # -# 25.5.2002 BS adapted to new convert program # -# # -# 29.5.2002 sleep -> usleep for meas. time , TS # -# # -##################################################################### - -BEGIN { - -# initialize variables - NPAR=2 - - PAR[1]="nrun" - PAR[2]="par" - - -# initialize default values - PARVAL[1] = 100 - PARVAL[2] = "none" - - - -# read command line defined variables - if (ARGC>1) { - printf("\n\nnumber of command line arguments: %i (incl. command)\n\n", ARGC); - for (i=1; i<=ARGC; i++) { - - nsplit=split(ARGV[i],array,"=") - VAR = array[1]; - VAL = array[2]; - - for (j=1; j<=NPAR; j++) { - if ( VAR==PAR[j] ) { - PARVAL[j] = VAL - } - } - } - } - - run=PARVAL[1] - par=PARVAL[2] - - - - -# print command line arguments - for (i=1; i<=NPAR; i++){ - printf("\t... %2i.\t%7s = %s\n", i, PAR[i], PARVAL[i] ); - } -#execute action hereafter - -} - - - - - diff --git a/examples/two_no_receiver.config b/examples/two_no_receiver.config deleted file mode 100755 index 18718ad64..000000000 --- a/examples/two_no_receiver.config +++ /dev/null @@ -1,64 +0,0 @@ -#####Any line with a # is not read###### - -#type Gotthard+ -hostname bchip007+bchip009+ - -#0:hostname bchip007 -#0:port 1952 -#0:stopport 1953 -#0:rx_tcpport 1956 -0:settingsdir /home/l_msdetect/dhanya/slsDetectorsPackage/settingsdir/gotthard -0:angdir 1.000000 -0:moveflag 0.000000 -0:lock 0 -0:caldir /home/l_msdetect/dhanya/slsDetectorsPackage/settingsdir/gotthard -0:ffdir /home/l_msdetect -0:extsig:0 off -0:extsig:1 off -0:extsig:2 off -0:extsig:3 off -#0:detectorip 10.1.1.2 -#0:detectormac 00:aa:bb:cc:dd:ee -#0:rx_udpport 50001 -#0:rx_udpip 10.1.1.1 -#0:rx_hostname 129.129.202.134 -0:outdir /data/speedt -0:vhighvoltage 120 - - -#1:hostname bchip009 -#1:port 1952 -#1:stopport 1953 -1:rx_tcpport 1957 -1:settingsdir /home/l_msdetect/dhanya/slsDetectorsPackage/settingsdir/gotthard -1:angdir 1.000000 -1:moveflag 0.000000 -1:lock 0 -1:caldir /home/l_msdetect/dhanya/slsDetectorsPackage/settingsdir/gotthard -1:ffdir /home/l_msdetect -1:extsig:0 off -1:extsig:1 off -1:extsig:2 off -1:extsig:3 off -#1:detectorip 10.1.2.2 -#1:detectormac 00:aa:bb:cc:dd:ee -#1:rx_udpport 50004 -#1:rx_udpip 10.1.2.1 -#1:rx_hostname 129.129.202.134 -1:outdir /data/speedt -1:vhighvoltage 120 - - -master -1 -sync none -outdir /data/speedt -ffdir /home/l_msdetect -headerbefore none -headerafter none -headerbeforepar none -headerafterpar none -badchannels none -angconv none -globaloff 0.000000 -binsize 0.001000 -threaded 1 From e2ef043e040becea668a8e9301a801b45e46a962 Mon Sep 17 00:00:00 2001 From: Erik Frojdh Date: Fri, 24 May 2019 16:31:25 +0200 Subject: [PATCH 8/8] removed old configure file --- configure | 58 ------------------------------------------------------- 1 file changed, 58 deletions(-) delete mode 100755 configure diff --git a/configure b/configure deleted file mode 100755 index a58728f9f..000000000 --- a/configure +++ /dev/null @@ -1,58 +0,0 @@ -##!/bin/bash - -: ${INSTALLROOT=$PWD} -read -p "Installation directory [default:\"$INSTALLROOT\"]:" -e t3 -if [ -z "$t3" ] -then -echo -else - INSTALLROOT=$t3 -fi -echo "INSTALLROOT will be \"$INSTALLROOT\"" -export INSTALLROOT - -: ${BINDIR="bin"} -read -p "Binaries directory [default:\"$BINDIR\"]:" -e t4 -if [ -z "$t4" ] -then - BINDIR=$INSTALLROOT/$BINDIR -else - BINDIR=$INSTALLROOT/$t4 -fi -echo "BINDIR will be \"$BINDIR\"" -export BINDIR - -: ${LIBDIR="bin"} -read -p "Libraries directory [default:\"$LIBDIR\"]:" -e t5 -if [ -z "$t5" ] -then - LIBDIR=$INSTALLROOT/$LIBDIR -else - LIBDIR=$INSTALLROOT/$t5 -fi -echo "LIBDIR will be \"$LIBDIR\"" -export LIBDIR - -: ${INCDIR="include"} -read -p "Includes directory [default:\"$INCDIR\"]:" -e t6 -if [ -z "$t6" ] -then - INCDIR=$INSTALLROOT/$INCDIR -else - INCDIR=$INSTALLROOT/$t6 -fi -echo "INCDIR will be \"$INCDIR\"" -export INCDIR - -: ${DOCDIR="doc"} -read -p "Documentation directory [default:\"$DOCDIR\"]:" -e t7 -if [ -z "$t7" ] -then - DOCDIR=$INSTALLROOT/$DOCDIR -else - DOCDIR=$INSTALLROOT/$t7 -fi -echo "DOCDIR will be \"$DOCDIR\"" -export DOCDIR - -