diff --git a/slsDetectorServers/ctbDetectorServer/bin/ctbDetectorServer_developer b/slsDetectorServers/ctbDetectorServer/bin/ctbDetectorServer_developer index eaa7761d3..49e8e536a 100755 Binary files a/slsDetectorServers/ctbDetectorServer/bin/ctbDetectorServer_developer and b/slsDetectorServers/ctbDetectorServer/bin/ctbDetectorServer_developer differ diff --git a/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c index da84f3d86..e7f57a896 100644 --- a/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/ctbDetectorServer/slsDetectorFunctionList.c @@ -25,7 +25,7 @@ // Global variable from slsDetectorServer_funcs extern int debugflag; extern int updateFlag; -extern udpStruct udpDetails; +extern udpStruct udpDetails[MAX_UDP_DESTINATION]; extern const enum detectorType myDetectorType; // Global variable from UDPPacketHeaderGenerator @@ -55,10 +55,10 @@ char *digitalData = 0; char volatile *analogDataPtr = 0; char volatile *digitalDataPtr = 0; char udpPacketData[UDP_PACKET_DATA_BYTES + sizeof(sls_detector_header)]; -uint32_t adcEnableMask_1g = 0; +uint32_t adcEnableMask_1g = BIT32_MSK; // 10g readout -uint8_t adcEnableMask_10g = 0; +uint8_t adcEnableMask_10g = 0xFF; int32_t clkPhase[NUM_CLOCKS] = {}; uint32_t clkFrequency[NUM_CLOCKS] = {40, 20, 20, 200}; @@ -392,7 +392,7 @@ uint32_t getDetectorIP() { #ifdef VIRTUAL return 0; #endif - char temp[50] = ""; + char temp[INET_ADDRSTRLEN] = ""; uint32_t res = 0; // execute and get address char output[255]; @@ -470,8 +470,8 @@ void setupDetector() { } vLimit = DEFAULT_VLIMIT; highvoltage = 0; - adcEnableMask_1g = 0; - adcEnableMask_10g = 0; + adcEnableMask_1g = BIT32_MSK; + adcEnableMask_10g = 0xFF; analogEnable = 1; digitalEnable = 0; naSamples = 1; @@ -480,6 +480,7 @@ void setupDetector() { sharedMemory_setStatus(IDLE); initializePatternWord(); #endif + setupUDPCommParameters(); ALTERA_PLL_ResetPLLAndReconfiguration(); resetCore(); @@ -1516,18 +1517,18 @@ void calcChecksum(udp_header *udp) { } int configureMAC() { - uint32_t srcip = udpDetails.srcip; - uint32_t dstip = udpDetails.dstip; - uint64_t srcmac = udpDetails.srcmac; - uint64_t dstmac = udpDetails.dstmac; - int srcport = udpDetails.srcport; - int dstport = udpDetails.dstport; + uint32_t srcip = udpDetails[0].srcip; + uint32_t dstip = udpDetails[0].dstip; + uint64_t srcmac = udpDetails[0].srcmac; + uint64_t dstmac = udpDetails[0].dstmac; + int srcport = udpDetails[0].srcport; + int dstport = udpDetails[0].dstport; LOG(logINFOBLUE, ("Configuring MAC\n")); - char src_mac[50], src_ip[INET_ADDRSTRLEN], dst_mac[50], - dst_ip[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac, 50, srcmac); - getMacAddressinString(dst_mac, 50, dstmac); + char src_mac[MAC_ADDRESS_SIZE], src_ip[INET_ADDRSTRLEN], + dst_mac[MAC_ADDRESS_SIZE], dst_ip[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, srcmac); + getMacAddressinString(dst_mac, MAC_ADDRESS_SIZE, dstmac); getIpAddressinString(src_ip, srcip); getIpAddressinString(dst_ip, dstip); @@ -1544,7 +1545,7 @@ int configureMAC() { LOG(logINFOBLUE, ("\t1G MAC\n")); if (updateDatabytesandAllocateRAM() == FAIL) return -1; - if (setUDPDestinationDetails(0, dst_ip, dstport) == FAIL) { + if (setUDPDestinationDetails(0, 0, dst_ip, dstport) == FAIL) { LOG(logERROR, ("could not set udp 1G destination IP and port\n")); return FAIL; } @@ -2023,7 +2024,7 @@ void *start_timer(void *arg) { imageData + srcOffset, dataSize); srcOffset += dataSize; - sendUDPPacket(0, packetData, packetSize); + sendUDPPacket(0, 0, packetData, packetSize); } LOG(logINFO, ("Sent frame: %d [%lld]\n", frameNr, (long long unsigned int)virtual_currentFrameNumber)); @@ -2140,10 +2141,10 @@ void readandSendUDPFrames(int *ret, char *mess) { LOG(logDEBUG1, ("Reading from 1G UDP\n")); // validate udp socket - if (getUdPSocketDescriptor(0) <= 0) { + if (getUdPSocketDescriptor(0, 0) <= 0) { *ret = FAIL; sprintf(mess, "UDP Socket not created. sockfd:%d\n", - getUdPSocketDescriptor(0)); + getUdPSocketDescriptor(0, 0)); LOG(logERROR, (mess)); return; } @@ -2152,7 +2153,7 @@ void readandSendUDPFrames(int *ret, char *mess) { while (readFrameFromFifo() == OK) { int bytesToSend = 0, n = 0; while ((bytesToSend = fillUDPPacket(udpPacketData))) { - n += sendUDPPacket(0, udpPacketData, bytesToSend); + n += sendUDPPacket(0, 0, udpPacketData, bytesToSend); } if (n >= dataBytes) { LOG(logINFO, (" Frame %lld sent (%d packets, %d databytes, n:%d " diff --git a/slsDetectorServers/eigerDetectorServer/Beb.c b/slsDetectorServers/eigerDetectorServer/Beb.c index 6bc68a9d4..0a4bbb5de 100644 --- a/slsDetectorServers/eigerDetectorServer/Beb.c +++ b/slsDetectorServers/eigerDetectorServer/Beb.c @@ -10,9 +10,6 @@ #define MAX(x, y) (((x) > (y)) ? (x) : (y)) -struct BebInfo beb_infos[10]; -int bebInfoSize = 0; - struct LocalLinkInterface ll_beb_local, *ll_beb; struct udp_header_type udp_header; @@ -31,8 +28,6 @@ short Beb_bit_mode; int BEB_MMAP_SIZE = 0x1000; int Beb_activated = 1; - -uint32_t Beb_detid = 0; int Beb_top = 0; uint64_t Beb_deactivatedNextFrameNumber = 0; @@ -45,72 +40,10 @@ int Beb_deactivated_transmission_delay_left = 0; int Beb_deactivated_transmission_delay_right = 0; int Beb_deactivated_left_datastream = 1; int Beb_deactivated_right_datastream = 1; +int Beb_deactivated_num_destinations = 1; -void BebInfo_BebInfo(struct BebInfo *bebInfo, unsigned int beb_num) { - bebInfo->beb_number = beb_num; - bebInfo->serial_address = 0; - strcpy(bebInfo->src_mac_1GbE, ""); - strcpy(bebInfo->src_mac_10GbE, ""); - strcpy(bebInfo->src_ip_1GbE, ""); - strcpy(bebInfo->src_ip_10GbE, ""); - bebInfo->src_port_1GbE = bebInfo->src_port_10GbE = 0; -} -int BebInfo_SetSerialAddress(struct BebInfo *bebInfo, unsigned int a) { - // address pre shifted - if (a > 0xff) - return 0; - bebInfo->serial_address = 0x04000000 | ((a & 0xff) << 16); - return 1; -} - -int BebInfo_SetHeaderInfo(struct BebInfo *bebInfo, int ten_gig, char *src_mac, - char *src_ip, unsigned int src_port) { - if (ten_gig) { - strcpy(bebInfo->src_mac_10GbE, src_mac); - strcpy(bebInfo->src_ip_10GbE, src_ip); - bebInfo->src_port_10GbE = src_port; - } else { - strcpy(bebInfo->src_mac_1GbE, src_mac); - strcpy(bebInfo->src_ip_1GbE, src_ip); - bebInfo->src_port_1GbE = src_port; - } - return 1; -} - -unsigned int BebInfo_GetBebNumber(struct BebInfo *bebInfo) { - return bebInfo->beb_number; -} -unsigned int BebInfo_GetSerialAddress(struct BebInfo *bebInfo) { - return bebInfo->serial_address; -} -char *BebInfo_GetSrcMAC(struct BebInfo *bebInfo, int ten_gig) { - return ten_gig ? bebInfo->src_mac_10GbE : bebInfo->src_mac_1GbE; -} -char *BebInfo_GetSrcIP(struct BebInfo *bebInfo, int ten_gig) { - return ten_gig ? bebInfo->src_ip_10GbE : bebInfo->src_ip_1GbE; -} -unsigned int BebInfo_GetSrcPort(struct BebInfo *bebInfo, int ten_gig) { - return ten_gig ? bebInfo->src_port_10GbE : bebInfo->src_port_1GbE; -} - -void BebInfo_Print(struct BebInfo *bebInfo) { - LOG(logINFO, - ("%d) Beb Info:\n" - "\tSerial Add: 0x%x\n" - "\tMAC 1GbE: %s\n" - "\tIP 1GbE: %s\n" - "\tPort 1GbE: %d\n" - "\tMAC 10GbE: %s\n" - "\tIP 10GbE: %s\n" - "\tPort 10GbE: %d\n", - bebInfo->beb_number, bebInfo->serial_address, bebInfo->src_mac_1GbE, - bebInfo->src_ip_1GbE, bebInfo->src_port_1GbE, bebInfo->src_mac_10GbE, - bebInfo->src_ip_10GbE, bebInfo->src_port_10GbE)); -} - -void Beb_Beb(int id) { - Beb_detid = id; +void Beb_Beb() { Beb_send_ndata = 0; Beb_send_buffer_size = 1026; Beb_send_data_raw = @@ -143,19 +76,126 @@ void Beb_Beb(int id) { {0x00, 0x00}, //{0x00, 0x11}, {0x00, 0x00}}; - if (!Beb_InitBebInfos()) - exit(1); - - LOG(logDEBUG1, ("Printing Beb infos:\n")); - for (unsigned int i = 1; i < bebInfoSize; i++) - BebInfo_Print(&beb_infos[i]); + Beb_ClearHeaderData(0); + Beb_ClearHeaderData(1); Beb_bit_mode = 4; +} - // ll_beb = &ll_beb_local; - // Local_LocalLinkInterface(ll_beb,XPAR_PLB_LL_FIFO_AURORA_DUAL_CTRL_FEB_LEFT_BASEADDR); +void Beb_ClearHeaderData(int ten_gig) { + for (int i = 0; i < MAX_UDP_DESTINATION; ++i) { + if (!Beb_SetUpUDPHeader(i, ten_gig, 0, 0, 0, 0, 0, 0)) { + LOG(logERROR, ("Could not clear header data for entry %d (tengiga:%d)\n", i, ten_gig)); + } + } +} - // Beb_SetByteOrder(); +int Beb_SetUpUDPHeader(unsigned int header_number, int ten_gig, + uint64_t src_mac, uint32_t src_ip, uint16_t src_port, + uint64_t dst_mac, uint32_t dst_ip, uint16_t dst_port) { + + if (!Beb_activated) + return 1; + + u_int32_t bram_phy_addr; + u_int32_t *csp0base = 0; + if (ten_gig) + bram_phy_addr = 0xC6002000; + else + bram_phy_addr = 0xC6001000; + + if (!Beb_SetHeaderData(src_mac, src_ip, src_port, dst_mac, dst_ip, dst_port)) + return 0; + + int fd = Beb_open(&csp0base, bram_phy_addr); + if (fd < 0) { + LOG(logERROR, ("Set up UDP Header FAIL\n")); + } else { + // read data + memcpy(csp0base + header_number * 16, &udp_header, sizeof(udp_header)); + // close file pointer + Beb_close(fd, csp0base); + } + return 1; +} + +int Beb_SetHeaderData(uint64_t src_mac, uint32_t src_ip, uint16_t src_port, + uint64_t dst_mac, uint32_t dst_ip, uint16_t dst_port) { + + // src mac is after dst mac in structure (6 bit each) + uint16_t src_msb = ((src_mac >> 32) & BIT16_MASK); + uint32_t src_lsb = ((src_mac >> 0) & BIT32_MASK); + memcpy(&(udp_header.src_mac[0]), &src_msb, sizeof(src_msb)); + memcpy(&(udp_header.src_mac[2]), &src_lsb, sizeof(src_lsb)); + for (int i = 0; i < 6; ++i) { + LOG(logDEBUG1, + ("src mac[%d]: %02x\n", i, (uint8_t *)udp_header.src_mac[i])); + } + + memcpy(&(udp_header.src_ip[0]), &src_ip, sizeof(udp_header.src_ip)); + for (int i = 0; i < 4; ++i) { + LOG(logDEBUG1, + ("src ip[%d]: %02x\n", i, (uint8_t *)udp_header.src_ip[i])); + } + + memcpy(&(udp_header.src_port[0]), &src_port, sizeof(udp_header.src_port)); + for (int i = 0; i < 2; ++i) { + LOG(logDEBUG1, + ("src port[%d]: %02x\n", i, (uint8_t *)udp_header.src_port[i])); + } + + uint32_t dst_msb = ((dst_mac >> 16) & BIT32_MASK); + uint16_t dst_lsb = ((dst_mac >> 0) & BIT16_MASK); + memcpy(&(udp_header.dst_mac[0]), &dst_msb, sizeof(dst_msb)); + memcpy(&(udp_header.dst_mac[4]), &dst_lsb, sizeof(dst_lsb)); + for (int i = 0; i < 6; ++i) { + LOG(logDEBUG1, + ("dst mac[%d]: %02x\n", i, (uint8_t *)udp_header.dst_mac[i])); + } + + memcpy(&(udp_header.dst_ip[0]), &dst_ip, sizeof(udp_header.dst_ip)); + for (int i = 0; i < 4; ++i) { + LOG(logDEBUG1, + ("dst ip[%d]: %02x\n", i, (uint8_t *)udp_header.dst_ip[i])); + } + + memcpy(&(udp_header.dst_port[0]), &dst_port, + sizeof(udp_header.dst_port)); + for (int i = 0; i < 2; ++i) { + LOG(logDEBUG1, + ("dst port[%d]: %02x\n", i, (uint8_t *)udp_header.dst_port[i])); + } + + Beb_AdjustIPChecksum(&udp_header); + + unsigned int *base_ptr = (unsigned int *)&udp_header; + unsigned int num_words = (sizeof(struct udp_header_type) + 3) / 4; + for (unsigned int i = 0; i < num_words; i++) + Beb_send_data[i + 2] = base_ptr[i]; + for (unsigned int i = num_words; i < 16; i++) + Beb_send_data[i + 2] = 0; + + return 1; +} + +void Beb_AdjustIPChecksum(struct udp_header_type *ip) { + unsigned char *cptr = (unsigned char *)ip->ver_headerlen; + + ip->ip_header_checksum[0] = 0; + ip->ip_header_checksum[1] = 0; + ip->total_length[0] = 0; + ip->total_length[1] = 28; // IP + UDP Header Length + + // calc ip checksum + unsigned int ip_checksum = 0; + for (unsigned int i = 0; i < 10; i++) { + ip_checksum += ((cptr[2 * i] << 8) + (cptr[2 * i + 1])); + if (ip_checksum & 0x00010000) + ip_checksum = (ip_checksum + 1) & 0x0000ffff; + } + + ip->ip_header_checksum[0] = (ip_checksum >> 8) & 0xff; + ip->ip_header_checksum[1] = ip_checksum & 0xff; } void Beb_GetModuleConfiguration(int *master, int *top, int *normal) { @@ -816,357 +856,11 @@ void Beb_ResetFrameNumber() { } } -void Beb_ClearBebInfos() { bebInfoSize = 0; } - -int Beb_InitBebInfos() { // file name at some point - Beb_ClearBebInfos(); - - struct BebInfo b0; - BebInfo_BebInfo(&b0, 0); - if (BebInfo_SetSerialAddress( - &b0, - 0xff)) { // all bebs for reset and possibly get request data? - beb_infos[bebInfoSize] = b0; - bebInfoSize++; - } - - int i0 = Beb_detid, i1 = 0; - if (Beb_GetBebInfoIndex(i0)) { - LOG(logERROR, - ("cant add beb. adding beb %d, beb number %d already added.\n", - Beb_detid, i0)); - exit(0); - } - struct BebInfo b1; - BebInfo_BebInfo(&b1, i0); - BebInfo_SetSerialAddress(&b1, i1); - BebInfo_SetHeaderInfo(&b1, 0, (char *)"00:50:c2:46:d9:34", - (char *)"129.129.205.78", 42000 + i0); - BebInfo_SetHeaderInfo(&b1, 1, (char *)"00:50:c2:46:d9:35", - (char *)"10.0.26.1", 52000 + i0); - beb_infos[bebInfoSize] = b1; - bebInfoSize++; - - /* -//loop through file to fill vector. -BebInfo* b = new BebInfo(26); -b->SetSerialAddress(0); //0xc4000000 -b->SetHeaderInfo(0,"00:50:c2:46:d9:34","129.129.205.78",42000 + 26); // 1 -GbE, ip address can be acquire from the network "arp" -b->SetHeaderInfo(1,"00:50:c2:46:d9:35","10.0.26.1",52000 + 26); //10 GbE, -everything calculable/setable beb_infos.push_back(b); - */ - - return Beb_CheckSourceStuffBebInfo(); -} - -int Beb_SetBebSrcHeaderInfos(unsigned int beb_number, int ten_gig, - char *src_mac, char *src_ip, - unsigned int src_port) { - // so that the values can be reset externally for now.... - - unsigned int i = 1; /*Beb_GetBebInfoIndex(beb_number);*/ - /******* if (!i) return 0;****************************/ // i must be - // greater than - // 0, zero is - // the global - // send - BebInfo_SetHeaderInfo(&beb_infos[i], ten_gig, src_mac, src_ip, src_port); - - LOG(logINFO, ("Printing Beb info number (%d) :\n", i)); - BebInfo_Print(&beb_infos[i]); - - return 1; -} - -int Beb_CheckSourceStuffBebInfo() { - for (unsigned int i = 1; i < bebInfoSize; - i++) { // header stuff always starts from 1 - if (!Beb_SetHeaderData(BebInfo_GetBebNumber(&beb_infos[i]), 0, - "00:00:00:00:00:00", "10.0.0.1", 20000) || - !Beb_SetHeaderData(BebInfo_GetBebNumber(&beb_infos[i]), 1, - "00:00:00:00:00:00", "10.0.0.1", 20000)) { - LOG(logINFO, ("Error in BebInfo for module number %d.\n", - BebInfo_GetBebNumber(&beb_infos[i]))); - BebInfo_Print(&beb_infos[i]); - return 0; - } - } - return 1; -} - -unsigned int Beb_GetBebInfoIndex(unsigned int beb_numb) { - for (unsigned int i = 1; i < bebInfoSize; i++) - if (beb_numb == BebInfo_GetBebNumber(&beb_infos[i])) { - LOG(logDEBUG1, - ("*****found beb index:%d, for beb number:%d\n", i, beb_numb)); - return i; - } - LOG(logDEBUG1, ("*****Returning 0\n")); - return 0; -} - -int Beb_WriteTo(unsigned int index) { - - if (!Beb_activated) - return 1; - - if (index >= bebInfoSize) { - LOG(logERROR, ("WriteTo index error.\n")); - return 0; - } - - Beb_send_data_raw[0] = - 0x90000000 | BebInfo_GetSerialAddress(&beb_infos[index]); - if (Local_Write(ll_beb, 4, Beb_send_data_raw) != 4) - return 0; - - Beb_send_data_raw[0] = 0xc0000000; - if ((Beb_send_ndata + 1) * 4 != - Local_Write(ll_beb, (Beb_send_ndata + 1) * 4, Beb_send_data_raw)) - return 0; - - return 1; -} - -void Beb_SwapDataFun(int little_endian, unsigned int n, unsigned int *d) { - if (little_endian) - for (unsigned int i = 0; i < n; i++) - d[i] = (((d[i] & 0xff) << 24) | ((d[i] & 0xff00) << 8) | - ((d[i] & 0xff0000) >> 8) | - ((d[i] & 0xff000000) >> 24)); // little_endian - else - for (unsigned int i = 0; i < n; i++) - d[i] = (((d[i] & 0xffff) << 16) | ((d[i] & 0xffff0000) >> 16)); -} - -int Beb_SetByteOrder() { return 1; } - -int Beb_SetUpUDPHeader(unsigned int beb_number, int ten_gig, - unsigned int header_number, char *dst_mac, char *dst_ip, - unsigned int dst_port) { - - if (!Beb_activated) - return 1; - - u_int32_t bram_phy_addr; - u_int32_t *csp0base = 0; - /*u_int32_t* bram_ptr = NULL;*/ - if (ten_gig) - bram_phy_addr = 0xC6002000; - else - bram_phy_addr = 0xC6001000; - - if (!Beb_SetHeaderData(beb_number, ten_gig, dst_mac, dst_ip, dst_port)) - return 0; - - int fd = Beb_open(&csp0base, bram_phy_addr); - if (fd < 0) { - LOG(logERROR, ("Set up UDP Header FAIL\n")); - } else { - // read data - memcpy(csp0base + header_number * 16, &udp_header, sizeof(udp_header)); - // close file pointer - Beb_close(fd, csp0base); - } - return 1; -} - -int Beb_SetHeaderData(unsigned int beb_number, int ten_gig, char *dst_mac, - char *dst_ip, unsigned int dst_port) { - unsigned int i = 1; /*Beb_GetBebInfoIndex(beb_number);*/ - /***********************************if (!i) return 0; - * *************************************///i must be greater than 0, zero is the global send - return Beb_SetHeaderData1(BebInfo_GetSrcMAC(&beb_infos[i], ten_gig), - BebInfo_GetSrcIP(&beb_infos[i], ten_gig), - BebInfo_GetSrcPort(&beb_infos[i], ten_gig), - dst_mac, dst_ip, dst_port); -} - -int Beb_SetHeaderData1(char *src_mac, char *src_ip, unsigned int src_port, - char *dst_mac, char *dst_ip, unsigned int dst_port) { - /* example header*/ - // static unsigned int* word_ptr = new unsigned int [16]; - /*static*/ - /* -udp_header_type udp_header = { - {0x00, 0x50, 0xc5, 0xb2, 0xcb, 0x46}, // DST MAC - {0x00, 0x50, 0xc2, 0x46, 0xd9, 0x02}, // SRC MAC - {0x08, 0x00}, - {0x45}, - {0x00}, - {0x00, 0x00}, - {0x00, 0x00}, - {0x40}, - {0x00}, - {0xff}, - {0x11}, - {0x00, 0x00}, - {129, 205, 205, 128}, // Src IP - {129, 205, 205, 122}, // Dst IP - {0x0f, 0xa1}, - {0x13, 0x89}, - {0x00, 0x00}, //{0x00, 0x11}, - {0x00, 0x00} - }; - */ - - if (!Beb_SetMAC(src_mac, &(udp_header.src_mac[0]))) - return 0; - LOG(logINFO, ("Setting Source MAC to %s\n", src_mac)); - if (!Beb_SetIP(src_ip, &(udp_header.src_ip[0]))) - return 0; - LOG(logINFO, ("Setting Source IP to %s\n", src_ip)); - if (!Beb_SetPortNumber(src_port, &(udp_header.src_port[0]))) - return 0; - LOG(logINFO, ("Setting Source port to %d\n", src_port)); - - if (!Beb_SetMAC(dst_mac, &(udp_header.dst_mac[0]))) - return 0; - LOG(logINFO, ("Setting Destination MAC to %s\n", dst_mac)); - if (!Beb_SetIP(dst_ip, &(udp_header.dst_ip[0]))) - return 0; - LOG(logINFO, ("Setting Destination IP to %s\n", dst_ip)); - if (!Beb_SetPortNumber(dst_port, &(udp_header.dst_port[0]))) - return 0; - LOG(logINFO, ("Setting Destination port to %d\n", dst_port)); - - Beb_AdjustIPChecksum(&udp_header); - - unsigned int *base_ptr = (unsigned int *)&udp_header; - unsigned int num_words = (sizeof(struct udp_header_type) + 3) / 4; - for (unsigned int i = 0; i < num_words; i++) - Beb_send_data[i + 2] = base_ptr[i]; - for (unsigned int i = num_words; i < 16; i++) - Beb_send_data[i + 2] = 0; - - return 1; -} - -int Beb_SetMAC(char *mac, uint8_t *dst_ptr) { - char macVal[50]; - strcpy(macVal, mac); - - int i = 0; - char *pch = strtok(macVal, ":"); - while (pch != NULL) { - if (strlen(pch) != 2) { - LOG(logERROR, ("Error: in mac address -> %s\n", macVal)); - return 0; - } - - int itemp; - sscanf(pch, "%x", &itemp); - dst_ptr[i] = (u_int8_t)itemp; - pch = strtok(NULL, ":"); - i++; - } - return 1; -} - -int Beb_SetIP(char *ip, uint8_t *dst_ptr) { - char ipVal[50]; - strcpy(ipVal, ip); - int i = 0; - char *pch = strtok(ipVal, "."); - while (pch != NULL) { - if (((i != 3) && ((strlen(pch) > 3) || (strlen(pch) < 1))) || - ((i == 3) && ((strlen(pch) < 1) || (strlen(pch) > 3)))) { - LOG(logERROR, ("Error: in ip address -> %s\n", ipVal)); - return 0; - } - - int itemp; - sscanf(pch, "%d", &itemp); - dst_ptr[i] = (u_int8_t)itemp; - pch = strtok(NULL, "."); - i++; - } - return 1; -} - -int Beb_SetPortNumber(unsigned int port_number, uint8_t *dst_ptr) { - dst_ptr[0] = (port_number >> 8) & 0xff; - dst_ptr[1] = port_number & 0xff; - return 1; -} - -void Beb_AdjustIPChecksum(struct udp_header_type *ip) { - unsigned char *cptr = (unsigned char *)ip->ver_headerlen; - - ip->ip_header_checksum[0] = 0; - ip->ip_header_checksum[1] = 0; - ip->total_length[0] = 0; - ip->total_length[1] = 28; // IP + UDP Header Length - - // calc ip checksum - unsigned int ip_checksum = 0; - for (unsigned int i = 0; i < 10; i++) { - ip_checksum += ((cptr[2 * i] << 8) + (cptr[2 * i + 1])); - if (ip_checksum & 0x00010000) - ip_checksum = (ip_checksum + 1) & 0x0000ffff; - } - - ip->ip_header_checksum[0] = (ip_checksum >> 8) & 0xff; - ip->ip_header_checksum[1] = ip_checksum & 0xff; -} - -int Beb_SendMultiReadRequest(unsigned int beb_number, unsigned int left_right, - int ten_gig, unsigned int dst_number, - unsigned int npackets, unsigned int packet_size, - int stop_read_when_fifo_empty) { - - // This is a dead function, will be removed in future - // ================================================== - - unsigned int i = - 1; /*Beb_GetBebInfoIndex(beb_number); //zero is the global send*/ - - Beb_send_ndata = 3; - if (left_right == 1) - Beb_send_data[0] = 0x00040000; - else if (left_right == 2) - Beb_send_data[0] = 0x00080000; - else if (left_right == 3) - Beb_send_data[0] = 0x000c0000; - else - return 0; - - // packet_size/=2; - if (dst_number > 0x3f) - return 0; - if (packet_size > 0x3ff) - return 0; - if (npackets == 0 || npackets > 0x100) - return 0; - npackets--; - - Beb_send_data[1] = 0x62000000 | (!stop_read_when_fifo_empty) << 27 | - (ten_gig == 1) << 24 | packet_size << 14 | - dst_number << 8 | npackets; - LOG(logDEBUG1, ("Beb_send_data[1]:%X\n", Beb_send_data[1])); - Beb_send_data[2] = 0; - - Beb_SwapDataFun(0, 2, &(Beb_send_data[1])); - LOG(logDEBUG1, ("Beb_send_data[1] Swapped:%X\n", Beb_send_data[1])); - - if (Beb_activated) { - if (!Beb_WriteTo(i)) - return 0; - } - - return 1; -} - int Beb_SetUpTransferParameters(short the_bit_mode) { if (the_bit_mode != 4 && the_bit_mode != 8 && the_bit_mode != 16 && the_bit_mode != 32) return 0; Beb_bit_mode = the_bit_mode; - - // nimages = the_number_of_images; - // on_dst = 0; - return 1; } @@ -1203,16 +897,11 @@ int Beb_StopAcquisition() { return 1; } -int Beb_RequestNImages(unsigned int beb_number, int ten_gig, - unsigned int dst_number, unsigned int nimages, - int test_just_send_out_packets_no_wait) { +int Beb_RequestNImages(int ten_gig, unsigned int nimages, int test_just_send_out_packets_no_wait) { if (!Beb_activated) return 1; - if (dst_number > 64) - return 0; - - unsigned int maxnl = MAX_ROWS_PER_READOUT; + unsigned int maxnl = MAX_ROWS_PER_READOUT; unsigned int maxnp = (ten_gig ? 4 : 16) * Beb_bit_mode; unsigned int nl = Beb_partialReadout; unsigned int npackets = (nl * maxnp) / maxnl; @@ -1229,10 +918,10 @@ int Beb_RequestNImages(unsigned int beb_number, int ten_gig, unsigned int packet_size = ten_gig ? 0x200 : 0x80; // 4k or 1k packets LOG(logDEBUG1, ("----Beb_RequestNImages Start----\n")); - LOG(logINFO, ("beb_number:%d, ten_gig:%d,dst_number:%d, npackets:%d, " + LOG(logINFO, ("ten_gig:%d, npackets:%d, " "Beb_bit_mode:%d, header_size:%d, nimages:%d, " "test_just_send_out_packets_no_wait:%d\n", - beb_number, ten_gig, dst_number, npackets, Beb_bit_mode, + ten_gig, npackets, Beb_bit_mode, header_size, nimages, test_just_send_out_packets_no_wait)); u_int32_t right_port_value = 0x2000; @@ -1260,7 +949,6 @@ int Beb_RequestNImages(unsigned int beb_number, int ten_gig, ("%X\n", Beb_Read32(csp0base, (LEFT_OFFSET + i * 4)))); } LOG(logDEBUG1, ("%d\n", in_two_requests)); - //"0x20 << 8" is dst_number (0x00 for left, 0x20 for right) // Left Beb_Write32(csp0base, (LEFT_OFFSET + FIRST_CMD_PART1_OFFSET), 0); Beb_Write32(csp0base, (LEFT_OFFSET + FIRST_CMD_PART2_OFFSET), @@ -1310,41 +998,6 @@ int Beb_RequestNImages(unsigned int beb_number, int ten_gig, return 1; } -int Beb_Test(unsigned int beb_number) { - LOG(logINFO, ("Testing module number: %d\n", beb_number)); - - // int SetUpUDPHeader(unsigned int beb_number, int ten_gig, unsigned int - // header_number, string dst_mac, string dst_ip, unsigned int dst_port) - // { SetUpUDPHeader(26,0,0,"60:fb:42:f4:e3:d2","129.129.205.186",22000); - - unsigned int index = Beb_GetBebInfoIndex(beb_number); - if (!index) { - LOG(logERROR, ("Error beb number (%d)not in list????\n", beb_number)); - return 0; - } - - for (unsigned int i = 0; i < 64; i++) { - if (!Beb_SetUpUDPHeader(beb_number, 0, i, "60:fb:42:f4:e3:d2", - "129.129.205.186", 22000 + i)) { - LOG(logERROR, ("Error setting up header table....\n")); - return 0; - } - } - - // SendMultiReadRequest(unsigned int beb_number, unsigned int - // left_right, int ten_gig, unsigned int dst_number, unsigned int - // npackets, unsigned int packet_size, int - // stop_read_when_fifo_empty=1); - for (unsigned int i = 0; i < 64; i++) { - if (!Beb_SendMultiReadRequest(beb_number, i % 3 + 1, 0, i, 1, 0, 1)) { - LOG(logERROR, ("Error requesting data....\n")); - return 0; - } - } - - return 1; -} - // Returns the FPGA temperature from the xps sysmon ip core // Temperature value is cropped and not well rounded int Beb_GetBebFPGATemp() { @@ -1614,6 +1267,63 @@ int Beb_GetNextFrameNumber(uint64_t *retval, int tengigaEnable) { void Beb_SetPartialReadout(int value) { Beb_partialReadout = value; } +int Beb_GetNumberofDestinations(int *retval) { + if (!Beb_activated) { + *retval = Beb_deactivated_num_destinations; + return OK; + } + u_int32_t offset[2] = {LEFT_OFFSET + NUM_UDP_DEST_OFFSET, + RIGHT_OFFSET + NUM_UDP_DEST_OFFSET}; + u_int32_t *csp0base = 0; + int fd = Beb_open(&csp0base, XPAR_CMD_GENERATOR); + if (fd <= 0) { + LOG(logERROR, ("Could not read register to get number of udp " + "destinations. FAIL\n")); + return FAIL; + } else { + int retval1[2] = {0, 0}; + retval1[0] = Beb_Read32(csp0base, offset[0]); + retval1[1] = Beb_Read32(csp0base, offset[1]); + Beb_close(fd, csp0base); + if (retval1[0] != retval1[1]) { + LOG(logERROR, ("Inconsistent values on left (%d) and right (%d) " + "fpga for number of destinations. FAIL\n", + retval1[0], retval1[1])); + return FAIL; + } + *retval = ++retval1[0]; + return OK; + } +} + +int Beb_SetNumberofDestinations(int value) { + LOG(logINFO, ("Setting number of destinations to %d\n", value)); + if (value < 0 || value >= MAX_UDP_DESTINATION) { + LOG(logERROR, ("Invalid number of destinations %d\n", value)); + return FAIL; + } + if (!Beb_activated) { + Beb_deactivated_num_destinations = value; + return OK; + } + u_int32_t offset[2] = {LEFT_OFFSET + NUM_UDP_DEST_OFFSET, + RIGHT_OFFSET + NUM_UDP_DEST_OFFSET}; + u_int32_t *csp0base = 0; + int fd = Beb_open(&csp0base, XPAR_CMD_GENERATOR); + if (fd <= 0) { + LOG(logERROR, ("Could not read register to set number of udp " + "destinations. FAIL\n")); + return FAIL; + } else { + Beb_deactivated_num_destinations = value; + --value; + Beb_Write32(csp0base, offset[0], value); + Beb_Write32(csp0base, offset[1], value); + Beb_close(fd, csp0base); + return OK; + } +} + uint16_t Beb_swap_uint16(uint16_t val) { return (val << 8) | (val >> 8); } int Beb_open(u_int32_t **csp0base, u_int32_t offset) { diff --git a/slsDetectorServers/eigerDetectorServer/Beb.h b/slsDetectorServers/eigerDetectorServer/Beb.h index b29e252ea..152db2dd5 100644 --- a/slsDetectorServers/eigerDetectorServer/Beb.h +++ b/slsDetectorServers/eigerDetectorServer/Beb.h @@ -4,34 +4,14 @@ #include "slsDetectorServer_defs.h" #include -struct BebInfo { - unsigned int beb_number; - unsigned int serial_address; - char src_mac_1GbE[50]; - char src_mac_10GbE[50]; - char src_ip_1GbE[50]; - char src_ip_10GbE[50]; - unsigned int src_port_1GbE; - unsigned int src_port_10GbE; -}; - -void BebInfo_BebInfo(struct BebInfo *bebInfo, unsigned int beb_num); -void BebInfo_BebDstInfo(struct BebInfo *bebInfo, unsigned int beb_num); -int BebInfo_SetSerialAddress(struct BebInfo *bebInfo, unsigned int add); -int BebInfo_SetHeaderInfo( - struct BebInfo *bebInfo, int ten_gig, char *src_mac, char *src_ip, - unsigned int - src_port); // src_port fixed 42000+beb_number or 52000 + beb_number); -unsigned int BebInfo_GetBebNumber(struct BebInfo *bebInfo); -unsigned int BebInfo_GetSerialAddress(struct BebInfo *bebInfo); -char *BebInfo_GetSrcMAC(struct BebInfo *bebInfo, int ten_gig); -char *BebInfo_GetSrcIP(struct BebInfo *bebInfo, int ten_gig); -unsigned int BebInfo_GetSrcPort(struct BebInfo *bebInfo, int ten_gig); -void BebInfo_Print(struct BebInfo *bebInfo); -void Beb_ClearBebInfos(); -int Beb_InitBebInfos(); -int Beb_CheckSourceStuffBebInfo(); -unsigned int Beb_GetBebInfoIndex(unsigned int beb_numb); +void Beb_Beb(); +void Beb_ClearHeaderData(int ten_gig); +int Beb_SetUpUDPHeader(unsigned int header_number, int ten_gig, + uint64_t src_mac, uint32_t src_ip, uint16_t src_port, + uint64_t dst_mac, uint32_t dst_ip, uint16_t dst_port); +int Beb_SetHeaderData(uint64_t src_mac, uint32_t src_ip, uint16_t src_port, + uint64_t dst_mac, uint32_t dst_ip, uint16_t dst_port); +void Beb_AdjustIPChecksum(struct udp_header_type *ip); void Beb_GetModuleConfiguration(int *master, int *top, int *normal); int Beb_IsTransmitting(int *retval, int tengiga, int waitForDelay); @@ -44,7 +24,6 @@ int Beb_GetActivate(int *retval); int Beb_SetDataStream(enum portPosition port, int enable); int Beb_GetDataStream(enum portPosition port, int *retval); int Beb_Set32bitOverflow(int val); - int Beb_GetTenGigaFlowControl(); int Beb_SetTenGigaFlowControl(int value); int Beb_GetTransmissionDelayFrame(); @@ -56,50 +35,13 @@ int Beb_SetTransmissionDelayRight(int value); u_int32_t Beb_GetFirmwareRevision(); u_int32_t Beb_GetFirmwareSoftwareAPIVersion(); + void Beb_ResetFrameNumber(); -int Beb_WriteTo(unsigned int index); -int Beb_SetMAC(char *mac, uint8_t *dst_ptr); -int Beb_SetIP(char *ip, uint8_t *dst_ptr); -int Beb_SetPortNumber(unsigned int port_number, uint8_t *dst_ptr); -void Beb_AdjustIPChecksum(struct udp_header_type *ip); - -int Beb_SetHeaderData(unsigned int beb_number, int ten_gig, char *dst_mac, - char *dst_ip, unsigned int dst_port); -int Beb_SetHeaderData1(char *src_mac, char *src_ip, unsigned int src_port, - char *dst_mac, char *dst_ip, unsigned int dst_port); - -void Beb_SwapDataFun(int little_endian, unsigned int n, unsigned int *d); -int Beb_SetByteOrder(); -void Beb_Beb(); -int Beb_SetBebSrcHeaderInfos(unsigned int beb_number, int ten_gig, - char *src_mac, char *src_ip, - unsigned int src_port); -int Beb_SetUpUDPHeader(unsigned int beb_number, int ten_gig, - unsigned int header_number, char *dst_mac, char *dst_ip, - unsigned int dst_port); - -/*int Beb_SendMultiReadRequest(unsigned int beb_number, unsigned int - * left_right, int ten_gig, unsigned int dst_number, unsigned int npackets, - * unsigned int packet_size, int stop_read_when_fifo_empty=1);*/ -int Beb_SendMultiReadRequest(unsigned int beb_number, unsigned int left_right, - int ten_gig, unsigned int dst_number, - unsigned int npackets, unsigned int packet_size, - int stop_read_when_fifo_empty); - -int Beb_StopAcquisition(); int Beb_SetUpTransferParameters(short the_bit_mode); -/*int Beb_RequestNImages(unsigned int beb_number, unsigned int left_right, int - * ten_gig, unsigned int dst_number, unsigned int nimages, int - * test_just_send_out_packets_no_wait=0); //all images go to the same - * destination!*/ -int Beb_RequestNImages(unsigned int beb_number, int ten_gig, - unsigned int dst_number, unsigned int nimages, +int Beb_StopAcquisition(); +int Beb_RequestNImages(int ten_gig, unsigned int nimages, int test_just_send_out_packets_no_wait); - -int Beb_Test(unsigned int beb_number); - int Beb_GetBebFPGATemp(); - void Beb_SetDetectorNumber(uint32_t detid); int Beb_SetQuad(int value); int Beb_GetQuad(); @@ -107,8 +49,9 @@ int *Beb_GetDetectorPosition(); int Beb_SetDetectorPosition(int pos[]); int Beb_SetNextFrameNumber(uint64_t value); int Beb_GetNextFrameNumber(uint64_t *retval, int tengigaEnable); - void Beb_SetPartialReadout(int value); +int Beb_GetNumberofDestinations(int *retval); +int Beb_SetNumberofDestinations(int value); uint16_t Beb_swap_uint16(uint16_t val); int Beb_open(u_int32_t **csp0base, u_int32_t offset); diff --git a/slsDetectorServers/eigerDetectorServer/FebRegisterDefs.h b/slsDetectorServers/eigerDetectorServer/FebRegisterDefs.h index da4728be6..d1349735e 100644 --- a/slsDetectorServers/eigerDetectorServer/FebRegisterDefs.h +++ b/slsDetectorServers/eigerDetectorServer/FebRegisterDefs.h @@ -208,6 +208,7 @@ #define STOP_ACQ_BIT 0x40000000 #define TWO_REQUESTS_OFFSET 0x1c #define TWO_REQUESTS_BIT 0x80000000 +#define NUM_UDP_DEST_OFFSET 0x20 // version #define FIRMWARE_VERSION_OFFSET 0x4 diff --git a/slsDetectorServers/eigerDetectorServer/bin/eigerDetectorServer_developer b/slsDetectorServers/eigerDetectorServer/bin/eigerDetectorServer_developer index 9739cb51c..38c924b7c 100755 Binary files a/slsDetectorServers/eigerDetectorServer/bin/eigerDetectorServer_developer and b/slsDetectorServers/eigerDetectorServer/bin/eigerDetectorServer_developer differ diff --git a/slsDetectorServers/eigerDetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/eigerDetectorServer/slsDetectorFunctionList.c index 1b7c91d42..60cd9210c 100644 --- a/slsDetectorServers/eigerDetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/eigerDetectorServer/slsDetectorFunctionList.c @@ -21,7 +21,8 @@ // Global variable from slsDetectorServer_funcs extern int debugflag; extern int updateFlag; -extern udpStruct udpDetails; +extern udpStruct udpDetails[MAX_UDP_DESTINATION]; +extern int numUdpDestinations; extern const enum detectorType myDetectorType; // Global variable from communication_funcs.c @@ -40,11 +41,7 @@ int *detectorChans = NULL; int *detectorDacs = NULL; int send_to_ten_gig = 0; -int ndsts_in_use = 32; unsigned int nimages_per_request = 1; -int on_dst = 0; -int dst_requested[32] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; int top = 0; int master = 0; @@ -136,8 +133,10 @@ void basictests() { // update default udpdstip and udpdstmac (1g is hardware ip and hardware // mac) - udpDetails.srcip = ipadd; - udpDetails.srcmac = macadd; + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; ++iRxEntry) { + udpDetails[iRxEntry].srcip = ipadd; + udpDetails[iRxEntry].srcmac = macadd; + } #ifdef VIRTUAL return; @@ -284,7 +283,7 @@ u_int64_t getDetectorMAC() { } u_int32_t getDetectorIP() { - char temp[50] = ""; + char temp[INET_ADDRSTRLEN] = ""; u_int32_t res = 0; // execute and get address char output[255]; @@ -355,7 +354,7 @@ void initControlServer() { sharedMemory_unlockLocalLink(); LOG(logDEBUG1, ("Control server: FEB Initialization done\n")); Beb_SetTopVariable(top); - Beb_Beb(detid); + Beb_Beb(); Beb_SetDetectorNumber(getDetectorNumber()); LOG(logDEBUG1, ("Control server: BEB Initialization done\n")); #endif @@ -689,6 +688,7 @@ void setupDetector() { resetToDefaultDacs(0); #ifdef VIRTUAL sharedMemory_setStatus(IDLE); + setupUDPCommParameters(); #endif LOG(logINFOBLUE, ("Setting Default Parameters\n")); @@ -739,10 +739,16 @@ void setupDetector() { ("Module: %s %s %s\n", (top ? "TOP" : "BOTTOM"), (master ? "MASTER" : "SLAVE"), (normal ? "NORMAL" : "SPECIAL"))); + if (setNumberofDestinations(numUdpDestinations) == FAIL) { + initError = FAIL; + strcpy(initErrorMessage, "Could not set number of udp destinations\n"); + LOG(logERROR, (initErrorMessage)); + } + // client first connect (from shm) will activate if (setActivate(0) == FAIL) { initError = FAIL; - sprintf(initErrorMessage, "Could not deactivate\n"); + strcpy(initErrorMessage, "Could not deactivate\n"); LOG(logERROR, (initErrorMessage)); } LOG(logDEBUG1, ("Setup detector done\n\n")); @@ -833,9 +839,6 @@ int setDynamicRange(int dr) { #ifndef VIRTUAL sharedMemory_lockLocalLink(); if (Feb_Control_SetDynamicRange(dr)) { - on_dst = 0; - for (int i = 0; i < 32; ++i) - dst_requested[i] = 0; // clear dst requested if (!Beb_SetUpTransferParameters(dr)) { LOG(logERROR, ("Could not set bit mode in the back end\n")); sharedMemory_unlockLocalLink(); @@ -913,10 +916,6 @@ void setNumFrames(int64_t val) { sharedMemory_lockLocalLink(); if (Feb_Control_SetNExposures((unsigned int)val * eiger_ntriggers)) { eiger_nexposures = val; - on_dst = 0; - for (int i = 0; i < 32; ++i) - dst_requested[i] = 0; // clear dst requested - ndsts_in_use = 1; nimages_per_request = eiger_nexposures * eiger_ntriggers; } sharedMemory_unlockLocalLink(); @@ -936,9 +935,6 @@ void setNumTriggers(int64_t val) { sharedMemory_lockLocalLink(); if (Feb_Control_SetNExposures((unsigned int)val * eiger_nexposures)) { eiger_ntriggers = val; - on_dst = 0; - for (int i = 0; i < 32; ++i) - dst_requested[i] = 0; // clear dst requested nimages_per_request = eiger_nexposures * eiger_ntriggers; } sharedMemory_unlockLocalLink(); @@ -1517,80 +1513,96 @@ enum timingMode getTiming() { /* configure mac */ -int configureMAC() { - uint32_t srcip = udpDetails.srcip; - uint32_t dstip = udpDetails.dstip; - uint64_t srcmac = udpDetails.srcmac; - uint64_t dstmac = udpDetails.dstmac; - int srcport = udpDetails.srcport; - int dstport = udpDetails.dstport; - int dstport2 = udpDetails.dstport2; - - LOG(logINFOBLUE, ("Configuring MAC\n")); - char src_mac[50], src_ip[INET_ADDRSTRLEN], dst_mac[50], - dst_ip[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac, 50, srcmac); - getMacAddressinString(dst_mac, 50, dstmac); - getIpAddressinString(src_ip, srcip); - getIpAddressinString(dst_ip, dstip); - - LOG(logINFO, - ("\tSource IP : %s\n" - "\tSource MAC : %s\n" - "\tSource Port : %d\n" - "\tDest IP : %s\n" - "\tDest MAC : %s\n" - "\tDest Port : %d\n" - "\tDest Port2 : %d\n", - src_ip, src_mac, srcport, dst_ip, dst_mac, dstport, dstport2)); - +int getNumberofDestinations(int *retval) { #ifdef VIRTUAL - if (setUDPDestinationDetails(0, dst_ip, dstport) == FAIL) { - LOG(logERROR, ("could not set udp destination IP and port\n")); - return FAIL; - } - if (setUDPDestinationDetails(1, dst_ip, dstport2) == FAIL) { - LOG(logERROR, ("could not set udp destination IP and port2\n")); - return FAIL; - } + *retval = numUdpDestinations; return OK; #else - - int beb_num = detid; - int header_number = 0; - int dst_port = dstport; - if (!top) - dst_port = dstport2; - - if (Beb_SetBebSrcHeaderInfos(beb_num, send_to_ten_gig, src_mac, src_ip, - srcport) && - Beb_SetUpUDPHeader(beb_num, send_to_ten_gig, header_number, dst_mac, - dst_ip, dst_port)) { - LOG(logDEBUG1, ("\tset up left ok\n")); - } else { - return FAIL; - } - - header_number = 32; - dst_port = dstport2; - if (!top) - dst_port = dstport; - - if (Beb_SetBebSrcHeaderInfos(beb_num, send_to_ten_gig, src_mac, src_ip, - srcport) && - Beb_SetUpUDPHeader(beb_num, send_to_ten_gig, header_number, dst_mac, - dst_ip, dst_port)) { - LOG(logDEBUG1, (" set up right ok\n")); - } else { - return FAIL; - } - - on_dst = 0; - - for (int i = 0; i < 32; ++i) - dst_requested[i] = 0; // clear dst requested - nimages_per_request = eiger_nexposures * eiger_ntriggers; + return Beb_GetNumberofDestinations(retval); #endif +} + +int setNumberofDestinations(int value) { +#ifdef VIRTUAL + // already set in funcs.c + return OK; +#else + return Beb_SetNumberofDestinations(value); +#endif +} + +int configureMAC() { + + LOG(logINFOBLUE, ("Configuring MAC\n")); + + LOG(logINFO, ("Number of entries: %d\n", numUdpDestinations)); + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; ++iRxEntry) { + uint32_t srcip = udpDetails[iRxEntry].srcip; + uint32_t dstip = udpDetails[iRxEntry].dstip; + uint64_t srcmac = udpDetails[iRxEntry].srcmac; + uint64_t dstmac = udpDetails[iRxEntry].dstmac; + int srcport = udpDetails[iRxEntry].srcport; + int dstport = udpDetails[iRxEntry].dstport; + int dstport2 = udpDetails[iRxEntry].dstport2; + + char src_mac[MAC_ADDRESS_SIZE], src_ip[INET_ADDRSTRLEN], + dst_mac[MAC_ADDRESS_SIZE], dst_ip[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, srcmac); + getMacAddressinString(dst_mac, MAC_ADDRESS_SIZE, dstmac); + getIpAddressinString(src_ip, srcip); + getIpAddressinString(dst_ip, dstip); + + if (iRxEntry < numUdpDestinations) { + LOG(logINFOBLUE, ("\tEntry %d\n", iRxEntry)); + LOG(logINFO, + ("\tSource IP : %s\n" + "\tSource MAC : %s\n" + "\tSource Port : %d\n" + "\tDest IP : %s\n" + "\tDest MAC : %s\n" + "\tDest Port : %d\n" + "\tDest Port2 : %d\n", + src_ip, src_mac, srcport, dst_ip, dst_mac, dstport, dstport2)); + } + +#ifdef VIRTUAL + if (setUDPDestinationDetails(iRxEntry, 0, dst_ip, dstport) == FAIL) { + LOG(logERROR, + ("could not set udp destination IP and port [entry:%d]\n", + iRxEntry)); + return FAIL; + } + if (setUDPDestinationDetails(iRxEntry, 1, dst_ip, dstport2) == FAIL) { + LOG(logERROR, + ("could not set udp destination IP and port2 [entry:%d]\n", + iRxEntry)); + return FAIL; + } +#else + uint16_t dst_port = dstport; + if (!top) + dst_port = dstport2; + + if (Beb_SetUpUDPHeader(iRxEntry, send_to_ten_gig, srcmac, srcip, + srcport, dstmac, dstip, dst_port)) { + LOG(logDEBUG1, ("\tset up left ok\n")); + } else { + return FAIL; + } + + dst_port = dstport2; + if (!top) + dst_port = dstport; + + if (Beb_SetUpUDPHeader(iRxEntry + MAX_UDP_DESTINATION, send_to_ten_gig, + srcmac, srcip, srcport, dstmac, dstip, + dst_port)) { + LOG(logDEBUG1, ("\tset up right ok\n")); + } else { + return FAIL; + } +#endif + } return OK; } @@ -1706,6 +1718,9 @@ int enableTenGigabitEthernet(int val) { send_to_ten_gig = 1; else send_to_ten_gig = 0; +#ifndef VIRTUAL + Beb_ClearHeaderData(send_to_ten_gig == 0 ? 1 : 0); +#endif } return send_to_ten_gig; } @@ -2381,6 +2396,7 @@ void *start_timer(void *arg) { if (!skipData) { uint64_t frameNr = 0; getNextFrameNumber(&frameNr); + int iRxEntry = 0; // loop over number of frames for (int iframes = 0; iframes != numFrames; ++iframes) { @@ -2471,17 +2487,16 @@ void *start_timer(void *arg) { } if (eiger_virtual_left_datastream && i >= startval && i <= endval) { usleep(eiger_virtual_transmission_delay_left); - sendUDPPacket(0, packetData, packetsize); + sendUDPPacket(iRxEntry, 0, packetData, packetsize); LOG(logDEBUG1, ("Sent left packet: %d\n", i)); } if (eiger_virtual_right_datastream && i >= startval && i <= endval) { usleep(eiger_virtual_transmission_delay_right); - sendUDPPacket(1, packetData2, packetsize); + sendUDPPacket(iRxEntry, 1, packetData2, packetsize); LOG(logDEBUG1, ("Sent right packet: %d\n", i)); } } - LOG(logINFO, ("Sent frame: %d[%lld]\n", iframes, - (long long unsigned int)(frameNr + iframes))); + LOG(logINFO, ("Sent frame %d [#%ld] to E%d\n", iframes, frameNr + iframes, iRxEntry)); clock_gettime(CLOCK_REALTIME, &end); int64_t timeNs = ((end.tv_sec - begin.tv_sec) * 1E9 + (end.tv_nsec - begin.tv_nsec)); @@ -2492,6 +2507,10 @@ void *start_timer(void *arg) { usleep((periodNs - timeNs) / 1000); } } + ++iRxEntry; + if (iRxEntry == numUdpDestinations) { + iRxEntry = 0; + } } setNextFrameNumber(frameNr + numFrames); } @@ -2577,30 +2596,13 @@ int softwareTrigger(int block) { } int startReadOut() { - LOG(logINFO, ("Requesting images...\n")); -#ifdef VIRTUAL - return OK; -#else - // RequestImages(); - int ret_val = 0; - dst_requested[0] = 1; - while (dst_requested[on_dst]) { - // waits on data - int beb_num = detid; - if ((ret_val = (!Beb_RequestNImages(beb_num, send_to_ten_gig, on_dst, - nimages_per_request, 0)))) - break; - - dst_requested[on_dst++] = 0; - on_dst %= ndsts_in_use; - } - - if (ret_val) +#ifndef VIRTUAL + if (!Beb_RequestNImages(send_to_ten_gig, nimages_per_request, 0)) { return FAIL; - else - return OK; + } #endif + return OK; } enum runStatus getRunStatus() { diff --git a/slsDetectorServers/eigerDetectorServer/slsDetectorServer_defs.h b/slsDetectorServers/eigerDetectorServer/slsDetectorServer_defs.h index 4cccd8768..9a9d9bdce 100644 --- a/slsDetectorServers/eigerDetectorServer/slsDetectorServer_defs.h +++ b/slsDetectorServers/eigerDetectorServer/slsDetectorServer_defs.h @@ -126,6 +126,8 @@ enum MASTERINDEX { MASTER_HARDWARE, OW_MASTER, OW_SLAVE }; #define UDP_HEADER_MAX_FRAME_VALUE (0xFFFFFFFFFFFF) +#define BIT16_MASK (0xFFFF) + #define DAC_MIN_MV (0) #define DAC_MAX_MV (2048) #define LTC2620_MIN_VAL \ diff --git a/slsDetectorServers/gotthard2DetectorServer/bin/gotthard2DetectorServer_developer b/slsDetectorServers/gotthard2DetectorServer/bin/gotthard2DetectorServer_developer index 0c98256db..f2808a55c 100755 Binary files a/slsDetectorServers/gotthard2DetectorServer/bin/gotthard2DetectorServer_developer and b/slsDetectorServers/gotthard2DetectorServer/bin/gotthard2DetectorServer_developer differ diff --git a/slsDetectorServers/gotthard2DetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/gotthard2DetectorServer/slsDetectorFunctionList.c index 0c09235b4..127dc370f 100644 --- a/slsDetectorServers/gotthard2DetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/gotthard2DetectorServer/slsDetectorFunctionList.c @@ -24,7 +24,7 @@ extern int debugflag; extern int updateFlag; extern int checkModuleFlag; -extern udpStruct udpDetails; +extern udpStruct udpDetails[MAX_UDP_DESTINATION]; extern const enum detectorType myDetectorType; // Global variable from communication_funcs.c @@ -323,7 +323,7 @@ u_int32_t getDetectorIP() { #ifdef VIRTUAL return 0; #endif - char temp[50] = ""; + char temp[INET_ADDRSTRLEN] = ""; u_int32_t res = 0; // execute and get address char output[255]; @@ -417,6 +417,7 @@ void setupDetector() { memset(adcConfiguration, 0, sizeof(adcConfiguration)); #ifdef VIRTUAL sharedMemory_setStatus(IDLE); + setupUDPCommParameters(); #endif // pll defines @@ -1728,30 +1729,30 @@ void calcChecksum(udp_header *udp) { int configureMAC() { - uint32_t srcip = udpDetails.srcip; - uint32_t srcip2 = udpDetails.srcip2; - uint32_t dstip = udpDetails.dstip; - uint32_t dstip2 = udpDetails.dstip2; - uint64_t srcmac = udpDetails.srcmac; - uint64_t srcmac2 = udpDetails.srcmac2; - uint64_t dstmac = udpDetails.dstmac; - uint64_t dstmac2 = udpDetails.dstmac2; - int srcport = udpDetails.srcport; - int srcport2 = udpDetails.srcport2; - int dstport = udpDetails.dstport; - int dstport2 = udpDetails.dstport2; + uint32_t srcip = udpDetails[0].srcip; + uint32_t srcip2 = udpDetails[0].srcip2; + uint32_t dstip = udpDetails[0].dstip; + uint32_t dstip2 = udpDetails[0].dstip2; + uint64_t srcmac = udpDetails[0].srcmac; + uint64_t srcmac2 = udpDetails[0].srcmac2; + uint64_t dstmac = udpDetails[0].dstmac; + uint64_t dstmac2 = udpDetails[0].dstmac2; + int srcport = udpDetails[0].srcport; + int srcport2 = udpDetails[0].srcport2; + int dstport = udpDetails[0].dstport; + int dstport2 = udpDetails[0].dstport2; LOG(logINFOBLUE, ("Configuring MAC\n")); - char src_mac[50], src_ip[INET_ADDRSTRLEN], dst_mac[50], - dst_ip[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac, 50, srcmac); - getMacAddressinString(dst_mac, 50, dstmac); + char src_mac[MAC_ADDRESS_SIZE], src_ip[INET_ADDRSTRLEN], + dst_mac[MAC_ADDRESS_SIZE], dst_ip[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, srcmac); + getMacAddressinString(dst_mac, MAC_ADDRESS_SIZE, dstmac); getIpAddressinString(src_ip, srcip); getIpAddressinString(dst_ip, dstip); - char src_mac2[50], src_ip2[INET_ADDRSTRLEN], dst_mac2[50], - dst_ip2[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac2, 50, srcmac2); - getMacAddressinString(dst_mac2, 50, dstmac2); + char src_mac2[MAC_ADDRESS_SIZE], src_ip2[INET_ADDRSTRLEN], + dst_mac2[MAC_ADDRESS_SIZE], dst_ip2[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac2, MAC_ADDRESS_SIZE, srcmac2); + getMacAddressinString(dst_mac2, MAC_ADDRESS_SIZE, dstmac2); getIpAddressinString(src_ip2, srcip2); getIpAddressinString(dst_ip2, dstip2); @@ -1786,11 +1787,11 @@ int configureMAC() { src_ip2, src_mac2, srcport2, dst_ip2, dst_mac2, dstport2)); #ifdef VIRTUAL - if (setUDPDestinationDetails(0, dst_ip, dstport) == FAIL) { + if (setUDPDestinationDetails(0, 0, dst_ip, dstport) == FAIL) { LOG(logERROR, ("could not set udp destination IP and port\n")); return FAIL; } - if (i10gbe && setUDPDestinationDetails(1, dst_ip2, dstport2) == FAIL) { + if (i10gbe && setUDPDestinationDetails(0, 1, dst_ip2, dstport2) == FAIL) { LOG(logERROR, ("could not set udp destination IP and port for " "interface 2\n")); return FAIL; @@ -2915,7 +2916,7 @@ void *start_timer(void *arg) { memcpy(packetData + sizeof(sls_detector_header), imageData, datasize); // send 1 packet = 1 frame - sendUDPPacket(0, packetData, packetsize); + sendUDPPacket(0, 0, packetData, packetsize); // second interface (veto) char packetData2[vetopacketsize]; @@ -2929,7 +2930,7 @@ void *start_timer(void *arg) { memcpy(packetData2 + sizeof(veto_header), vetoData, vetodatasize); // send 1 packet = 1 frame - sendUDPPacket(1, packetData2, vetopacketsize); + sendUDPPacket(0, 1, packetData2, vetopacketsize); } LOG(logINFO, ("Sent frame %s: %d (bursts/ triggers: %d) [%lld]\n", (i10gbe ? "(+veto)" : ""), frameNr, repeatNr, diff --git a/slsDetectorServers/gotthardDetectorServer/bin/gotthardDetectorServer_developer b/slsDetectorServers/gotthardDetectorServer/bin/gotthardDetectorServer_developer index 877ac3ac4..4d6b04553 100755 Binary files a/slsDetectorServers/gotthardDetectorServer/bin/gotthardDetectorServer_developer and b/slsDetectorServers/gotthardDetectorServer/bin/gotthardDetectorServer_developer differ diff --git a/slsDetectorServers/gotthardDetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/gotthardDetectorServer/slsDetectorFunctionList.c index 1f7e5104d..895042dd6 100644 --- a/slsDetectorServers/gotthardDetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/gotthardDetectorServer/slsDetectorFunctionList.c @@ -21,7 +21,7 @@ // Global variable from slsDetectorServer_funcs extern int debugflag; extern int updateFlag; -extern udpStruct udpDetails; +extern udpStruct udpDetails[MAX_UDP_DESTINATION]; extern const enum detectorType myDetectorType; // Variables that will be exported @@ -315,7 +315,7 @@ u_int32_t getDetectorIP() { #ifdef VIRTUAL return 0; #endif - char temp[50] = ""; + char temp[INET_ADDRSTRLEN] = ""; u_int32_t res = 0; // execute and get address char output[255]; @@ -376,6 +376,7 @@ void setupDetector() { #ifdef VIRTUAL sharedMemory_setStatus(IDLE); + setupUDPCommParameters(); #endif // Initialization @@ -1331,18 +1332,18 @@ void calcChecksum(mac_conf *mac, int sourceip, int destip) { } int configureMAC() { - uint32_t srcip = udpDetails.srcip; - uint32_t dstip = udpDetails.dstip; - uint64_t srcmac = udpDetails.srcmac; - uint64_t dstmac = udpDetails.dstmac; - int srcport = udpDetails.srcport; - int dstport = udpDetails.dstport; + uint32_t srcip = udpDetails[0].srcip; + uint32_t dstip = udpDetails[0].dstip; + uint64_t srcmac = udpDetails[0].srcmac; + uint64_t dstmac = udpDetails[0].dstmac; + int srcport = udpDetails[0].srcport; + int dstport = udpDetails[0].dstport; LOG(logINFOBLUE, ("Configuring MAC\n")); - char src_mac[50], src_ip[INET_ADDRSTRLEN], dst_mac[50], - dst_ip[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac, 50, srcmac); - getMacAddressinString(dst_mac, 50, dstmac); + char src_mac[MAC_ADDRESS_SIZE], src_ip[INET_ADDRSTRLEN], + dst_mac[MAC_ADDRESS_SIZE], dst_ip[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, srcmac); + getMacAddressinString(dst_mac, MAC_ADDRESS_SIZE, dstmac); getIpAddressinString(src_ip, srcip); getIpAddressinString(dst_ip, dstip); @@ -1355,7 +1356,7 @@ int configureMAC() { src_ip, src_mac, srcport, dst_ip, dst_mac, dstport)); #ifdef VIRTUAL - if (setUDPDestinationDetails(0, dst_ip, dstport) == FAIL) { + if (setUDPDestinationDetails(0, 0, dst_ip, dstport) == FAIL) { LOG(logERROR, ("could not set udp 1G destination IP and port\n")); return FAIL; } @@ -1641,7 +1642,7 @@ void *start_timer(void *arg) { memcpy(packetData + 4, imageData + srcOffset, dataSize); srcOffset += dataSize; - sendUDPPacket(0, packetData, packetSize); + sendUDPPacket(0, 0, packetData, packetSize); } LOG(logINFO, ("Sent frame: %d [%d]\n", frameNr, virtual_currentFrameNumber)); diff --git a/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_developer b/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_developer index 1c9a481a7..b3a8e42d9 100755 Binary files a/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_developer and b/slsDetectorServers/jungfrauDetectorServer/bin/jungfrauDetectorServer_developer differ diff --git a/slsDetectorServers/jungfrauDetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/jungfrauDetectorServer/slsDetectorFunctionList.c index 09c4647f9..07b33448d 100644 --- a/slsDetectorServers/jungfrauDetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/jungfrauDetectorServer/slsDetectorFunctionList.c @@ -23,7 +23,8 @@ // Global variable from slsDetectorServer_funcs extern int debugflag; extern int updateFlag; -extern udpStruct udpDetails; +extern udpStruct udpDetails[MAX_UDP_DESTINATION]; +extern int numUdpDestinations; extern const enum detectorType myDetectorType; // Global variable from communication_funcs.c @@ -51,6 +52,9 @@ int detPos[4] = {}; int chipVersion = 10; // (1.0) int chipConfigured = 0; +// until firmware is done +int temp_partialReadout = 512; + int isInitCheckDone() { return initCheckDone; } int getInitResult(char **mess) { @@ -333,7 +337,7 @@ u_int32_t getDetectorIP() { #ifdef VIRTUAL return 0; #endif - char temp[50] = ""; + char temp[INET_ADDRSTRLEN] = ""; u_int32_t res = 0; // execute and get address char output[255]; @@ -393,6 +397,7 @@ void setupDetector() { chipConfigured = 0; #ifdef VIRTUAL sharedMemory_setStatus(IDLE); + setupUDPCommParameters(); #endif // get chip version @@ -1326,6 +1331,34 @@ int getNumberofUDPInterfaces() { return ((bus_r(CONFIG_REG) & CONFIG_OPRTN_MDE_2_X_10GbE_MSK) ? 2 : 1); } +int getNumberofDestinations(int *retval) { + *retval = (((bus_r(CONTROL_REG) & CONTROL_RX_ADDTNL_ENDPTS_NUM_MSK) >> + CONTROL_RX_ADDTNL_ENDPTS_NUM_OFST) + + 1); + return OK; +} + +int setNumberofDestinations(int value) { + LOG(logINFO, ("Setting number of entries to %d\n", value)); + --value; + bus_w(CONTROL_REG, bus_r(CONTROL_REG) & ~CONTROL_RX_ADDTNL_ENDPTS_NUM_MSK); + bus_w(CONTROL_REG, bus_r(CONTROL_REG) | ((value << CONTROL_RX_ADDTNL_ENDPTS_NUM_OFST) & CONTROL_RX_ADDTNL_ENDPTS_NUM_MSK)); + return OK; +} + +int getFirstUDPDestination() { + return ((bus_r(CONTROL_REG) & CONTROL_RX_ENDPTS_START_MSK) >> + CONTROL_RX_ENDPTS_START_OFST); +} + +void setFirstUDPDestination(int value) { + LOG(logINFO, ("Setting first entry to %d\n", value)); + bus_w(CONTROL_REG, bus_r(CONTROL_REG) & ~CONTROL_RX_ENDPTS_START_MSK); + bus_w(CONTROL_REG, + bus_r(CONTROL_REG) | ((value << CONTROL_RX_ENDPTS_START_OFST) & + CONTROL_RX_ENDPTS_START_MSK)); +} + void selectPrimaryInterface(int val) { uint32_t addr = CONFIG_REG; @@ -1348,7 +1381,7 @@ int getPrimaryInterface() { 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); @@ -1386,6 +1419,9 @@ void setupHeader(int iRxEntry, enum interfaceType type, uint32_t destip, // total length is redefined in firmware calcChecksum(udp); + if (iRxEntry < numUdpDestinations) { + LOG(logINFO, ("\tIP checksum : 0x%lx\n\n", udp->ip_checksum)); + } } void calcChecksum(udp_header *udp) { @@ -1416,38 +1452,12 @@ void calcChecksum(udp_header *udp) { sum = (sum & 0xffff) + (sum >> 16); // Fold 32-bit sum to 16 bits long int checksum = sum & 0xffff; checksum += UDP_IP_HEADER_LENGTH_BYTES; - LOG(logINFO, ("\tIP checksum is 0x%lx\n", checksum)); udp->ip_checksum = checksum; } int configureMAC() { - uint32_t srcip = udpDetails.srcip; - uint32_t srcip2 = udpDetails.srcip2; - uint32_t dstip = udpDetails.dstip; - uint32_t dstip2 = udpDetails.dstip2; - uint64_t srcmac = udpDetails.srcmac; - uint64_t srcmac2 = udpDetails.srcmac2; - uint64_t dstmac = udpDetails.dstmac; - uint64_t dstmac2 = udpDetails.dstmac2; - int srcport = udpDetails.srcport; - int srcport2 = udpDetails.srcport2; - int dstport = udpDetails.dstport; - int dstport2 = udpDetails.dstport2; - LOG(logINFOBLUE, ("Configuring MAC\n")); - char src_mac[50], src_ip[INET_ADDRSTRLEN], dst_mac[50], - dst_ip[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac, 50, srcmac); - getMacAddressinString(dst_mac, 50, dstmac); - getIpAddressinString(src_ip, srcip); - getIpAddressinString(dst_ip, dstip); - char src_mac2[50], src_ip2[INET_ADDRSTRLEN], dst_mac2[50], - dst_ip2[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac2, 50, srcmac2); - getMacAddressinString(dst_mac2, 50, dstmac2); - getIpAddressinString(src_ip2, srcip2); - getIpAddressinString(dst_ip2, dstip2); int numInterfaces = getNumberofUDPInterfaces(); int selInterface = getPrimaryInterface(); @@ -1455,65 +1465,94 @@ int configureMAC() { LOG(logINFO, ("\tInterface : %d %s\n\n", selInterface, (selInterface ? "Inner" : "Outer"))); - LOG(logINFO, ("\tOuter %s\n", (numInterfaces == 2) - ? "(Bottom)" - : (selInterface ? "Not Used" : "Used"))); - LOG(logINFO, ("\tSource IP : %s\n" - "\tSource MAC : %s\n" - "\tSource Port : %d\n" - "\tDest IP : %s\n" - "\tDest MAC : %s\n" - "\tDest Port : %d\n", - src_ip, src_mac, srcport, dst_ip, dst_mac, dstport)); + LOG(logINFO, ("Number of entries: %d\n\n", numUdpDestinations)); + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; ++iRxEntry) { + uint32_t srcip = udpDetails[iRxEntry].srcip; + uint32_t srcip2 = udpDetails[iRxEntry].srcip2; + uint32_t dstip = udpDetails[iRxEntry].dstip; + uint32_t dstip2 = udpDetails[iRxEntry].dstip2; + uint64_t srcmac = udpDetails[iRxEntry].srcmac; + uint64_t srcmac2 = udpDetails[iRxEntry].srcmac2; + uint64_t dstmac = udpDetails[iRxEntry].dstmac; + uint64_t dstmac2 = udpDetails[iRxEntry].dstmac2; + int srcport = udpDetails[iRxEntry].srcport; + int srcport2 = udpDetails[iRxEntry].srcport2; + int dstport = udpDetails[iRxEntry].dstport; + int dstport2 = udpDetails[iRxEntry].dstport2; - LOG(logINFO, ("\tInner %s\n", (numInterfaces == 2) - ? "(Top)" - : (selInterface ? "Used" : "Not Used"))); - LOG(logINFO, ("\tSource IP2 : %s\n" - "\tSource MAC2 : %s\n" - "\tSource Port2: %d\n" - "\tDest IP2 : %s\n" - "\tDest MAC2 : %s\n" - "\tDest Port2 : %d\n", - src_ip2, src_mac2, srcport2, dst_ip2, dst_mac2, dstport2)); + char src_mac[MAC_ADDRESS_SIZE], src_ip[INET_ADDRSTRLEN], + dst_mac[MAC_ADDRESS_SIZE], dst_ip[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, srcmac); + getMacAddressinString(dst_mac, MAC_ADDRESS_SIZE, dstmac); + getIpAddressinString(src_ip, srcip); + getIpAddressinString(dst_ip, dstip); + char src_mac2[MAC_ADDRESS_SIZE], src_ip2[INET_ADDRSTRLEN], + dst_mac2[MAC_ADDRESS_SIZE], dst_ip2[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac2, MAC_ADDRESS_SIZE, srcmac2); + getMacAddressinString(dst_mac2, MAC_ADDRESS_SIZE, dstmac2); + getIpAddressinString(src_ip2, srcip2); + getIpAddressinString(dst_ip2, dstip2); + if (iRxEntry < numUdpDestinations) { + LOG(logINFOBLUE, ("\tEntry %d\n", iRxEntry)); + + LOG(logINFO, ("\tOuter %s\n", (numInterfaces == 2) + ? "(Bottom)" + : (selInterface ? "Not Used" : "Used"))); + LOG(logINFO, ("\tSource IP : %s\n" + "\tSource MAC : %s\n" + "\tSource Port : %d\n" + "\tDest IP : %s\n" + "\tDest MAC : %s\n" + "\tDest Port : %d\n\n", + src_ip, src_mac, srcport, dst_ip, dst_mac, dstport)); + + LOG(logINFO, ("\tInner %s\n", (numInterfaces == 2) + ? "(Top)" + : (selInterface ? "Used" : "Not Used"))); + LOG(logINFO, ("\tSource IP2 : %s\n" + "\tSource MAC2 : %s\n" + "\tSource Port2: %d\n" + "\tDest IP2 : %s\n" + "\tDest MAC2 : %s\n" + "\tDest Port2 : %d\n\n", + src_ip2, src_mac2, srcport2, dst_ip2, dst_mac2, dstport2)); + } #ifdef VIRTUAL - if (setUDPDestinationDetails(0, dst_ip, dstport) == FAIL) { - LOG(logERROR, - ("could not set udp destination IP and port for interface 1\n")); - return FAIL; - } - if (numInterfaces == 2 && - setUDPDestinationDetails(1, dst_ip2, dstport2) == FAIL) { - LOG(logERROR, - ("could not set udp destination IP and port for interface 2\n")); - return FAIL; - } - return OK; + if (setUDPDestinationDetails(iRxEntry, 0, dst_ip, dstport) == FAIL) { + LOG(logERROR, ("could not set udp destination IP and port for " + "interface 1 [entry:%d] \n", + iRxEntry)); + return FAIL; + } + if (numInterfaces == 2 && + setUDPDestinationDetails(iRxEntry, 1, dst_ip2, dstport2) == FAIL) { + LOG(logERROR, ("could not set udp destination IP and port for " + "interface 2 [entry:%d]\n", + iRxEntry)); + return FAIL; + } #endif - // default one rxr entry (others not yet implemented in client yet) - int iRxEntry = 0; - - if (numInterfaces == 2) { - // bottom - setupHeader(iRxEntry, OUTER, dstip, dstmac, dstport, srcmac, srcip, - srcport); - // top - setupHeader(iRxEntry, INNER, dstip2, dstmac2, dstport2, srcmac2, srcip2, - srcport2); - } - // single interface - else { - // default - if (selInterface == 0) { + if (numInterfaces == 2) { + // bottom setupHeader(iRxEntry, OUTER, dstip, dstmac, dstport, srcmac, srcip, srcport); - } else { - setupHeader(iRxEntry, INNER, dstip, dstmac, dstport, srcmac, srcip, + // top + setupHeader(iRxEntry, INNER, dstip2, dstmac2, dstport2, srcmac2, srcip2, srcport2); } + // single interface + else { + // default + if (selInterface == 0) { + setupHeader(iRxEntry, OUTER, dstip, dstmac, dstport, srcmac, srcip, + srcport); + } else { + setupHeader(iRxEntry, INNER, dstip, dstmac, dstport, srcmac, srcip, + srcport2); + } + } } - setNumberofUDPInterfaces(numInterfaces); selectPrimaryInterface(selInterface); @@ -1601,6 +1640,10 @@ int setPartialReadout(int value) { if (value < 0 || (value % PARTIAL_READOUT_MULTIPLE != 0)) return FAIL; + // will be replaced when firmware is fixed + temp_partialReadout = value; + return OK; + // regval is numpackets - 1 int regval = (value / PARTIAL_READOUT_MULTIPLE) - 1; uint32_t addr = PARTIAL_READOUT_REG; @@ -1619,10 +1662,14 @@ int setPartialReadout(int value) { } int getPartialReadout() { + + // will be replaced when firmware is fixed + return temp_partialReadout; + int enable = (bus_r(PARTIAL_READOUT_REG) & PARTIAL_READOUT_ENBL_MSK); int regval = ((bus_r(PARTIAL_READOUT_REG) & PARTIAL_READOUT_NUM_ROWS_MSK) >> PARTIAL_READOUT_NUM_ROWS_OFST); - int maxRegval = (MAX_ROWS_PER_READOUT/ PARTIAL_READOUT_MULTIPLE) - 1; + int maxRegval = (MAX_ROWS_PER_READOUT/ PARTIAL_READOUT_MULTIPLE) - 1; if ((regval == maxRegval && enable) || (regval != maxRegval && !enable)) { return -1; } @@ -2296,9 +2343,8 @@ void *start_timer(void *arg) { if (!isControlServer) { return NULL; } - + int firstDest = getFirstUDPDestination(); int transmissionDelayUs = getTransmissionDelayFrame() * 1000; - int numInterfaces = getNumberofUDPInterfaces(); int64_t periodNs = getPeriod(); int numFrames = (getNumFrames() * getNumTriggers() * @@ -2339,6 +2385,7 @@ void *start_timer(void *arg) { { uint64_t frameNr = 0; getNextFrameNumber(&frameNr); + int iRxEntry = firstDest; for (int iframes = 0; iframes != numFrames; ++iframes) { usleep(transmissionDelayUs); @@ -2383,7 +2430,7 @@ void *start_timer(void *arg) { srcOffset += dataSize; if (i >= startval && i <= endval) { - sendUDPPacket(0, packetData, packetsize); + sendUDPPacket(iRxEntry, 0, packetData, packetsize); LOG(logDEBUG1, ("Sent packet: %d [interface 0]\n", i)); } } @@ -2410,12 +2457,12 @@ void *start_timer(void *arg) { srcOffset2 += dataSize; if (i >= startval && i <= endval) { - sendUDPPacket(1, packetData2, packetsize); + sendUDPPacket(iRxEntry, 1, packetData2, packetsize); LOG(logDEBUG1, ("Sent packet: %d [interface 1]\n", pnum)); } } } - LOG(logINFO, ("Sent frame: %d\n", iframes)); + LOG(logINFO, ("Sent frame %d [#%ld] to E%d\n", iframes, frameNr + iframes, iRxEntry)); clock_gettime(CLOCK_REALTIME, &end); int64_t timeNs = ((end.tv_sec - begin.tv_sec) * 1E9 + (end.tv_nsec - begin.tv_nsec)); @@ -2426,6 +2473,10 @@ void *start_timer(void *arg) { usleep((periodNs - timeNs) / 1000); } } + ++iRxEntry; + if (iRxEntry == numUdpDestinations) { + iRxEntry = 0; + } } setNextFrameNumber(frameNr + numFrames); } diff --git a/slsDetectorServers/moenchDetectorServer/bin/moenchDetectorServer_developer b/slsDetectorServers/moenchDetectorServer/bin/moenchDetectorServer_developer index 4739ab6f9..5b8661f09 100755 Binary files a/slsDetectorServers/moenchDetectorServer/bin/moenchDetectorServer_developer and b/slsDetectorServers/moenchDetectorServer/bin/moenchDetectorServer_developer differ diff --git a/slsDetectorServers/moenchDetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/moenchDetectorServer/slsDetectorFunctionList.c index 1b97e243c..bdda08571 100644 --- a/slsDetectorServers/moenchDetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/moenchDetectorServer/slsDetectorFunctionList.c @@ -23,7 +23,7 @@ // Global variable from slsDetectorServer_funcs extern int debugflag; extern int updateFlag; -extern udpStruct udpDetails; +extern udpStruct udpDetails[MAX_UDP_DESTINATION]; extern const enum detectorType myDetectorType; // Global variable from UDPPacketHeaderGenerator @@ -53,10 +53,10 @@ char *digitalData = 0; char volatile *analogDataPtr = 0; char volatile *digitalDataPtr = 0; char udpPacketData[UDP_PACKET_DATA_BYTES + sizeof(sls_detector_header)]; -uint32_t adcEnableMask_1g = 0; +uint32_t adcEnableMask_1g = BIT32_MSK; // 10g readout -uint8_t adcEnableMask_10g = 0; +uint8_t adcEnableMask_10g = 0xFF; int32_t clkPhase[NUM_CLOCKS] = {}; uint32_t clkFrequency[NUM_CLOCKS] = {40, 20, 20, 200}; @@ -389,7 +389,7 @@ uint32_t getDetectorIP() { #ifdef VIRTUAL return 0; #endif - char temp[50] = ""; + char temp[INET_ADDRSTRLEN] = ""; uint32_t res = 0; // execute and get address char output[255]; @@ -480,13 +480,14 @@ void setupDetector() { dacValues[i] = -1; vLimit = DEFAULT_VLIMIT; highvoltage = 0; - adcEnableMask_1g = 0; - adcEnableMask_10g = 0; + adcEnableMask_1g = BIT32_MSK; + adcEnableMask_10g = 0xFF; nSamples = 1; #ifdef VIRTUAL sharedMemory_setStatus(IDLE); initializePatternWord(); #endif + setupUDPCommParameters(); ALTERA_PLL_ResetPLLAndReconfiguration(); resetCore(); @@ -1181,18 +1182,18 @@ void calcChecksum(udp_header *udp) { } int configureMAC() { - uint32_t srcip = udpDetails.srcip; - uint32_t dstip = udpDetails.dstip; - uint64_t srcmac = udpDetails.srcmac; - uint64_t dstmac = udpDetails.dstmac; - int srcport = udpDetails.srcport; - int dstport = udpDetails.dstport; + uint32_t srcip = udpDetails[0].srcip; + uint32_t dstip = udpDetails[0].dstip; + uint64_t srcmac = udpDetails[0].srcmac; + uint64_t dstmac = udpDetails[0].dstmac; + int srcport = udpDetails[0].srcport; + int dstport = udpDetails[0].dstport; LOG(logINFOBLUE, ("Configuring MAC\n")); - char src_mac[50], src_ip[INET_ADDRSTRLEN], dst_mac[50], - dst_ip[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac, 50, srcmac); - getMacAddressinString(dst_mac, 50, dstmac); + char src_mac[MAC_ADDRESS_SIZE], src_ip[INET_ADDRSTRLEN], + dst_mac[MAC_ADDRESS_SIZE], dst_ip[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, srcmac); + getMacAddressinString(dst_mac, MAC_ADDRESS_SIZE, dstmac); getIpAddressinString(src_ip, srcip); getIpAddressinString(dst_ip, dstip); @@ -1209,7 +1210,7 @@ int configureMAC() { LOG(logINFOBLUE, ("\t1G MAC\n")); if (updateDatabytesandAllocateRAM() == FAIL) return -1; - if (setUDPDestinationDetails(0, dst_ip, dstport) == FAIL) { + if (setUDPDestinationDetails(0, 0, dst_ip, dstport) == FAIL) { LOG(logERROR, ("could not set udp 1G destination IP and port\n")); return FAIL; } @@ -1687,7 +1688,7 @@ void *start_timer(void *arg) { imageData + srcOffset, dataSize); srcOffset += dataSize; - sendUDPPacket(0, packetData, packetSize); + sendUDPPacket(0, 0, packetData, packetSize); } LOG(logINFO, ("Sent frame: %d [%lld]\n", frameNr, (long long unsigned int)virtual_currentFrameNumber)); @@ -1806,10 +1807,10 @@ void readandSendUDPFrames(int *ret, char *mess) { LOG(logDEBUG1, ("Reading from 1G UDP\n")); // validate udp socket - if (getUdPSocketDescriptor(0) <= 0) { + if (getUdPSocketDescriptor(0, 0) <= 0) { *ret = FAIL; sprintf(mess, "UDP Socket not created. sockfd:%d\n", - getUdPSocketDescriptor(0)); + getUdPSocketDescriptor(0, 0)); LOG(logERROR, (mess)); return; } @@ -1818,7 +1819,7 @@ void readandSendUDPFrames(int *ret, char *mess) { while (readFrameFromFifo() == OK) { int bytesToSend = 0, n = 0; while ((bytesToSend = fillUDPPacket(udpPacketData))) { - n += sendUDPPacket(0, udpPacketData, bytesToSend); + n += sendUDPPacket(0, 0, udpPacketData, bytesToSend); } if (n >= dataBytes) { LOG(logINFO, (" Frame %lld sent (%d packets, %d databytes, n:%d " diff --git a/slsDetectorServers/mythen3DetectorServer/bin/mythen3DetectorServer_developer b/slsDetectorServers/mythen3DetectorServer/bin/mythen3DetectorServer_developer index 4422a87f5..f2ad66776 100755 Binary files a/slsDetectorServers/mythen3DetectorServer/bin/mythen3DetectorServer_developer and b/slsDetectorServers/mythen3DetectorServer/bin/mythen3DetectorServer_developer differ diff --git a/slsDetectorServers/mythen3DetectorServer/slsDetectorFunctionList.c b/slsDetectorServers/mythen3DetectorServer/slsDetectorFunctionList.c index f0ae19d82..9180efeef 100644 --- a/slsDetectorServers/mythen3DetectorServer/slsDetectorFunctionList.c +++ b/slsDetectorServers/mythen3DetectorServer/slsDetectorFunctionList.c @@ -25,7 +25,7 @@ extern int debugflag; extern int updateFlag; extern int checkModuleFlag; -extern udpStruct udpDetails; +extern udpStruct udpDetails[MAX_UDP_DESTINATION]; extern const enum detectorType myDetectorType; // Global variable from communication_funcs.c @@ -323,7 +323,7 @@ u_int32_t getDetectorIP() { #ifdef VIRTUAL return 0; #endif - char temp[50] = ""; + char temp[INET_ADDRSTRLEN] = ""; u_int32_t res = 0; // execute and get address char output[255]; @@ -429,6 +429,7 @@ void setupDetector() { } #ifdef VIRTUAL sharedMemory_setStatus(IDLE); + setupUDPCommParameters(); #endif // pll defines @@ -1722,18 +1723,18 @@ int getExtSignal(int signalIndex) { int configureMAC() { - uint32_t srcip = udpDetails.srcip; - uint32_t dstip = udpDetails.dstip; - uint64_t srcmac = udpDetails.srcmac; - uint64_t dstmac = udpDetails.dstmac; - int srcport = udpDetails.srcport; - int dstport = udpDetails.dstport; + uint32_t srcip = udpDetails[0].srcip; + uint32_t dstip = udpDetails[0].dstip; + uint64_t srcmac = udpDetails[0].srcmac; + uint64_t dstmac = udpDetails[0].dstmac; + int srcport = udpDetails[0].srcport; + int dstport = udpDetails[0].dstport; LOG(logINFOBLUE, ("Configuring MAC\n")); - char src_mac[50], src_ip[INET_ADDRSTRLEN], dst_mac[50], - dst_ip[INET_ADDRSTRLEN]; - getMacAddressinString(src_mac, 50, srcmac); - getMacAddressinString(dst_mac, 50, dstmac); + char src_mac[MAC_ADDRESS_SIZE], src_ip[INET_ADDRSTRLEN], + dst_mac[MAC_ADDRESS_SIZE], dst_ip[INET_ADDRSTRLEN]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, srcmac); + getMacAddressinString(dst_mac, MAC_ADDRESS_SIZE, dstmac); getIpAddressinString(src_ip, srcip); getIpAddressinString(dst_ip, dstip); @@ -1746,7 +1747,7 @@ int configureMAC() { src_ip, src_mac, srcport, dst_ip, dst_mac, dstport)); #ifdef VIRTUAL - if (setUDPDestinationDetails(0, dst_ip, dstport) == FAIL) { + if (setUDPDestinationDetails(0, 0, dst_ip, dstport) == FAIL) { LOG(logERROR, ("could not set udp destination IP and port\n")); return FAIL; } @@ -2290,7 +2291,7 @@ void *start_timer(void *arg) { imageData + srcOffset, dataSize); srcOffset += dataSize; - sendUDPPacket(0, packetData, packetSize); + sendUDPPacket(0, 0, packetData, packetSize); } LOG(logINFO, ("Sent frame: %d [%lld]\n", frameNr, (long long unsigned int)virtual_currentFrameNumber)); diff --git a/slsDetectorServers/slsDetectorServer/include/communication_funcs_UDP.h b/slsDetectorServers/slsDetectorServer/include/communication_funcs_UDP.h index 01d9226eb..3ba9f251d 100644 --- a/slsDetectorServers/slsDetectorServer/include/communication_funcs_UDP.h +++ b/slsDetectorServers/slsDetectorServer/include/communication_funcs_UDP.h @@ -1,35 +1,15 @@ #pragma once -/** - * Get UDP socket desicriptor - * @param udp port index - */ -int getUdPSocketDescriptor(int index); -/** - * Set udp destination - * @param index udp port index - * @param ip udp destination ip - * @param port udp destination port - */ -int setUDPDestinationDetails(int index, const char *ip, +void setupUDPCommParameters(); + +int getUdPSocketDescriptor(int iRxEntry, int index); + +void setNumberOfUDPDestinations(int value); + +int setUDPDestinationDetails(int iRxEntry, int index, const char *ip, unsigned short int port); - -/** - * Create udp socket - * @param index udp port index - */ int createUDPSocket(int index); -/** - * Writes to socket file descriptor - * @param index udp port index - * @param buf pointer to memory to write - * @param length length of buffer to write to socket - */ -int sendUDPPacket(int index, const char *buf, int length); +int sendUDPPacket(int iRxEntry, int index, const char *buf, int length); -/** - * Close udp socket - * @index udp port index - */ void closeUDPSocket(int index); diff --git a/slsDetectorServers/slsDetectorServer/include/slsDetectorFunctionList.h b/slsDetectorServers/slsDetectorServer/include/slsDetectorFunctionList.h index e793fbf35..ced82bf64 100644 --- a/slsDetectorServers/slsDetectorServer/include/slsDetectorFunctionList.h +++ b/slsDetectorServers/slsDetectorServer/include/slsDetectorFunctionList.h @@ -52,6 +52,7 @@ typedef struct udpStruct_s { uint32_t dstip; uint32_t dstip2; } udpStruct; +#define MAC_ADDRESS_SIZE 18 // basic tests int isInitCheckDone(); @@ -385,7 +386,14 @@ void calcChecksum(mac_conf *mac, int sourceip, int destip); void setNumberofUDPInterfaces(int val); int getNumberofUDPInterfaces(); #endif + +#if defined(JUNGFRAUD) || defined(EIGERD) +int getNumberofDestinations(int *retval); +int setNumberofDestinations(int value); +#endif #ifdef JUNGFRAUD +int getFirstUDPDestination(); +void setFirstUDPDestination(int value); void selectPrimaryInterface(int val); int getPrimaryInterface(); void setupHeader(int iRxEntry, enum interfaceType type, uint32_t destip, diff --git a/slsDetectorServers/slsDetectorServer/include/slsDetectorServer_funcs.h b/slsDetectorServers/slsDetectorServer/include/slsDetectorServer_funcs.h index ea1c86554..6bf9ef13e 100644 --- a/slsDetectorServers/slsDetectorServer/include/slsDetectorServer_funcs.h +++ b/slsDetectorServers/slsDetectorServer/include/slsDetectorServer_funcs.h @@ -268,4 +268,10 @@ int get_adc_pipeline(int); int set_dbit_pipeline(int); int get_dbit_pipeline(int); int get_module_id(int); -int set_module_id(int); \ No newline at end of file +int set_module_id(int); +int get_dest_udp_list(int); +int set_dest_udp_list(int); +int get_num_dest_list(int); +int set_num_dest_list(int); +int get_udp_first_dest(int); +int set_udp_first_dest(int); \ No newline at end of file diff --git a/slsDetectorServers/slsDetectorServer/src/communication_funcs_UDP.c b/slsDetectorServers/slsDetectorServer/src/communication_funcs_UDP.c index f001f3629..95a0fc641 100644 --- a/slsDetectorServers/slsDetectorServer/src/communication_funcs_UDP.c +++ b/slsDetectorServers/slsDetectorServer/src/communication_funcs_UDP.c @@ -13,25 +13,38 @@ #include #include -int udpSockfd[2] = {-1, -1}; -struct addrinfo *udpServerAddrInfo[2] = {0, 0}; -unsigned short int udpDestinationPort[2] = {0, 0}; -char udpDestinationIp[2][INET_ADDRSTRLEN] = {"", ""}; +int udpSockfd[MAX_UDP_DESTINATION][2] = {}; +struct addrinfo *udpServerAddrInfo[MAX_UDP_DESTINATION][2] = {}; +unsigned short int udpDestinationPort[MAX_UDP_DESTINATION][2] = {}; +char udpDestinationIp[MAX_UDP_DESTINATION][2][INET_ADDRSTRLEN] = {}; +extern int numUdpDestinations; -// DEFAULT_TX_UDP_PORT;// src port -int getUdPSocketDescriptor(int index) { return udpSockfd[index]; } +void setupUDPCommParameters() { + for (int i = 0; i != MAX_UDP_DESTINATION; i++) { + udpSockfd[i][0] = -1; + udpSockfd[i][1] = -1; + } + memset(udpServerAddrInfo, 0, sizeof(udpServerAddrInfo)); + memset(udpDestinationIp, 0, sizeof(udpDestinationIp)); +} -int setUDPDestinationDetails(int index, const char *ip, +int getUdPSocketDescriptor(int iRxEntry, int index) { return udpSockfd[iRxEntry][index]; } + + +int setUDPDestinationDetails(int iRxEntry, int index, const char *ip, unsigned short int port) { - udpDestinationPort[index] = port; + LOG(logDEBUG1, + ("Setting udp destination details for socket %d [iRxEntry:%d]\n", index, + iRxEntry)); + udpDestinationPort[iRxEntry][index] = port; size_t len = strlen(ip); - memset(udpDestinationIp[index], 0, INET_ADDRSTRLEN); - strncpy(udpDestinationIp[index], ip, + memset(udpDestinationIp[iRxEntry][index], 0, INET_ADDRSTRLEN); + strncpy(udpDestinationIp[iRxEntry][index], ip, len > INET_ADDRSTRLEN ? INET_ADDRSTRLEN : len); - if (udpServerAddrInfo[index]) { - freeaddrinfo(udpServerAddrInfo[index]); - udpServerAddrInfo[index] = 0; + if (udpServerAddrInfo[iRxEntry][index]) { + freeaddrinfo(udpServerAddrInfo[iRxEntry][index]); + udpServerAddrInfo[iRxEntry][index] = 0; } // convert ip to internet address @@ -43,21 +56,21 @@ int setUDPDestinationDetails(int index, const char *ip, hints.ai_protocol = 0; char sport[100]; memset(sport, 0, 100); - sprintf(sport, "%d", udpDestinationPort[index]); - int err = getaddrinfo(udpDestinationIp[index], sport, &hints, - &udpServerAddrInfo[index]); + sprintf(sport, "%d", udpDestinationPort[iRxEntry][index]); + int err = getaddrinfo(udpDestinationIp[iRxEntry][index], sport, &hints, + &udpServerAddrInfo[iRxEntry][index]); if (err != 0) { - LOG(logERROR, ("Failed to resolve remote socket address %s at port %d. " + LOG(logERROR, ("Failed to resolve remote socket address %s at port %d [entry:%d]. " "(Error code:%d, %s)\n", - udpDestinationIp[index], udpDestinationPort[index], err, + udpDestinationIp[iRxEntry][index], udpDestinationPort[iRxEntry][index], iRxEntry, err, gai_strerror(err))); return FAIL; } - if (udpServerAddrInfo[index] == NULL) { - LOG(logERROR, ("Failed to resolve remote socket address %s at port %d " + if (udpServerAddrInfo[iRxEntry][index] == NULL) { + LOG(logERROR, ("Failed to resolve remote socket address %s at port %d [entry:%d]." "(getaddrinfo returned NULL)\n", - udpDestinationIp[index], udpDestinationPort[index])); - udpServerAddrInfo[index] = 0; + udpDestinationIp[iRxEntry][index], udpDestinationPort[iRxEntry][index], iRxEntry)); + udpServerAddrInfo[iRxEntry][index] = 0; return FAIL; } @@ -65,49 +78,54 @@ int setUDPDestinationDetails(int index, const char *ip, } int createUDPSocket(int index) { - LOG(logDEBUG2, ("Creating UDP Socket %d\n", index)); - if (!strlen(udpDestinationIp[index])) { - LOG(logERROR, ("No destination UDP ip specified.\n")); - return FAIL; - } + + for (int iRxEntry = 0; iRxEntry != numUdpDestinations; ++iRxEntry) { - if (udpSockfd[index] != -1) { - LOG(logERROR, ("Strange that Udp socket was still open. Closing it to " - "create a new one\n")); - close(udpSockfd[index]); - udpSockfd[index] = -1; - } + LOG(logDEBUG2, ("Creating UDP Socket %d [entry:%d]\n", index, iRxEntry)); + if (!strlen(udpDestinationIp[iRxEntry][index])) { + LOG(logERROR, ("No destination UDP ip specified for socket %d [entry:%d].\n", index, iRxEntry)); + return FAIL; + } - // Creating socket file descriptor - udpSockfd[index] = socket(udpServerAddrInfo[index]->ai_family, - udpServerAddrInfo[index]->ai_socktype, - udpServerAddrInfo[index]->ai_protocol); - if (udpSockfd[index] == -1) { - LOG(logERROR, ("UDP socket at port %d failed. (Error code:%d, %s)\n", - udpDestinationPort[index], errno, gai_strerror(errno))); - return FAIL; - } - LOG(logINFO, ("Udp client socket created for server (port %d, ip:%s)\n", - udpDestinationPort[index], udpDestinationIp[index])); + if (udpSockfd[iRxEntry][index] != -1) { + LOG(logERROR, ("Strange that Udp socket was still open [socket:%d, entry:%d]. Closing it to " + "create a new one.\n", index, iRxEntry)); + close(udpSockfd[iRxEntry][index]); + udpSockfd[iRxEntry][index] = -1; + } - // Using connect expects that the receiver (udp server) exists to listen to - // these packets connecting allows to use "send/write" instead of "sendto", - // avoiding checking for server address for each packet using write without - // a connect will end in segv - LOG(logINFO, ("Udp client socket connected\n", udpDestinationPort[index], - udpDestinationIp[index])); + // Creating socket file descriptor + udpSockfd[iRxEntry][index] = socket(udpServerAddrInfo[iRxEntry][index]->ai_family, + udpServerAddrInfo[iRxEntry][index]->ai_socktype, + udpServerAddrInfo[iRxEntry][index]->ai_protocol); + if (udpSockfd[iRxEntry][index] == -1) { + LOG(logERROR, ("UDP socket at port %d failed [entry:%d]. (Error code:%d, %s)\n", + udpDestinationPort[iRxEntry][index], iRxEntry, errno, gai_strerror(errno))); + return FAIL; + } + LOG(logINFO, ("Udp client socket created for server (entry:%d, port %d, ip:%s)\n", + iRxEntry, udpDestinationPort[iRxEntry][index], udpDestinationIp[iRxEntry][index])); + + // Using connect expects that the receiver (udp server) exists to listen to + // these packets connecting allows to use "send/write" instead of "sendto", + // avoiding checking for server address for each packet using write without + // a connect will end in segv + LOG(logINFO, ("Udp client socket connected [%d, %d, %s]\n", iRxEntry, udpDestinationPort[iRxEntry][index], + udpDestinationIp[iRxEntry][index])); + + } return OK; } -int sendUDPPacket(int index, const char *buf, int length) { - int n = sendto(udpSockfd[index], buf, length, 0, - udpServerAddrInfo[index]->ai_addr, - udpServerAddrInfo[index]->ai_addrlen); +int sendUDPPacket(int iRxEntry, int index, const char *buf, int length) { + int n = sendto(udpSockfd[iRxEntry][index], buf, length, 0, + udpServerAddrInfo[iRxEntry][index]->ai_addr, + udpServerAddrInfo[iRxEntry][index]->ai_addrlen); // udp sends atomically, no need to handle partial data if (n == -1) { LOG(logERROR, - ("Could not send udp packet for socket %d. (Error code:%d, %s)\n", - index, n, errno, gai_strerror(errno))); + ("Could not send udp packet for socket %d [entry:%d]. (Error code:%d, %s)\n", + index, iRxEntry, errno, gai_strerror(errno))); } else { LOG(logDEBUG2, ("%d bytes sent\n", n)); } @@ -115,9 +133,11 @@ int sendUDPPacket(int index, const char *buf, int length) { } void closeUDPSocket(int index) { - if (udpSockfd[index] != -1) { - LOG(logINFO, ("Udp client socket closed\n")); - close(udpSockfd[index]); - udpSockfd[index] = -1; + for (int iRxEntry = 0; iRxEntry != numUdpDestinations; ++iRxEntry) { + if (udpSockfd[iRxEntry][index] != -1) { + LOG(logINFO, ("Udp client socket closed\n")); + close(udpSockfd[iRxEntry][index]); + udpSockfd[iRxEntry][index] = -1; + } } } diff --git a/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c b/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c index 9e2473a5b..54baf5a59 100644 --- a/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c +++ b/slsDetectorServers/slsDetectorServer/src/slsDetectorServer_funcs.c @@ -49,7 +49,11 @@ int sockfd = 0; int debugflag = 0; int updateFlag = 0; int checkModuleFlag = 1; -udpStruct udpDetails = {32410, 32411, 50001, 50002, 0, 0, 0, 0, 0, 0, 0, 0}; + +udpStruct udpDetails[MAX_UDP_DESTINATION]; +int numUdpDestinations = 1; +int firstUDPDestination = 0; + int configured = FAIL; char configureMessage[MAX_STR_LENGTH] = "udp parameters not configured yet"; int maxydet = -1; @@ -79,6 +83,13 @@ void init_detector() { #ifdef VIRTUAL LOG(logINFO, ("This is a VIRTUAL detector\n")); #endif + memset(udpDetails, 0, sizeof(udpDetails)); + udpDetails[0].srcport = DEFAULT_UDP_SRC_PORTNO; + udpDetails[0].dstport = DEFAULT_UDP_DST_PORTNO; +#ifdef EIGERD + udpDetails[0].dstport2 = DEFAULT_UDP_DST_PORTNO + 1; +#endif + if (isControlServer) { basictests(); initControlServer(); @@ -394,6 +405,12 @@ void function_table() { flist[F_GET_DBIT_PIPELINE] = &get_dbit_pipeline; flist[F_GET_MODULE_ID] = &get_module_id; flist[F_SET_MODULE_ID] = &set_module_id; + flist[F_GET_DEST_UDP_LIST] = &get_dest_udp_list; + flist[F_SET_DEST_UDP_LIST] = &set_dest_udp_list; + flist[F_GET_NUM_DEST_UDP] = &get_num_dest_list; + flist[F_SET_NUM_DEST_UDP] = &set_num_dest_list; + flist[F_GET_UDP_FIRST_DEST] = &get_udp_first_dest; + flist[F_SET_UDP_FIRST_DEST] = &set_udp_first_dest; // check if (NUM_DET_FUNCTIONS >= RECEIVER_ENUM_START) { @@ -1733,18 +1750,18 @@ int acquire(int blocking, int file_des) { #endif #ifdef EIGERD // check for hardware mac and hardware ip - if (udpDetails.srcmac != getDetectorMAC()) { + if (udpDetails[0].srcmac != getDetectorMAC()) { ret = FAIL; uint64_t sourcemac = getDetectorMAC(); - char src_mac[50]; - getMacAddressinString(src_mac, 50, sourcemac); + char src_mac[MAC_ADDRESS_SIZE]; + getMacAddressinString(src_mac, MAC_ADDRESS_SIZE, sourcemac); sprintf(mess, "Invalid udp source mac address for this detector. Must be " "same as hardware detector mac address %s\n", src_mac); LOG(logERROR, (mess)); } else if (!enableTenGigabitEthernet(GET_FLAG) && - (udpDetails.srcip != getDetectorIP())) { + (udpDetails[0].srcip != getDetectorIP())) { ret = FAIL; uint32_t sourceip = getDetectorIP(); char src_ip[INET_ADDRSTRLEN]; @@ -2911,14 +2928,20 @@ int enable_ten_giga(int file_des) { enableTenGigabitEthernet(arg); #ifdef EIGERD uint64_t hardwaremac = getDetectorMAC(); - if (udpDetails.srcmac != hardwaremac) { + if (udpDetails[0].srcmac != hardwaremac) { LOG(logINFOBLUE, ("Updating udp source mac\n")); - udpDetails.srcmac = hardwaremac; + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcmac = hardwaremac; + } } uint32_t hardwareip = getDetectorIP(); - if (arg == 0 && udpDetails.srcip != hardwareip) { + if (arg == 0 && udpDetails[0].srcip != hardwareip) { LOG(logINFOBLUE, ("Updating udp source ip\n")); - udpDetails.srcip = hardwareip; + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcip = hardwareip; + } } #endif configure_mac(); @@ -4842,34 +4865,42 @@ void calculate_and_set_position() { // to redo the detector mac (depends on positions) else { // create detector mac from x and y - if (udpDetails.srcmac == 0) { - char dmac[50]; - memset(dmac, 0, 50); + if (udpDetails[0].srcmac == 0) { + char dmac[MAC_ADDRESS_SIZE]; + memset(dmac, 0, MAC_ADDRESS_SIZE); sprintf(dmac, "aa:bb:cc:dd:%02x:%02x", pos[0] & 0xFF, pos[1] & 0xFF); LOG(logINFO, ("Udp source mac address created: %s\n", dmac)); unsigned char a[6]; sscanf(dmac, "%hhx:%hhx:%hhx:%hhx:%hhx:%hhx", &a[0], &a[1], &a[2], &a[3], &a[4], &a[5]); - udpDetails.srcmac = 0; + udpDetails[0].srcmac = 0; for (int i = 0; i < 6; ++i) { - udpDetails.srcmac = (udpDetails.srcmac << 8) + a[i]; + udpDetails[0].srcmac = (udpDetails[0].srcmac << 8) + a[i]; + } + for (int iRxEntry = 1; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcmac = udpDetails[0].srcmac; } } #if defined(JUNGFRAUD) || defined(GOTTHARD2D) if (getNumberofUDPInterfaces() > 1) { - if (udpDetails.srcmac2 == 0) { - char dmac2[50]; - memset(dmac2, 0, 50); + if (udpDetails[0].srcmac2 == 0) { + char dmac2[MAC_ADDRESS_SIZE]; + memset(dmac2, 0, MAC_ADDRESS_SIZE); sprintf(dmac2, "aa:bb:cc:dd:%02x:%02x", (pos[0] + 1) & 0xFF, pos[1] & 0xFF); LOG(logINFO, ("Udp source mac address2 created: %s\n", dmac2)); unsigned char a[6]; sscanf(dmac2, "%hhx:%hhx:%hhx:%hhx:%hhx:%hhx", &a[0], &a[1], &a[2], &a[3], &a[4], &a[5]); - udpDetails.srcmac2 = 0; + udpDetails[0].srcmac2 = 0; for (int i = 0; i < 6; ++i) { - udpDetails.srcmac2 = (udpDetails.srcmac2 << 8) + a[i]; + udpDetails[0].srcmac2 = (udpDetails[0].srcmac2 << 8) + a[i]; + } + for (int iRxEntry = 1; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcmac2 = udpDetails[0].srcmac2; } } } @@ -4914,50 +4945,52 @@ int check_detector_idle(const char *s) { } int is_udp_configured() { - if (udpDetails.dstip == 0) { - strcpy(configureMessage, "udp destination ip not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; - } - if (udpDetails.srcip == 0) { - strcpy(configureMessage, "udp source ip not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; - } - if (udpDetails.srcmac == 0) { - strcpy(configureMessage, "udp source mac not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; - } - if (udpDetails.dstmac == 0) { - strcpy(configureMessage, "udp destination mac not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; - } + for (int i = 0; i != numUdpDestinations; ++i) { + if (udpDetails[i].dstip == 0) { + sprintf(configureMessage, "udp destination ip not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } + if (udpDetails[i].srcip == 0) { + sprintf(configureMessage, "udp source ip not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } + if (udpDetails[i].srcmac == 0) { + sprintf(configureMessage, "udp source mac not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } + if (udpDetails[i].dstmac == 0) { + sprintf(configureMessage, "udp destination mac not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } #if defined(JUNGFRAUD) || defined(GOTTHARD2D) - if (getNumberofUDPInterfaces() == 2) { - if (udpDetails.srcip2 == 0) { - strcpy(configureMessage, "udp source ip2 not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; + if (getNumberofUDPInterfaces() == 2) { + if (udpDetails[i].srcip2 == 0) { + sprintf(configureMessage, "udp source ip2 not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } + if (udpDetails[i].dstip2 == 0) { + sprintf(configureMessage, "udp destination ip2 not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } + if (udpDetails[i].srcmac2 == 0) { + sprintf(configureMessage, "udp source mac2 not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } + if (udpDetails[i].dstmac2 == 0) { + sprintf(configureMessage, "udp destination mac2 not configured [entry:%d]\n", i); + LOG(logWARNING, ("%s", configureMessage)); + return FAIL; + } } - if (udpDetails.dstip2 == 0) { - strcpy(configureMessage, "udp destination ip2 not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; - } - if (udpDetails.srcmac2 == 0) { - strcpy(configureMessage, "udp source mac2 not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; - } - if (udpDetails.dstmac2 == 0) { - strcpy(configureMessage, "udp destination mac2 not configured\n"); - LOG(logWARNING, ("%s", configureMessage)); - return FAIL; - } - } #endif + } return OK; } @@ -5000,8 +5033,11 @@ int set_source_udp_ip(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.srcip != arg) { - udpDetails.srcip = arg; + if (udpDetails[0].srcip != arg) { + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcip = arg; + } configure_mac(); } } @@ -5016,7 +5052,7 @@ int get_source_udp_ip(int file_des) { LOG(logDEBUG1, ("Getting udp source ip\n")); // get only - retval = udpDetails.srcip; + retval = udpDetails[0].srcip; retval = __builtin_bswap32(retval); LOG(logDEBUG1, ("udp soure ip retval: 0x%x\n", retval)); @@ -5039,8 +5075,11 @@ int set_source_udp_ip2(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.srcip2 != arg) { - udpDetails.srcip2 = arg; + if (udpDetails[0].srcip2 != arg) { + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcip2 = arg; + } configure_mac(); } } @@ -5059,7 +5098,7 @@ int get_source_udp_ip2(int file_des) { functionNotImplemented(); #else // get only - retval = udpDetails.srcip2; + retval = udpDetails[0].srcip2; retval = __builtin_bswap32(retval); LOG(logDEBUG1, ("udp soure ip2 retval: 0x%x\n", retval)); #endif @@ -5079,8 +5118,8 @@ int set_dest_udp_ip(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.dstip != arg) { - udpDetails.dstip = arg; + if (udpDetails[0].dstip != arg) { + udpDetails[0].dstip = arg; configure_mac(); } } @@ -5095,7 +5134,7 @@ int get_dest_udp_ip(int file_des) { LOG(logDEBUG1, ("Getting destination ip\n")); // get only - retval = udpDetails.dstip; + retval = udpDetails[0].dstip; retval = __builtin_bswap32(retval); LOG(logDEBUG1, ("udp destination ip retval: 0x%x\n", retval)); @@ -5118,8 +5157,8 @@ int set_dest_udp_ip2(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.dstip2 != arg) { - udpDetails.dstip2 = arg; + if (udpDetails[0].dstip2 != arg) { + udpDetails[0].dstip2 = arg; configure_mac(); } } @@ -5138,7 +5177,7 @@ int get_dest_udp_ip2(int file_des) { functionNotImplemented(); #else // get only - retval = udpDetails.dstip2; + retval = udpDetails[0].dstip2; retval = __builtin_bswap32(retval); LOG(logDEBUG1, ("udp destination ip2 retval: 0x%x\n", retval)); #endif @@ -5157,8 +5196,11 @@ int set_source_udp_mac(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.srcmac != arg) { - udpDetails.srcmac = arg; + if (udpDetails[0].srcmac != arg) { + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcmac = arg; + } configure_mac(); } } @@ -5173,7 +5215,7 @@ int get_source_udp_mac(int file_des) { LOG(logDEBUG1, ("Getting udp source mac\n")); // get only - retval = udpDetails.srcmac; + retval = udpDetails[0].srcmac; LOG(logDEBUG1, ("udp soure mac retval: 0x%lx\n", retval)); return Server_SendResult(file_des, INT64, &retval, sizeof(retval)); @@ -5194,8 +5236,11 @@ int set_source_udp_mac2(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.srcmac2 != arg) { - udpDetails.srcmac2 = arg; + if (udpDetails[0].srcmac2 != arg) { + for (int iRxEntry = 0; iRxEntry != MAX_UDP_DESTINATION; + ++iRxEntry) { + udpDetails[iRxEntry].srcmac2 = arg; + } configure_mac(); } } @@ -5214,7 +5259,7 @@ int get_source_udp_mac2(int file_des) { functionNotImplemented(); #else // get only - retval = udpDetails.srcmac2; + retval = udpDetails[0].srcmac2; LOG(logDEBUG1, ("udp soure mac2 retval: 0x%lx\n", retval)); #endif return Server_SendResult(file_des, INT64, &retval, sizeof(retval)); @@ -5232,8 +5277,8 @@ int set_dest_udp_mac(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.dstmac != arg) { - udpDetails.dstmac = arg; + if (udpDetails[0].dstmac != arg) { + udpDetails[0].dstmac = arg; configure_mac(); } } @@ -5248,7 +5293,7 @@ int get_dest_udp_mac(int file_des) { LOG(logDEBUG1, ("Getting udp destination mac\n")); // get only - retval = udpDetails.dstmac; + retval = udpDetails[0].dstmac; LOG(logDEBUG1, ("udp destination mac retval: 0x%lx\n", retval)); return Server_SendResult(file_des, INT64, &retval, sizeof(retval)); @@ -5269,8 +5314,8 @@ int set_dest_udp_mac2(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.dstmac2 != arg) { - udpDetails.dstmac2 = arg; + if (udpDetails[0].dstmac2 != arg) { + udpDetails[0].dstmac2 = arg; configure_mac(); } } @@ -5289,7 +5334,7 @@ int get_dest_udp_mac2(int file_des) { functionNotImplemented(); #else // get only - retval = udpDetails.dstmac2; + retval = udpDetails[0].dstmac2; LOG(logDEBUG1, ("udp destination mac2 retval: 0x%lx\n", retval)); #endif return Server_SendResult(file_des, INT64, &retval, sizeof(retval)); @@ -5307,8 +5352,8 @@ int set_dest_udp_port(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.dstport != arg) { - udpDetails.dstport = arg; + if (udpDetails[0].dstport != arg) { + udpDetails[0].dstport = arg; configure_mac(); } } @@ -5323,7 +5368,7 @@ int get_dest_udp_port(int file_des) { LOG(logDEBUG1, ("Getting destination port")); // get only - retval = udpDetails.dstport; + retval = udpDetails[0].dstport; LOG(logDEBUG, ("udp destination port retval: %u\n", retval)); return Server_SendResult(file_des, INT32, &retval, sizeof(retval)); @@ -5344,8 +5389,8 @@ int set_dest_udp_port2(int file_des) { // only set if (Server_VerifyLock() == OK) { if (check_detector_idle("configure mac") == OK) { - if (udpDetails.dstport2 != arg) { - udpDetails.dstport2 = arg; + if (udpDetails[0].dstport2 != arg) { + udpDetails[0].dstport2 = arg; configure_mac(); } } @@ -5364,7 +5409,7 @@ int get_dest_udp_port2(int file_des) { functionNotImplemented(); #else // get only - retval = udpDetails.dstport2; + retval = udpDetails[0].dstport2; LOG(logDEBUG1, ("udp destination port2 retval: %u\n", retval)); #endif return Server_SendResult(file_des, INT32, &retval, sizeof(retval)); @@ -5393,6 +5438,33 @@ int set_num_interfaces(int file_des) { } else if (check_detector_idle("configure mac") == OK) { if (getNumberofUDPInterfaces() != arg) { setNumberofUDPInterfaces(arg); + for (int iRxEntry = 0; iRxEntry != numUdpDestinations; ++iRxEntry) { + if (arg == 1) { + udpDetails[iRxEntry].srcport2 = 0; + udpDetails[iRxEntry].srcip2 = 0; + udpDetails[iRxEntry].srcmac2 = 0; + udpDetails[iRxEntry].dstport2 = 0; + udpDetails[iRxEntry].dstip2 = 0; + udpDetails[iRxEntry].dstmac2 = 0; + } else { + // if still 0, set defaults + udpDetails[iRxEntry].srcport2 = DEFAULT_UDP_SRC_PORTNO + 1; + if (udpDetails[iRxEntry].dstport2 == 0) { + udpDetails[iRxEntry].dstport2 = 2 * iRxEntry + 1 + DEFAULT_UDP_DST_PORTNO; + } + // if still 0, copy from entry 0 + if (iRxEntry != 0) { + udpDetails[iRxEntry].srcip2 = udpDetails[0].srcip2; + udpDetails[iRxEntry].srcmac2 = udpDetails[0].srcmac2; + if (udpDetails[iRxEntry].dstip2 == 0) { + udpDetails[iRxEntry].dstip2 = udpDetails[0].dstip2; + } + if (udpDetails[iRxEntry].dstmac2 == 0) { + udpDetails[iRxEntry].dstmac2 = udpDetails[0].dstmac2; + } + } + } + } calculate_and_set_position(); // aleady configures mac } } @@ -6967,39 +7039,39 @@ int get_receiver_parameters(int file_des) { return printSocketReadError(); // udp dst port - i32 = udpDetails.dstport; + i32 = udpDetails[0].dstport; n += sendData(file_des, &i32, sizeof(i32), INT32); if (n < 0) return printSocketReadError(); // udp dst ip - u32 = udpDetails.dstip; + u32 = udpDetails[0].dstip; u32 = __builtin_bswap32(u32); n += sendData(file_des, &u32, sizeof(u32), INT32); if (n < 0) return printSocketReadError(); // udp dst mac - u64 = udpDetails.dstmac; + u64 = udpDetails[0].dstmac; n += sendData(file_des, &u64, sizeof(u64), INT64); if (n < 0) return printSocketReadError(); // udp dst port2 - i32 = udpDetails.dstport2; + i32 = udpDetails[0].dstport2; n += sendData(file_des, &i32, sizeof(i32), INT32); if (n < 0) return printSocketReadError(); // udp dst ip2 - u32 = udpDetails.dstip2; + u32 = udpDetails[0].dstip2; u32 = __builtin_bswap32(u32); n += sendData(file_des, &u32, sizeof(u32), INT32); if (n < 0) return printSocketReadError(); // udp dst mac2 - u64 = udpDetails.dstmac2; + u64 = udpDetails[0].dstmac2; n += sendData(file_des, &u64, sizeof(u64), INT64); if (n < 0) return printSocketReadError(); @@ -8978,4 +9050,284 @@ int set_module_id(int file_des) { } #endif return Server_SendResult(file_des, INT32, NULL, 0); -} \ No newline at end of file +} + +int get_dest_udp_list(int file_des) { + ret = OK; + memset(mess, 0, sizeof(mess)); + uint32_t arg = 0; + uint32_t retvals[5] = {}; + uint64_t retvals64[2] = {}; + + if (receiveData(file_des, &arg, sizeof(arg), INT32) < 0) + return printSocketReadError(); + LOG(logDEBUG1, ("Getting udp destination list for entry %d\n", arg)); + +#if !defined(EIGERD) && !defined(JUNGFRAUD) + functionNotImplemented(); +#else + if (arg > MAX_UDP_DESTINATION) { + ret = FAIL; + sprintf( + mess, + "Could not set udp destination. Invalid entry. Options: 0 - %d\n", + MAX_UDP_DESTINATION); + LOG(logERROR, (mess)); + } else { + retvals[0] = arg; + retvals[1] = udpDetails[arg].dstport; + retvals[2] = udpDetails[arg].dstport2; + retvals[3] = udpDetails[arg].dstip; + retvals[4] = udpDetails[arg].dstip2; + retvals64[0] = udpDetails[arg].dstmac; + retvals64[1] = udpDetails[arg].dstmac2; + + // swap ip + retvals[3] = __builtin_bswap32(retvals[3]); + retvals[4] = __builtin_bswap32(retvals[4]); + + // convert to string + char ip[INET_ADDRSTRLEN], ip2[INET_ADDRSTRLEN]; + getIpAddressinString(ip, retvals[3]); + getIpAddressinString(ip2, retvals[4]); + char mac[MAC_ADDRESS_SIZE], mac2[MAC_ADDRESS_SIZE]; + getMacAddressinString(mac, MAC_ADDRESS_SIZE, retvals64[0]); + getMacAddressinString(mac2, MAC_ADDRESS_SIZE, retvals64[1]); + LOG(logDEBUG1, + ("Udp Dest. retval [%d]: [port %d, port2 %d, ip %s, ip2 %s, " + "mac %s, mac2 %s]\n", + retvals[0], retvals[1], retvals[2], ip, ip2, mac, mac2)); + } +#endif + Server_SendResult(file_des, INT32, NULL, 0); + if (ret != FAIL) { + sendData(file_des, retvals, sizeof(retvals), INT32); + sendData(file_des, retvals64, sizeof(retvals64), INT64); + } + return ret; +} + +int set_dest_udp_list(int file_des) { + ret = OK; + memset(mess, 0, sizeof(mess)); + uint32_t args[5] = {}; + uint64_t args64[2] = {}; + + if (receiveData(file_des, args, sizeof(args), INT32) < 0) + return printSocketReadError(); + if (receiveData(file_des, args64, sizeof(args64), INT64) < 0) + return printSocketReadError(); + + // swap ip + args[3] = __builtin_bswap32(args[3]); + args[4] = __builtin_bswap32(args[4]); + + // convert to string + char ip[INET_ADDRSTRLEN], ip2[INET_ADDRSTRLEN]; + getIpAddressinString(ip, args[3]); + getIpAddressinString(ip2, args[4]); + char mac[MAC_ADDRESS_SIZE], mac2[MAC_ADDRESS_SIZE]; + getMacAddressinString(mac, MAC_ADDRESS_SIZE, args64[0]); + getMacAddressinString(mac2, MAC_ADDRESS_SIZE, args64[1]); + +#if !defined(EIGERD) && !defined(JUNGFRAUD) + functionNotImplemented(); +#else + // only set + if (Server_VerifyLock() == OK) { + int entry = args[0]; + LOG(logINFOBLUE, + ("Setting udp dest. [%d]: [port %d, port2 %d, ip %s, ip2 %s, " + "mac %s, mac2 %s]\n", + entry, args[1], args[2], ip, ip2, mac, mac2)); + + if (entry < 1 || entry > MAX_UDP_DESTINATION) { + ret = FAIL; + sprintf( + mess, + "Could not set udp destination. Invalid entry. Options: 1 - %d\n", + MAX_UDP_DESTINATION); + LOG(logERROR, (mess)); + } +#ifdef EIGERD + else if (args[4] != 0 || args64[1] != 0) { + ret = FAIL; + strcpy( + mess, + "Could not set udp destination. ip2 and mac2 not implemented for this detector.\n"); + LOG(logERROR, (mess)); + } +#endif + else { + if (check_detector_idle("set udp destination list entries") == OK) { + if (args[1] != 0) { + udpDetails[entry].dstport = args[1]; + } + if (args[2] != 0) { + udpDetails[entry].dstport2 = args[2]; + } + if (args[3] != 0) { + udpDetails[entry].dstip = args[3]; + } + if (args[4] != 0) { + udpDetails[entry].dstip2 = args[4]; + } + if (args64[0] != 0) { + udpDetails[entry].dstmac = args64[0]; + } + if (args64[1] != 0) { + udpDetails[entry].dstmac2 = args64[1]; + } + + // if still 0, set defaults + int twoInterfaces = 0; +#if defined(JUNGFRAUD) || defined(GOTTHARD2D) + twoInterfaces = getNumberofUDPInterfaces() == 2 ? 1 : 0; +#endif + udpDetails[entry].srcport = DEFAULT_UDP_SRC_PORTNO; + if (udpDetails[entry].dstport == 0) { + udpDetails[entry].dstport = 2 * entry + DEFAULT_UDP_DST_PORTNO; + } + if (myDetectorType == EIGER || twoInterfaces) { + udpDetails[entry].srcport2 = DEFAULT_UDP_SRC_PORTNO + 1; + if (udpDetails[entry].dstport2 == 0) { + udpDetails[entry].dstport2 = 2 * entry + 1 + DEFAULT_UDP_DST_PORTNO; + } + } + // if still 0, copy from entry 0 + if (entry != 0) { + udpDetails[entry].srcip = udpDetails[0].srcip; + udpDetails[entry].srcmac = udpDetails[0].srcmac; + if (udpDetails[entry].dstip == 0) { + udpDetails[entry].dstip = udpDetails[0].dstip; + } + if (udpDetails[entry].dstmac == 0) { + udpDetails[entry].dstmac = udpDetails[0].dstmac; + } + if (twoInterfaces) { + udpDetails[entry].srcip2 = udpDetails[0].srcip2; + udpDetails[entry].srcmac2 = udpDetails[0].srcmac2; + if (udpDetails[entry].dstip2 == 0) { + udpDetails[entry].dstip2 = udpDetails[0].dstip2; + } + if (udpDetails[entry].dstmac2 == 0) { + udpDetails[entry].dstmac2 = udpDetails[0].dstmac2; + } + } + } + configure_mac(); + } + } + } +#endif + return Server_SendResult(file_des, INT32, NULL, 0); +} + +int get_num_dest_list(int file_des) { + ret = OK; + memset(mess, 0, sizeof(mess)); + int retval = -1; +#if !defined(JUNGFRAUD) && !defined(EIGERD) + functionNotImplemented(); +#else + retval = numUdpDestinations; + int retval1 = 0; + if (getNumberofDestinations(&retval1) == FAIL || retval1 != retval) { + ret = FAIL; + sprintf( + mess, + "Could not get number of udp destinations. (server reads %d, fpga reads %d).\n", retval1, retval); + LOG(logERROR, (mess)); + } +#endif + LOG(logDEBUG1, ("numUdpDestinations retval: 0x%x\n", retval)); + return Server_SendResult(file_des, INT32, &retval, sizeof(retval)); +} + +int set_num_dest_list(int file_des) { + ret = OK; + memset(mess, 0, sizeof(mess)); + int arg = -1; + + if (receiveData(file_des, &arg, sizeof(arg), INT32) < 0) + return printSocketReadError(); + LOG(logDEBUG1, ("Setting number of udp destinations to %d\n", arg)); + +#if !defined(JUNGFRAUD) && !defined(EIGERD) + functionNotImplemented(); +#else + if (arg < 1 || arg > MAX_UDP_DESTINATION) { + ret = FAIL; + sprintf(mess, + "Could not set number of udp destinations. Options: 1-%d\n", + MAX_UDP_DESTINATION); + LOG(logERROR, (mess)); + } else { + if (check_detector_idle("set number of udp destinations") == OK) { + if (setNumberofDestinations(arg) == FAIL) { + ret = FAIL; + strcpy(mess, + "Could not set number of udp destinations.\n"); + LOG(logERROR, (mess)); + } else { + numUdpDestinations = arg; + configure_mac(); + } + } + } +#endif + return Server_SendResult(file_des, INT32, NULL, 0); +} + +int get_udp_first_dest(int file_des) { + ret = OK; + memset(mess, 0, sizeof(mess)); + int retval = -1; +#ifndef JUNGFRAUD + functionNotImplemented(); +#else + retval = firstUDPDestination; + if (getFirstUDPDestination() != retval) { + ret = FAIL; + sprintf(mess, + "Could not get first desintation. (server reads %d, fpga reads " + "%d).\n", + getFirstUDPDestination(), retval); + LOG(logERROR, (mess)); + } +#endif + LOG(logDEBUG1, ("first udp destination retval: 0x%x\n", retval)); + return Server_SendResult(file_des, INT32, &retval, sizeof(retval)); +} + +int set_udp_first_dest(int file_des) { + ret = OK; + memset(mess, 0, sizeof(mess)); + int arg = -1; + + if (receiveData(file_des, &arg, sizeof(arg), INT32) < 0) + return printSocketReadError(); + LOG(logDEBUG1, ("Setting first udp destination to %d\n", arg)); + +#ifndef JUNGFRAUD + functionNotImplemented(); +#else + if (arg < 0 || arg >= numUdpDestinations) { + ret = FAIL; + sprintf(mess, "Could not set first destination. Options: 0-%d\n", + numUdpDestinations - 1); + LOG(logERROR, (mess)); + } else { + if (check_detector_idle("set first udp destination") == OK) { + setFirstUDPDestination(arg); + int retval = getFirstUDPDestination(); + validate(&ret, mess, arg, retval, "set udp first destination", DEC); + if (ret == OK) { + firstUDPDestination = arg; + //configure_mac(); + } + } + } +#endif + return Server_SendResult(file_des, INT32, NULL, 0); +} diff --git a/slsDetectorSoftware/include/sls/Detector.h b/slsDetectorSoftware/include/sls/Detector.h index 5615fd8bb..d507464b3 100644 --- a/slsDetectorSoftware/include/sls/Detector.h +++ b/slsDetectorSoftware/include/sls/Detector.h @@ -666,6 +666,23 @@ class Detector { /** [Jungfrau] bottom half [Gotthard2] veto debugging */ void setSourceUDPMAC2(const MacAddr mac, Positions pos = {}); + Result getDestinationUDPList(const uint32_t entry, + Positions pos = {}) const; + + void setDestinationUDPList(const UdpDestination, const int module_id); + + /** [Jungfrau][Eiger] */ + Result getNumberofUDPDestinations(Positions pos = {}) const; + + /**[Jungfrau][Eiger] Options 1-32 */ + void setNumberofUDPDestinations(const int value, Positions pos = {}); + + /** [Jungfrau] */ + Result getFirstUDPDestination(Positions pos = {}) const; + + /**[Jungfrau] Options 0-31 (or number of udp destinations) */ + void setFirstUDPDestination(const int value, Positions pos = {}); + Result getDestinationUDPIP(Positions pos = {}) const; /** IP of the interface in receiver that the detector sends data to */ diff --git a/slsDetectorSoftware/src/CmdProxy.cpp b/slsDetectorSoftware/src/CmdProxy.cpp index a2862c45a..2f66ad821 100644 --- a/slsDetectorSoftware/src/CmdProxy.cpp +++ b/slsDetectorSoftware/src/CmdProxy.cpp @@ -1368,6 +1368,94 @@ std::string CmdProxy::Trigger(int action) { /* Network Configuration (Detector<->Receiver) */ +IpAddr CmdProxy::getIpFromAuto() { + std::string rxHostname = + det->getRxHostname(std::vector{det_id}).squash("none"); + // Hostname could be ip try to decode otherwise look up the hostname + auto val = sls::IpAddr{rxHostname}; + if (val == 0) { + val = HostnameToIp(rxHostname.c_str()); + } + return val; +} + +UdpDestination CmdProxy::getUdpEntry() { + UdpDestination udpDestination{}; + bool hasEntry = false; + + for (auto it : args) { + size_t pos = it.find('='); + std::string key = it.substr(0, pos); + std::string value = it.substr(pos + 1); + if (key == "entry") { + udpDestination.entry = StringTo(value); + hasEntry = true; + } else if (key == "ip") { + if (value == "auto") { + auto val = getIpFromAuto(); + LOG(logINFO) << "Setting udp_dstip of detector " << det_id + << " to " << val; + udpDestination.ip = val; + } else { + udpDestination.ip = IpAddr(value); + } + } else if (key == "ip2") { + if (value == "auto") { + auto val = getIpFromAuto(); + LOG(logINFO) << "Setting udp_dstip2 of detector " << det_id + << " to " << val; + udpDestination.ip2 = val; + } else { + udpDestination.ip2 = IpAddr(value); + } + } else if (key == "mac") { + udpDestination.mac = MacAddr(value); + } else if (key == "mac2") { + udpDestination.mac2 = MacAddr(value); + } else if (key == "port") { + udpDestination.port = StringTo(value); + } else if (key == "port2") { + udpDestination.port2 = StringTo(value); + } + } + if (!hasEntry) { + throw sls::RuntimeError("Found no entry argument."); + } + return udpDestination; +} + +std::string CmdProxy::UDPDestinationList(int action) { + std::ostringstream os; + os << cmd << ' '; + if (action == defs::HELP_ACTION) { + os << "[entry=n_val] [ip=x.x.x.x] [(optional)ip2=x.x.x.x] " + "\n[mac=xx:xx:xx:xx:xx:xx] " + "[(optional)mac2=xx:xx:xx:xx:xx:xx]\n[port=value] " + "[(optional)port2=value\n\tThe order of ip, mac and port does " + "not matter. entry_value can be >0 only for Eiger and Jungfrau " + "where round robin is implemented. If 'auto' used, then ip is " + "set to ip of rx_hostname." + << '\n'; + } else if (action == defs::GET_ACTION) { + if (args.size() != 1) { + WrongNumberOfParameters(1); + } + auto t = det->getDestinationUDPList(StringTo(args[0]), + std::vector{det_id}); + os << OutString(t) << '\n'; + } else if (action == defs::PUT_ACTION) { + if (args.empty()) { + WrongNumberOfParameters(1); + } + auto t = getUdpEntry(); + det->setDestinationUDPList(t, det_id); + os << ToString(args) << std::endl; + } else { + throw sls::RuntimeError("Unknown action"); + } + return os.str(); +} + std::string CmdProxy::UDPDestinationIP(int action) { std::ostringstream os; os << cmd << ' '; @@ -1387,13 +1475,7 @@ std::string CmdProxy::UDPDestinationIP(int action) { WrongNumberOfParameters(1); } if (args[0] == "auto") { - std::string rxHostname = - det->getRxHostname(std::vector{det_id}).squash("none"); - // Hostname could be ip try to decode otherwise look up the hostname - auto val = sls::IpAddr{rxHostname}; - if (val == 0) { - val = HostnameToIp(rxHostname.c_str()); - } + auto val = getIpFromAuto(); LOG(logINFO) << "Setting udp_dstip of detector " << det_id << " to " << val; det->setDestinationUDPIP(val, std::vector{det_id}); @@ -1429,13 +1511,7 @@ std::string CmdProxy::UDPDestinationIP2(int action) { WrongNumberOfParameters(1); } if (args[0] == "auto") { - std::string rxHostname = - det->getRxHostname(std::vector{det_id}).squash("none"); - // Hostname could be ip try to decode otherwise look up the hostname - auto val = sls::IpAddr{rxHostname}; - if (val == 0) { - val = HostnameToIp(rxHostname.c_str()); - } + auto val = getIpFromAuto(); LOG(logINFO) << "Setting udp_dstip2 of detector " << det_id << " to " << val; det->setDestinationUDPIP2(val, std::vector{det_id}); diff --git a/slsDetectorSoftware/src/CmdProxy.h b/slsDetectorSoftware/src/CmdProxy.h index 7bd0ab759..67123ed86 100644 --- a/slsDetectorSoftware/src/CmdProxy.h +++ b/slsDetectorSoftware/src/CmdProxy.h @@ -857,6 +857,9 @@ class CmdProxy { /* Network Configuration (Detector<->Receiver) */ {"numinterfaces", &CmdProxy::numinterfaces}, {"selinterface", &CmdProxy::selinterface}, + {"udp_dstlist", &CmdProxy::UDPDestinationList}, + {"udp_numdst", &CmdProxy::udp_numdst}, + {"udp_firstdst", &CmdProxy::udp_firstdst}, {"udp_srcip", &CmdProxy::udp_srcip}, {"udp_srcip2", &CmdProxy::udp_srcip2}, {"udp_dstip", &CmdProxy::UDPDestinationIP}, @@ -1113,6 +1116,9 @@ class CmdProxy { std::string Scan(int action); std::string Trigger(int action); /* Network Configuration (Detector<->Receiver) */ + IpAddr getIpFromAuto(); + UdpDestination getUdpEntry(); + std::string UDPDestinationList(int action); std::string UDPDestinationIP(int action); std::string UDPDestinationIP2(int action); /* Receiver Config */ @@ -1528,6 +1534,20 @@ class CmdProxy { "[0, 1]\n\t[Jungfrau] The udp interface to stream data from detector. " "Effective only when number of interfaces is 1. Default: 0 (outer)"); + INTEGER_COMMAND_VEC_ID(udp_numdst, getNumberofUDPDestinations, + setNumberofUDPDestinations, StringTo, + "[1 - 32]\n\t[Jungfrau][Eiger] One can set upto 32 " + "destinations that the detector will stream images " + "out in a round robin fashion. Default: 1"); + + INTEGER_COMMAND_VEC_ID( + udp_firstdst, getFirstUDPDestination, setFirstUDPDestination, + StringTo, + "[0 - 31 (or number of udp destinations)]\n\t[Jungfrau] One can set which is the first " + "destination that the detector will stream images " + "out from in a round robin fashion. The entry must not have been " + "empty. Default: 0"); + INTEGER_COMMAND_VEC_ID( udp_srcip, getSourceUDPIP, setSourceUDPIP, IpAddr, "[x.x.x.x]\n\tIp address of the detector (source) udp " diff --git a/slsDetectorSoftware/src/Detector.cpp b/slsDetectorSoftware/src/Detector.cpp index fac7c65a0..496a0411f 100644 --- a/slsDetectorSoftware/src/Detector.cpp +++ b/slsDetectorSoftware/src/Detector.cpp @@ -908,6 +908,35 @@ void Detector::setSourceUDPMAC2(const MacAddr mac, Positions pos) { pimpl->Parallel(&Module::setSourceUDPMAC2, pos, mac); } +Result Detector::getDestinationUDPList(const uint32_t entry, + Positions pos) const { + return pimpl->Parallel(&Module::getDestinationUDPList, pos, entry); +} + +void Detector::setDestinationUDPList(const UdpDestination dest, + const int module_id) { + if (module_id == -1 && size() > 1) { + throw sls::RuntimeError("Cannot set this parameter at detector level."); + } + pimpl->Parallel(&Module::setDestinationUDPList, {module_id}, dest); +} + +Result Detector::getNumberofUDPDestinations(Positions pos) const { + return pimpl->Parallel(&Module::getNumberofUDPDestinations, pos); +} + +void Detector::setNumberofUDPDestinations(const int value, Positions pos) { + pimpl->Parallel(&Module::setNumberofUDPDestinations, pos, value); +} + +Result Detector::getFirstUDPDestination(Positions pos) const { + return pimpl->Parallel(&Module::getFirstUDPDestination, pos); +} + +void Detector::setFirstUDPDestination(const int value, Positions pos) { + pimpl->Parallel(&Module::setFirstUDPDestination, pos, value); +} + Result Detector::getDestinationUDPIP(Positions pos) const { return pimpl->Parallel(&Module::getDestinationUDPIP, pos); } diff --git a/slsDetectorSoftware/src/DetectorImpl.cpp b/slsDetectorSoftware/src/DetectorImpl.cpp index 20b159875..edc4440a4 100644 --- a/slsDetectorSoftware/src/DetectorImpl.cpp +++ b/slsDetectorSoftware/src/DetectorImpl.cpp @@ -290,6 +290,11 @@ void DetectorImpl::updateDetectorSize() { LOG(logDEBUG) << "Updating Multi-Detector Size: " << size(); const slsDetectorDefs::xy det_size = detectors[0]->getNumberOfChannels(); + + if (det_size.x == 0 || det_size.y == 0) { + throw sls::RuntimeError("Module size for x or y dimensions is 0. Unable to proceed in updating detector size. "); + } + int maxx = multi_shm()->numberOfChannels.x; int maxy = multi_shm()->numberOfChannels.y; int ndetx = 0, ndety = 0; diff --git a/slsDetectorSoftware/src/Module.cpp b/slsDetectorSoftware/src/Module.cpp index fbff82223..54e5b927d 100644 --- a/slsDetectorSoftware/src/Module.cpp +++ b/slsDetectorSoftware/src/Module.cpp @@ -939,6 +939,52 @@ void Module::setSourceUDPMAC2(const sls::MacAddr mac) { sendToDetector(F_SET_SOURCE_UDP_MAC2, mac, nullptr); } +sls::UdpDestination Module::getDestinationUDPList(const uint32_t entry) const { + return sendToDetector(F_GET_DEST_UDP_LIST, entry); +} + +void Module::setDestinationUDPList(const sls::UdpDestination dest) { + // set them in the default way so the receivers are also set up + if (dest.entry == 0) { + if (dest.port != 0) { + setDestinationUDPPort(dest.port); + } + if (dest.ip != 0) { + setDestinationUDPIP(dest.ip); + } + if (dest.mac != 0) { + setDestinationUDPMAC(dest.mac); + } + if (dest.port2 != 0) { + setDestinationUDPPort2(dest.port2); + } + if (dest.ip2 != 0) { + setDestinationUDPIP2(dest.ip2); + } + if (dest.mac2 != 0) { + setDestinationUDPMAC2(dest.mac2); + } + } else { + sendToDetector(F_SET_DEST_UDP_LIST, dest, nullptr); + } +} + +int Module::getNumberofUDPDestinations() const { + return sendToDetector(F_GET_NUM_DEST_UDP); +} + +void Module::setNumberofUDPDestinations(const int value) { + sendToDetector(F_SET_NUM_DEST_UDP, value, nullptr); +} + +int Module::getFirstUDPDestination() const { + return sendToDetector(F_GET_UDP_FIRST_DEST); +} + +void Module::setFirstUDPDestination(const int value) { + sendToDetector(F_SET_UDP_FIRST_DEST, value, nullptr); +} + sls::IpAddr Module::getDestinationUDPIP() const { return sendToDetector(F_GET_DEST_UDP_IP); } diff --git a/slsDetectorSoftware/src/Module.h b/slsDetectorSoftware/src/Module.h index f53f40168..f84e78774 100644 --- a/slsDetectorSoftware/src/Module.h +++ b/slsDetectorSoftware/src/Module.h @@ -222,6 +222,12 @@ class Module : public virtual slsDetectorDefs { void setSourceUDPMAC(const sls::MacAddr mac); sls::MacAddr getSourceUDPMAC2() const; void setSourceUDPMAC2(const sls::MacAddr mac); + sls::UdpDestination getDestinationUDPList(const uint32_t entry) const; + void setDestinationUDPList(const sls::UdpDestination dest); + int getNumberofUDPDestinations() const; + void setNumberofUDPDestinations(const int value); + int getFirstUDPDestination() const; + void setFirstUDPDestination(const int value); sls::IpAddr getDestinationUDPIP() const; void setDestinationUDPIP(const sls::IpAddr ip); sls::IpAddr getDestinationUDPIP2() const; diff --git a/slsDetectorSoftware/tests/test-CmdProxy.cpp b/slsDetectorSoftware/tests/test-CmdProxy.cpp index 919b6098f..cb031219b 100644 --- a/slsDetectorSoftware/tests/test-CmdProxy.cpp +++ b/slsDetectorSoftware/tests/test-CmdProxy.cpp @@ -2215,6 +2215,84 @@ TEST_CASE("udp_srcip", "[.cmd]") { } } +TEST_CASE("udp_dstlist", "[.cmd]") { + Detector det; + CmdProxy proxy(&det); + auto det_type = det.getDetectorType().squash(); + if (det_type == defs::JUNGFRAU || det_type == defs::EIGER) { + REQUIRE_NOTHROW(proxy.Call("udp_dstlist", {"0"}, -1, GET)); + REQUIRE_THROWS(proxy.Call( + "udp_dstlist", + {"entry=0", "ip=0.0.0.0", "mac=00:00:00:00:00:00", "port=1233"}, -1, + PUT)); + } else { + REQUIRE_THROWS(proxy.Call("udp_dstlist", {"0"}, -1, GET)); + } +} + +TEST_CASE("udp_numdst", "[.cmd]") { + Detector det; + CmdProxy proxy(&det); + auto det_type = det.getDetectorType().squash(); + if (det_type == defs::JUNGFRAU || det_type == defs::EIGER) { + auto prev_val = det.getNumberofUDPDestinations(); + { + std::ostringstream oss; + proxy.Call("udp_numdst", {"10"}, -1, PUT, oss); + REQUIRE(oss.str() == "udp_numdst 10\n"); + } + { + std::ostringstream oss; + proxy.Call("udp_numdst", {}, -1, GET, oss); + REQUIRE(oss.str() == "udp_numdst 10\n"); + } + { + std::ostringstream oss; + proxy.Call("udp_numdst", {"32"}, -1, PUT, oss); + REQUIRE(oss.str() == "udp_numdst 32\n"); + } + REQUIRE_THROWS(proxy.Call("udp_numdst", {"0"}, -1, PUT)); + REQUIRE_THROWS(proxy.Call("udp_numdst", {"33"}, -1, PUT)); + + for (int i = 0; i != det.size(); ++i) { + det.setNumberofUDPDestinations(prev_val[i], {i}); + } + } else { + REQUIRE_THROWS(proxy.Call("udp_numdst", {}, -1, GET)); + } +} + +TEST_CASE("udp_firstdst", "[.cmd]") { + Detector det; + CmdProxy proxy(&det); + auto det_type = det.getDetectorType().squash(); + if (det_type == defs::JUNGFRAU) { + auto prev_val = det.getFirstUDPDestination(); + { + std::ostringstream oss; + proxy.Call("udp_firstdst", {"0"}, -1, PUT, oss); + REQUIRE(oss.str() == "udp_firstdst 10\n"); + } + { + std::ostringstream oss; + proxy.Call("udp_firstdst", {}, -1, GET, oss); + REQUIRE(oss.str() == "udp_firstdst 0\n"); + } + { + std::ostringstream oss; + proxy.Call("udp_firstdst", {"1"}, -1, PUT, oss); + REQUIRE(oss.str() == "udp_firstdst 1\n"); + } + REQUIRE_THROWS(proxy.Call("udp_firstdst", {"33"}, -1, PUT)); + + for (int i = 0; i != det.size(); ++i) { + det.setFirstUDPDestination(prev_val[i], {i}); + } + } else { + REQUIRE_THROWS(proxy.Call("udp_numdst", {}, -1, GET)); + } +} + TEST_CASE("udp_dstip", "[.cmd]") { Detector det; CmdProxy proxy(&det); diff --git a/slsReceiverSoftware/src/ClientInterface.cpp b/slsReceiverSoftware/src/ClientInterface.cpp index 7ebe53533..02d1119e0 100644 --- a/slsReceiverSoftware/src/ClientInterface.cpp +++ b/slsReceiverSoftware/src/ClientInterface.cpp @@ -1669,7 +1669,7 @@ int ClientInterface::set_rate_correct(Interface &socket) { std::vector t(index); socket.Receive(t); verifyIdle(socket); - LOG(logINFOBLUE) << "Setting rate corrections[" << index << ']'; + LOG(logINFO) << "Setting rate corrections[" << index << ']'; impl()->setRateCorrections(t); return socket.Send(OK); } diff --git a/slsSupportLib/include/sls/ToString.h b/slsSupportLib/include/sls/ToString.h index 0f18a6d4c..bbcd4a6c9 100644 --- a/slsSupportLib/include/sls/ToString.h +++ b/slsSupportLib/include/sls/ToString.h @@ -55,7 +55,6 @@ std::ostream &operator<<(std::ostream &os, std::string ToString(const slsDetectorDefs::currentSrcParameters &r); std::ostream &operator<<(std::ostream &os, const slsDetectorDefs::currentSrcParameters &r); - const std::string &ToString(const std::string &s); /** Convert std::chrono::duration with specified output unit */ diff --git a/slsSupportLib/include/sls/network_utils.h b/slsSupportLib/include/sls/network_utils.h index b741b6e5e..68b090651 100644 --- a/slsSupportLib/include/sls/network_utils.h +++ b/slsSupportLib/include/sls/network_utils.h @@ -30,7 +30,7 @@ class IpAddr { return addr_ != other; } constexpr uint32_t uint32() const noexcept { return addr_; } -}; +} __attribute__((packed)); class MacAddr { private: @@ -57,13 +57,33 @@ class MacAddr { return addr_ != other; } constexpr uint64_t uint64() const noexcept { return addr_; } -}; +} __attribute__((packed)); + +struct UdpDestination { + uint32_t entry{}; + uint32_t port{}; + uint32_t port2{}; + IpAddr ip; + IpAddr ip2; + MacAddr mac; + MacAddr mac2; + std::string str() const; + + constexpr bool operator==(const UdpDestination &other) const { + return ((entry == other.entry) && (port == other.port) && + (port2 == other.port2) && (ip== other.ip) && + (ip2 == other.ip2) && (mac == other.mac) && + (mac2 == other.mac2)); + } +} __attribute__((packed)); + +std::ostream &operator<<(std::ostream &out, const IpAddr &addr); +std::ostream &operator<<(std::ostream &out, const MacAddr &addr); +std::ostream &operator<<(std::ostream &out, const UdpDestination &dest); IpAddr HostnameToIp(const char *hostname); std::string IpToInterfaceName(const std::string &ip); MacAddr InterfaceNameToMac(const std::string &inf); IpAddr InterfaceNameToIp(const std::string &ifn); -std::ostream &operator<<(std::ostream &out, const IpAddr &addr); -std::ostream &operator<<(std::ostream &out, const MacAddr &addr); } // namespace sls diff --git a/slsSupportLib/include/sls/sls_detector_defs.h b/slsSupportLib/include/sls/sls_detector_defs.h index 9848ceb96..c257661ba 100644 --- a/slsSupportLib/include/sls/sls_detector_defs.h +++ b/slsSupportLib/include/sls/sls_detector_defs.h @@ -36,6 +36,10 @@ #define DEFAULT_UDP_PORTNO 50001 #define DEFAULT_ZMQ_CL_PORTNO 30001 #define DEFAULT_ZMQ_RX_PORTNO 30001 +#define DEFAULT_UDP_SRC_PORTNO 32410 +#define DEFAULT_UDP_DST_PORTNO 50001 + +#define MAX_UDP_DESTINATION 32 #define SLS_DETECTOR_HEADER_VERSION 0x2 #define SLS_DETECTOR_JSON_HEADER_VERSION 0x4 @@ -457,35 +461,36 @@ typedef struct { } __attribute__((packed)); struct currentSrcParameters { - int enable; - int fix; - int normal; - uint64_t select; + int enable_; + int fix_; + int normal_; + uint64_t select_; /** [Gotthard2][Jungfrau] disable */ - currentSrcParameters() : enable(0), fix(-1), normal(-1), select(0) {} + currentSrcParameters() + : enable_(0), fix_(-1), normal_(-1), select_(0) {} /** [Gotthard2] enable or disable */ - currentSrcParameters(bool ena) - : enable(static_cast(ena)), fix(-1), normal(-1), select(0) {} + explicit currentSrcParameters(bool enable) + : enable_(static_cast(enable)), fix_(-1), normal_(-1), + select_(0) {} /** [Jungfrau](chipv1.0) enable current src with fix or no fix, - * selectColumn is 0 to 63 columns only */ - currentSrcParameters(bool fixCurrent, uint64_t selectColumn) - : enable(1), fix(static_cast(fixCurrent)), normal(-1), - select(selectColumn) {} + * select is 0 to 63 columns only */ + currentSrcParameters(bool fix, uint64_t select) + : enable_(1), fix_(static_cast(fix)), normal_(-1), + select_(select) {} - /** [Jungfrau](chipv1.1) enable current src, fixCurrent[fix|no fix], - * selectColumn is a mask of 63 bits (muliple columns can be selected - * simultaneously, normalCurrent [normal|low] */ - currentSrcParameters(bool fixCurrent, uint64_t selectColumn, - bool normalCurrent) - : enable(1), fix(static_cast(fixCurrent)), - normal(static_cast(normalCurrent)), select(selectColumn) {} + /** [Jungfrau](chipv1.1) enable current src, fix[fix|no fix], + * select is a mask of 63 bits (muliple columns can be selected + * simultaneously, normal [normal|low] */ + currentSrcParameters(bool fix, uint64_t select, bool normal) + : enable_(1), fix_(static_cast(fix)), + normal_(static_cast(normal)), select_(select) {} bool operator==(const currentSrcParameters &other) const { - return ((enable == other.enable) && (fix == other.fix) && - (normal == other.normal) && (select == other.select)); + return ((enable_ == other.enable_) && (fix_ == other.fix_) && + (normal_ == other.normal_) && (select_ == other.select_)); } } __attribute__((packed)); diff --git a/slsSupportLib/include/sls/sls_detector_funcs.h b/slsSupportLib/include/sls/sls_detector_funcs.h index 0c1cf104d..8e8210aae 100755 --- a/slsSupportLib/include/sls/sls_detector_funcs.h +++ b/slsSupportLib/include/sls/sls_detector_funcs.h @@ -245,6 +245,12 @@ enum detFuncs { F_GET_DBIT_PIPELINE, F_GET_MODULE_ID, F_SET_MODULE_ID, + F_GET_DEST_UDP_LIST, + F_SET_DEST_UDP_LIST, + F_GET_NUM_DEST_UDP, + F_SET_NUM_DEST_UDP, + F_GET_UDP_FIRST_DEST, + F_SET_UDP_FIRST_DEST, NUM_DET_FUNCTIONS, RECEIVER_ENUM_START = 256, /**< detector function should not exceed this @@ -597,6 +603,12 @@ const char* getFunctionNameFromEnum(enum detFuncs func) { case F_GET_DBIT_PIPELINE: return "F_GET_DBIT_PIPELINE"; case F_GET_MODULE_ID: return "F_GET_MODULE_ID"; case F_SET_MODULE_ID: return "F_SET_MODULE_ID"; + case F_GET_DEST_UDP_LIST: return "F_GET_DEST_UDP_LIST"; + case F_SET_DEST_UDP_LIST: return "F_SET_DEST_UDP_LIST"; + case F_GET_NUM_DEST_UDP: return "F_GET_NUM_DEST_UDP"; + case F_SET_NUM_DEST_UDP: return "F_SET_NUM_DEST_UDP"; + case F_GET_UDP_FIRST_DEST: return "F_GET_UDP_FIRST_DEST"; + case F_SET_UDP_FIRST_DEST: return "F_SET_UDP_FIRST_DEST"; case NUM_DET_FUNCTIONS: return "NUM_DET_FUNCTIONS"; case RECEIVER_ENUM_START: return "RECEIVER_ENUM_START"; diff --git a/slsSupportLib/include/sls/versionAPI.h b/slsSupportLib/include/sls/versionAPI.h index 5a8f8da9a..3c80221d7 100644 --- a/slsSupportLib/include/sls/versionAPI.h +++ b/slsSupportLib/include/sls/versionAPI.h @@ -1,13 +1,15 @@ /** API versions */ -#define GITBRANCH "j10partial" +#define GITBRANCH "roundrobin" -#define APILIB 0x210816 -#define APIRECEIVER 0x210816 -#define APIGUI 0x210816 -#define APIEIGER 0x210825 -#define APICTB 0x210825 -#define APIGOTTHARD 0x210825 -#define APIGOTTHARD2 0x210825 -#define APIJUNGFRAU 0x210825 -#define APIMYTHEN3 0x210825 -#define APIMOENCH 0x210825 + + +#define APILIB 0x210831 +#define APIRECEIVER 0x210831 +#define APIGUI 0x210819 +#define APICTB 0x210907 +#define APIGOTTHARD 0x210907 +#define APIGOTTHARD2 0x210907 +#define APIJUNGFRAU 0x210907 +#define APIMYTHEN3 0x210907 +#define APIMOENCH 0x210907 +#define APIEIGER 0x210907 diff --git a/slsSupportLib/src/ToString.cpp b/slsSupportLib/src/ToString.cpp index 6686b3256..d4dd47e2e 100644 --- a/slsSupportLib/src/ToString.cpp +++ b/slsSupportLib/src/ToString.cpp @@ -116,25 +116,25 @@ std::ostream &operator<<(std::ostream &os, std::string ToString(const slsDetectorDefs::currentSrcParameters &r) { std::ostringstream oss; - if (r.fix < -1 || r.fix > 1 || r.normal < -1 || r.normal > 1) { + if (r.fix_ < -1 || r.fix_ > 1 || r.normal_ < -1 || r.normal_ > 1) { throw sls::RuntimeError( "Invalid current source parameters. Cannot print."); } oss << '['; - if (r.enable) { + if (r.enable_) { oss << "enabled"; // [jungfrau] - if (r.fix != -1) { - oss << (r.fix == 1 ? ", fix" : ", nofix"); + if (r.fix_ != -1) { + oss << (r.fix_ == 1 ? ", fix" : ", nofix"); } // [jungfrau chip v1.1] - if (r.normal != -1) { - oss << ", " << ToStringHex(r.select, 16); - oss << (r.normal == 1 ? ", normal" : ", low"); + if (r.normal_ != -1) { + oss << ", " << ToStringHex(r.select_, 16); + oss << (r.normal_ == 1 ? ", normal" : ", low"); } // [jungfrau chip v1.0] else { - oss << ", " << r.select; + oss << ", " << r.select_; } } else { oss << "disabled"; diff --git a/slsSupportLib/src/network_utils.cpp b/slsSupportLib/src/network_utils.cpp index 2f05e948c..56507e8f1 100644 --- a/slsSupportLib/src/network_utils.cpp +++ b/slsSupportLib/src/network_utils.cpp @@ -69,6 +69,26 @@ std::string MacAddr::str() const { return to_hex(':'); } std::string MacAddr::hex() const { return to_hex(); } +std::string UdpDestination::str() const { + std::ostringstream oss; + oss << '[' << std::endl + << "entry " << entry << std::endl + << "ip " << ip << std::endl + << "mac " << mac << std::endl + << "port " << port << std::endl; + if (port2 != 0) { + oss << "port2 " << port2 << std::endl; + } + if (ip2 != 0) { + oss << "ip2 " << ip2 << std::endl; + } + if (mac2 != 0) { + oss << "mac2 " << mac2 << std::endl; + } + oss << ']'; + return oss.str(); +} + std::ostream &operator<<(std::ostream &out, const IpAddr &addr) { return out << addr.str(); } @@ -77,6 +97,10 @@ std::ostream &operator<<(std::ostream &out, const MacAddr &addr) { return out << addr.str(); } +std::ostream &operator<<(std::ostream &out, const UdpDestination &dest) { + return out << dest.str(); +} + IpAddr HostnameToIp(const char *hostname) { addrinfo hints; addrinfo *result = nullptr; diff --git a/slsSupportLib/tests/test-file_utils.cpp b/slsSupportLib/tests/test-file_utils.cpp index 254c52055..b4f71cfb9 100644 --- a/slsSupportLib/tests/test-file_utils.cpp +++ b/slsSupportLib/tests/test-file_utils.cpp @@ -9,7 +9,7 @@ TEST_CASE("Get size of empty file") { char fname[] = "temfile_XXXXXX"; std::ifstream ifs(fname); auto size = sls::getFileSize(ifs); - REQUIRE(size == 0); + REQUIRE(size <= 0); // -1 or zero } TEST_CASE("Get size of file with data") { diff --git a/slsSupportLib/tests/test-network_utils.cpp b/slsSupportLib/tests/test-network_utils.cpp index 295da4c10..a6464d2b4 100644 --- a/slsSupportLib/tests/test-network_utils.cpp +++ b/slsSupportLib/tests/test-network_utils.cpp @@ -112,4 +112,19 @@ TEST_CASE("Copy construct a MacAddr") { CHECK(addr == addr2); } + +TEST_CASE("udp dst struct basic properties"){ + static_assert(sizeof(UdpDestination) == 36); + UdpDestination dst{}; + REQUIRE(dst.entry == 0); + REQUIRE(dst.port == 0); + REQUIRE(dst.port2 == 0); + REQUIRE(dst.ip == 0); + REQUIRE(dst.ip2 == 0); + REQUIRE(dst.mac == 0); + REQUIRE(dst.mac2 == 0); + +} + + // TODO!(Erik) Look up a real hostname and verify the IP