diff --git a/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c index 2d34011f4..106c1ae44 100644 --- a/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c @@ -572,8 +572,8 @@ void setupDetector() { if (initError == FAIL) return; - // power off voltage regulators - powerChip(false); + // power regulators + powerOff(); // adcs AD9257_SetDefines(ADC_SPI_REG, ADC_SPI_SRL_CS_OTPT_MSK, @@ -1625,6 +1625,13 @@ int getPowerRailMask(enum PWRINDEX index, uint32_t *mask, char *mess) { return OK; } +void powerOff() { + LOG(logINFOBLUE, ("Powering OFF all rails\n")); + // cannot call setPowerRailEnabled because of vchip dependency + uint32_t mask = POWER_ENBL_VLTG_RGLTR_MSK; + bus_w(POWER_REG, bus_r(POWER_REG) & ~(mask)); +} + int setPowerRailEnabled(enum DACINDEX indices[], int count, bool enable, char *mess) { // get power indices for log messages and mask diff --git a/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.h b/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.h index a5ae19911..da460ae61 100644 --- a/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.h +++ b/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.h @@ -151,12 +151,12 @@ int validatePower(enum DACINDEX ind, int val, char *mess); int getPowerIndexFromDACIndex(enum DACINDEX ind, enum PWRINDEX *pwrIndex, char *mess); int getPowerRailMask(enum PWRINDEX ind, uint32_t *mask, char *mess); + +void powerOff(); int setPowerRailEnabled(enum DACINDEX indices[], int count, bool enable, char *mess); int isPowerRailEnabled(enum DACINDEX ind, bool *retval, char *mess); int verifyPowerRailDisabled(enum DACINDEX ind, char *dacName, char *mess); -void powerChip(bool enable); -int getPowerChip(); int getADC(enum ADCINDEX ind); int getSlowADC(int ichan); diff --git a/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c b/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c index 925318a90..9270ab43b 100644 --- a/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c +++ b/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c @@ -1957,7 +1957,7 @@ int acquire(int blocking, int file_des) { } // only set if (Server_VerifyLock() == OK) { -#if defined(XILINX_CHIPTESTBOARDD) || defined(GOTTHARD2D) +#if defined(GOTTHARD2D) if (!isChipConfigured()) { ret = FAIL; strcpy(mess, "Could not start acquisition. Chip is not configured. " @@ -4006,8 +4006,7 @@ int power_chip(int file_des) { LOG(logDEBUG1, ("Powering chip to %d\n", arg)); #if !defined(JUNGFRAUD) && !defined(MOENCHD) && !defined(MYTHEN3D) && \ - !defined(GOTTHARD2D) && !defined(XILINX_CHIPTESTBOARDD) && \ - !defined(CHIPTESTBOARDD) + !defined(GOTTHARD2D) functionNotImplemented(); #else // set & get @@ -4026,8 +4025,7 @@ int power_chip(int file_des) { } } #endif -#if defined(XILINX_CHIPTESTBOARDD) || defined(CHIPTESTBOARDD) || \ - defined(GOTTHARD2D) +#if defined(GOTTHARD2D) if (ret == OK) { if (arg != -1) { if (arg != 0 && arg != 1) { @@ -4035,16 +4033,11 @@ int power_chip(int file_des) { sprintf(mess, "Power chip %d should be 0 or 1\n", arg); LOG(logERROR, (mess)); } else { -#if defined(GOTTHARD2D) || defined(XILINX_CHIPTESTBOARDD) ret = powerChip(arg, mess); -#else - powerChip(arg); -#endif } } if (ret == OK) { retval = getPowerChip(); - LOG(logDEBUG1, ("Power chip: %d\n", retval)); validate(&ret, mess, arg, retval, "power on/off chip", DEC); } } @@ -10871,17 +10864,9 @@ int config_transceiver(int file_des) { ret = OK; memset(mess, 0, sizeof(mess)); -#if !defined(XILINX_CHIPTESTBOARDD) + // currently not implemented anymore. functionNotImplemented(); -#else - if (Server_VerifyLock() == OK) { - LOG(logINFO, ("Configuring Transceiver\n")); - ret = configureTransceiver(mess); - if (ret == FAIL) { - LOG(logERROR, (mess)); - } - } -#endif + return Server_SendResult(file_des, INT32, NULL, 0); } diff --git a/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.c index f8689c5cb..697c3701c 100644 --- a/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.c @@ -41,7 +41,6 @@ char initErrorMessage[MAX_STR_LENGTH]; int detPos[2] = {0, 0}; uint32_t clkFrequency[NUM_CLOCKS] = {}; -int chipConfigured = 0; int analogEnable = 0; int digitalEnable = 0; int transceiverEnable = 0; @@ -379,7 +378,6 @@ void setupDetector() { clkFrequency[ADC_CLK] = DEFAULT_ADC_CLK; clkFrequency[SYNC_CLK] = DEFAULT_SYNC_CLK; clkFrequency[DBIT_CLK] = DEFAULT_DBIT_CLK; - chipConfigured = 0; analogEnable = 0; digitalEnable = 0; transceiverEnable = 0; @@ -397,11 +395,11 @@ void setupDetector() { if (initError == FAIL) { return; } - // power off chip - initError = powerChip(false, initErrorMessage); - if (initError == FAIL) { + + // power regulators + initError = powerOff(initErrorMessage); + if (initError == FAIL) return; - } LTC2620_D_SetDefines(DAC_MIN_MV, DAC_MAX_MV, DAC_DRIVER_FILE_NAME, NDAC, NPWR, DAC_POWERDOWN_DRIVER_FILE_NAME); @@ -511,18 +509,6 @@ int waitTransceiverReset(char *mess) { return OK; } -#ifdef VIRTUAL -void setTransceiverAlignment(int align) { - if (align) { - bus_w(TRANSCEIVERSTATUS, - (bus_r(TRANSCEIVERSTATUS) | RXBYTEISALIGNED_MSK)); - } else { - bus_w(TRANSCEIVERSTATUS, - (bus_r(TRANSCEIVERSTATUS) & ~RXBYTEISALIGNED_MSK)); - } -} -#endif - int isTransceiverAligned() { #ifdef VIRTUAL return 1; @@ -539,300 +525,6 @@ int isTransceiverAligned() { return retval; } -int waitTransceiverAligned(char *mess) { -#ifdef VIRTUAL - setTransceiverAlignment(1); -#else - - // no module: transceiver will never get aligned - if (!checkModuleFlag) { - LOG(logWARNING, ("No module: Transceiver will never get aligned. " - "Ignoring alignment check.\n")); - return OK; - } - - int transceiverWordAligned = isTransceiverAligned(); - int times = 0; - while (transceiverWordAligned == 0) { - if (times++ > WAIT_TIME_OUT_0US_TIMES) { - sprintf(mess, "Transceiver alignment timed out. Check connection, " - "p-n inversions, LSB-MSB inversions, link error " - "counters and channel enable settings\n"); - LOG(logERROR, (mess)); - return FAIL; - } - usleep(0); - transceiverWordAligned = isTransceiverAligned(); - } -#endif - LOG(logINFOBLUE, ("Transceiver alignment done\n")); - return OK; -} - -int configureTransceiver(char *mess) { - LOG(logINFOBLUE, ("\tConfiguring transceiver\n")); - - if (chipConfigured == 0) { - sprintf(mess, - "Chip not configured. Use powerchip to power on chip first.\n"); - LOG(logERROR, (mess)); - return FAIL; - } - return waitTransceiverAligned(mess); -} - -int isChipConfigured() { return chipConfigured; } - -// TODO powerchip and configurechip should be separate commands (not -// requirement) in the future -int powerChip(bool on, char *mess) { - uint32_t addr = CTRL_REG; - uint32_t mask = POWER_VIO_MSK | POWER_VCC_A_MSK | POWER_VCC_B_MSK | - POWER_VCC_C_MSK | POWER_VCC_D_MSK; - if (on) { - LOG(logINFOBLUE, ("Powering ON all\n")); - bus_w(addr, bus_r(addr) | mask); - - if (configureChip(mess) == FAIL) - return FAIL; - - } else { - LOG(logINFOBLUE, ("Powering OFF all\n")); - bus_w(addr, bus_r(addr) & ~mask); - chipConfigured = 0; - if (FAIL == XILINX_FMC_disable_all(mess, MAX_STR_LENGTH)) { - return FAIL; - } -#ifdef VIRTUAL - setTransceiverAlignment(0); -#endif - // transceiver alignment should be reset at power off - if (isTransceiverAligned()) { - sprintf(mess, "Transceiver alignment not reset\n"); - LOG(logERROR, (mess)); - - // to be removed when fixed later - LOG(logWARNING, - ("Bypassing this error for now. To be fixed later...\n")); - return OK; - - return FAIL; - } - LOG(logINFO, ("\tTransceiver alignment has been reset\n")); - } - return OK; -} - -int getPowerChip() { - uint32_t mask = POWER_VIO_MSK | POWER_VCC_A_MSK | POWER_VCC_B_MSK | - POWER_VCC_C_MSK | POWER_VCC_D_MSK; - uint32_t retval = bus_r(CTRL_REG) & mask; - if (retval == 0) - return 0; - if (retval == mask) - return 1; - LOG(logINFO, ("Power chip state is neither fully on nor fully off. Value " - "read: 0x%x\n", - retval)); - return -1; -} - -int configureChip(char *mess) { - LOG(logINFOBLUE, ("\tConfiguring chip\n")); - chipConfigured = 0; - if (readConfigFile(mess, CONFIG_CHIP_FILE, "chip config") == FAIL) { - return FAIL; - } - if (readConfigFile(mess, RESET_CHIP_FILE, "reset chip") == FAIL) { - return FAIL; - } - LOG(logINFOBLUE, ("Chip configured.\n")); - chipConfigured = 1; - return OK; -} - -int readConfigFile(char *mess, char *fileName, char *fileType) { - const int fileNameSize = 128; - char fname[fileNameSize]; - if (getAbsPath(fname, fileNameSize, fileName) == FAIL) { - sprintf(mess, "Could not get full path for %s file [%s].\n", fileType, - fname); - LOG(logERROR, (mess)); - return FAIL; - } - if (access(fname, F_OK) != 0) { - sprintf(mess, "Could not find %s file [%s].\n", fileType, fname); - LOG(logERROR, (mess)); - return FAIL; - } - FILE *fd = fopen(fname, "r"); - if (fd == NULL) { - sprintf(mess, "Could not open on-board detector server %s file [%s].\n", - fileType, fname); - LOG(logERROR, (mess)); - return FAIL; - } - LOG(logINFOBLUE, ("Reading %s file %s\n", fileType, fname)); - - const size_t LZ = 256; - char line[LZ]; - memset(line, 0, LZ); - char command[LZ]; - - // keep reading a line - while (fgets(line, LZ, fd)) { - - // ignore comments - if (line[0] == '#') { - LOG(logDEBUG1, ("Ignoring Comment\n")); - continue; - } - - // ignore empty lines - if (strlen(line) <= 1) { - LOG(logDEBUG1, ("Ignoring Empty line\n")); - continue; - } - - // removing leading spaces - if (line[0] == ' ' || line[0] == '\t') { - int len = strlen(line); - // find first valid character - int i = 0; - for (i = 0; i < len; ++i) { - if (line[i] != ' ' && line[i] != '\t') { - break; - } - } - // ignore the line full of spaces (last char \n) - if (i >= len - 1) { - LOG(logDEBUG1, ("Ignoring line full of spaces\n")); - continue; - } - // copying only valid char - char temp[LZ]; - memset(temp, 0, LZ); - memcpy(temp, line + i, strlen(line) - i); - memset(line, 0, LZ); - memcpy(line, temp, strlen(temp)); - LOG(logDEBUG1, ("Removing leading spaces.\n")); - } - - LOG(logDEBUG1, ("Command to process: (size:%d) %.*s\n", strlen(line), - strlen(line) - 1, line)); - memset(command, 0, LZ); - - // reg command - if (!strncmp(line, "reg", strlen("reg"))) { - uint32_t addr = 0; - uint32_t val = 0; - if (sscanf(line, "%s %x %x", command, &addr, &val) != 3) { - sprintf(mess, "Could not scan reg command. Line:[%s].\n", line); - LOG(logERROR, (mess)); - return FAIL; - } - bus_w(addr, val); - LOG(logINFOBLUE, ("Wrote 0x%x to 0x%x\n", val, addr)); - } - - // setbit command - else if (!strncmp(line, "setbit", strlen("setbit"))) { - uint32_t addr = 0; - uint32_t bit = 0; - if (sscanf(line, "%s %x %d", command, &addr, &bit) != 3) { - sprintf(mess, "Could not scan setbit command. Line:[%s].\n", - line); - LOG(logERROR, (mess)); - return FAIL; - } - bus_w(addr, bus_r(addr) | (1 << bit)); - LOG(logINFOBLUE, ("Set bit %d in 0x%x\n", bit, addr)); - } - - // clearbit command - else if (!strncmp(line, "clearbit", strlen("clearbit"))) { - uint32_t addr = 0; - uint32_t bit = 0; - if (sscanf(line, "%s %x %d", command, &addr, &bit) != 3) { - sprintf(mess, "Could not scan clearbit command. Line:[%s].\n", - line); - LOG(logERROR, (mess)); - return FAIL; - } - bus_w(addr, bus_r(addr) & ~(1 << bit)); - LOG(logINFOBLUE, ("Cleared bit %d in 0x%x\n", bit, addr)); - } - - // pollbit command - else if (!strncmp(line, "pollbit", strlen("pollbit"))) { - uint32_t addr = 0; - uint32_t bit = 0; - uint32_t val = 0; - if (sscanf(line, "%s %x %d %d", command, &addr, &bit, &val) != 4) { - sprintf(mess, "Could not scan pollbit command. Line:[%s].\n", - line); - LOG(logERROR, (mess)); - return FAIL; - } -#ifndef VIRTUAL - int times = 0; - while (((bus_r(addr) >> bit) & 0x1) != val) { - if (times++ > WAIT_TIME_OUT_0US_TIMES) { - sprintf(mess, "Polling bit %d in 0x%x timed out\n", bit, - addr); - LOG(logERROR, (mess)); - return FAIL; - } - usleep(0); - } -#endif - LOG(logINFOBLUE, ("Polled bit %d in 0x%x\n", bit, addr)); - } - - // pattern command - else if (!strncmp(line, "pattern", strlen("pattern"))) { - // take a file name and call loadPatterFile - char patternFileName[LZ]; - if (sscanf(line, "%s %s", command, patternFileName) != 2) { - sprintf(mess, "Could not scan pattern command. Line:[%s].\n", - line); - LOG(logERROR, (mess)); - return FAIL; - } - if (loadPatternFile(patternFileName, mess) == FAIL) { - return FAIL; - } - LOG(logINFOBLUE, ("loaded pattern [%s].\n", patternFileName)); - } - - // sleep command - else if (!strncmp(line, "sleep", strlen("sleep"))) { - int time = 0; - if (sscanf(line, "%s %d", command, &time) != 2) { - sprintf(mess, "Could not scan sleep command. Line:[%s].\n", - line); - LOG(logERROR, (mess)); - return FAIL; - } - usleep(time * 1000 * 1000); - LOG(logINFOBLUE, ("Slept for %d s\n", time)); - } - - // other commands - else { - sprintf(mess, - "Could not scan command from on-board server " - "%s file. Line:[%s].\n", - fileType, line); - break; - } - memset(line, 0, LZ); - } - fclose(fd); - LOG(logINFOBLUE, ("Successfully read %s file.\n", fileType)); - return OK; -} - /* set parameters - dr */ int setDynamicRange(int dr) { @@ -1442,6 +1134,20 @@ int getPowerRailMask(enum PWRINDEX index, uint32_t *mask, char *mess) { return OK; } +int powerOff(char *mess) { + LOG(logINFOBLUE, ("Powering OFF all rails\n")); + enum DACINDEX indices[] = {D_PWR_D, D_PWR_C, D_PWR_B, D_PWR_A, D_PWR_IO}; + int count = sizeof(indices) / sizeof(indices[0]); + int ret = setPowerRailEnabled(indices, count, false, mess); + if (ret == FAIL) + return FAIL; + + if (XILINX_FMC_disable_all(mess, MAX_STR_LENGTH) == FAIL) + return FAIL; + + return OK; +} + int setPowerRailEnabled(enum DACINDEX indices[], int count, bool enable, char *mess) { // get power indices for log messages and mask diff --git a/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.h b/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.h index 47fcc5b5d..3e38d20de 100644 --- a/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.h +++ b/slsDetectorServers/xilinx_ctbDetectorServer/slsDetectorFunctionList.h @@ -63,18 +63,7 @@ void setupDetector(); void cleanFifos(); void resetFlow(); int waitTransceiverReset(char *mess); -#ifdef VIRTUAL -void setTransceiverAlignment(int align); -#endif int isTransceiverAligned(); -int waitTransceiverAligned(char *mess); -int configureTransceiver(char *mess); -int isChipConfigured(); -int powerChip(bool on, char *mess); -int getPowerChip(); -int configureChip(char *mess); -int readConfigFile(char *mess, char *fileName, char *fileType); -int resetChip(char *mess); // parameters - dr, roi int setDynamicRange(int dr); @@ -138,6 +127,8 @@ int validatePower(enum DACINDEX ind, int val, char *mess); int getPowerIndexFromDACIndex(enum DACINDEX ind, enum PWRINDEX *pwrIndex, char *mess); int getPowerRailMask(enum PWRINDEX ind, uint32_t *mask, char *mess); + +int powerOff(char *mess); int setPowerRailEnabled(enum DACINDEX indices[], int count, bool enable, char *mess); int isPowerRailEnabled(enum DACINDEX ind, bool *retval, char *mess); diff --git a/slsDetectorSoftware/src/CallerSpecial.cpp b/slsDetectorSoftware/src/CallerSpecial.cpp index 79c583a0e..70d8004c2 100644 --- a/slsDetectorSoftware/src/CallerSpecial.cpp +++ b/slsDetectorSoftware/src/CallerSpecial.cpp @@ -1969,8 +1969,9 @@ std::string Caller::power(int action) { if (action == defs::HELP_ACTION) { os << "[list of power names] [on|off]\n\t[Ctb][Xilinx Ctb] Enable or " "disable power rails. Power name can be v_a, v_b, v_c, v_d or " - "v_io or any names set using powername. One can retrieve only " - "one at a time." + "v_io or any defines using 'powername'. If power name is set to " + "'all', the command applies to all 'powers'. Only one power can " + "be queried at a time." << '\n'; return os.str(); } @@ -1993,18 +1994,33 @@ std::string Caller::power(int action) { } else if (action == defs::PUT_ACTION) { + bool all = false; + if (std::find(args.begin(), args.end(), "all") != args.end()) { + if (args.size() != 2) + WrongNumberOfParameters(2); + all = true; + } if (args.size() < 1 || args.size() > 6) { WrongNumberOfParameters(1); } + + // enable arg std::string lastArg = args.back(); if (lastArg != "on" && lastArg != "off") { throw RuntimeError("Last argument '" + lastArg + - "' must be on or off"); + "' is enable. Options: 'on' or 'off'"); } bool enable = StringTo(lastArg, defs::OnOff); + + // power indices std::vector powerIndices; - for (size_t i = 0; i < args.size() - 1; ++i) { - powerIndices.push_back(parsePowerIndex(i)); + if (all) { + powerIndices = det->getPowerList(); + } else { + // push back indices from command line + for (size_t i = 0; i < args.size() - 1; ++i) { + powerIndices.push_back(parsePowerIndex(i)); + } } det->setPowerEnabled(powerIndices, enable, std::vector{det_id}); diff --git a/slsDetectorSoftware/src/Detector.cpp b/slsDetectorSoftware/src/Detector.cpp index d0648318f..801e470cc 100644 --- a/slsDetectorSoftware/src/Detector.cpp +++ b/slsDetectorSoftware/src/Detector.cpp @@ -2200,6 +2200,9 @@ Result Detector::isPowerEnabled(defs::dacIndex index, void Detector::setPowerEnabled(const std::vector &indices, bool value, Positions pos) { + if (indices.empty()) { + throw RuntimeError("No Power Index provided"); + } std::vector valid_indices = getPowerList(); for (const auto &index : indices) { if (std::find(valid_indices.begin(), valid_indices.end(), index) == diff --git a/slsDetectorSoftware/tests/Caller/test-Caller-chiptestboard.cpp b/slsDetectorSoftware/tests/Caller/test-Caller-chiptestboard.cpp index 5e86153f2..4c689c133 100644 --- a/slsDetectorSoftware/tests/Caller/test-Caller-chiptestboard.cpp +++ b/slsDetectorSoftware/tests/Caller/test-Caller-chiptestboard.cpp @@ -1266,8 +1266,8 @@ TEST_CASE("power", "[.detectorintegration]") { REQUIRE(oss[6].str() == "power v_d on\n"); REQUIRE(oss[7].str() == "power v_io off\n"); } - { // power chip - caller.call("powerchip", {"1"}, -1, PUT); + { // power on all + caller.call("power", {"all", "on"}, -1, PUT); std::ostringstream oss1, oss2, oss3, oss4, oss5; caller.call("power", {"v_a"}, -1, GET, oss1); caller.call("power", {"v_b"}, -1, GET, oss2); @@ -1280,6 +1280,7 @@ TEST_CASE("power", "[.detectorintegration]") { REQUIRE(oss4.str() == "power v_d on\n"); REQUIRE(oss5.str() == "power v_io on\n"); } + REQUIRE_THROWS(caller.call("power", {"all"}, -1, GET)); for (size_t iPower = 0; iPower < cmds.size(); ++iPower) { det.setPowerEnabled(std::vector{indices[iPower]}, prev_val[iPower]); } diff --git a/slsDetectorSoftware/tests/Caller/test-Caller.cpp b/slsDetectorSoftware/tests/Caller/test-Caller.cpp index ba05b1350..f7f815d58 100644 --- a/slsDetectorSoftware/tests/Caller/test-Caller.cpp +++ b/slsDetectorSoftware/tests/Caller/test-Caller.cpp @@ -1547,9 +1547,7 @@ TEST_CASE("powerchip", "[.detectorintegration]") { auto det_type = det.getDetectorType().squash(); if (det_type == defs::JUNGFRAU || det_type == defs::MOENCH || - det_type == defs::MYTHEN3 || det_type == defs::GOTTHARD2 || - det_type == defs::XILINX_CHIPTESTBOARD || - det_type == defs::CHIPTESTBOARD) { + det_type == defs::MYTHEN3 || det_type == defs::GOTTHARD2) { auto prev_val = det.getPowerChip().tsquash("Inconsistent power chip values"); { diff --git a/tests/scripts/utils_for_test.py b/tests/scripts/utils_for_test.py index 9e1b527ee..ae8930860 100644 --- a/tests/scripts/utils_for_test.py +++ b/tests/scripts/utils_for_test.py @@ -305,11 +305,11 @@ def loadConfig(name, rx_hostname = 'localhost', settingsdir = None, log_file_fp if num_interfaces == 2: d.udp_dstip2 = 'auto' - if name == "jungfrau" or name == "moench" or name == "xilinx_ctb": + if name == "jungfrau" or name == "moench": d.powerchip = 1 - if name == "xilinx_ctb": - d.configureTransceiver() + #if name == "xilinx_ctb": + # d.configureTransceiver() if settingsdir is not None and name in ['eiger', 'mythen3']: d.settingspath = settingsdir + '/' + name + '/'