1. Ctb transceiver ro (#773)

*  transceiverenable, tsamples, romode for tranceiver and digital_transceiver

* 202 spec instr only for transceiver mode

* removed check for empty in trans readout and clean memory before reading from fifo

* ctb read fifo strobe for all after reading all channels, adding 1us after selecting channel, changing fw date

* updated 10gb transceiver enable

----
* added transceiver (tsamples, romode(transceiver, digital_transceiver), transceiverenable (mask)

* clean memory before reading from fifo (for analog and digital as well)

* read fifo then read strobe (also corresp fw) fixes number of reads (also for analg and digital)-> increases all pipelines by 1

* fixed bug in rearranging digital data in receiver

* fixed bug in streaming size of data after rearranging

* fixed bug in setbit, clearbit,and getbit

* status checks fifo before returning idle (transmitting if data in fifo if transceiver more enabled)

* soem matterhorn specifics that will need to be put into pattern in a month or two. this is temporary.

* NOTE: breaking api. rxParameters struct has transceiverenabel and tsamples given from det to receiver
This commit is contained in:
2023-07-14 16:29:21 +02:00
committed by GitHub
parent a56be25500
commit c628ae2192
30 changed files with 1118 additions and 238 deletions

View File

@ -206,6 +206,8 @@ int setADCEnableMask(uint32_t mask);
uint32_t getADCEnableMask();
void setADCEnableMask_10G(uint32_t mask);
uint32_t getADCEnableMask_10G();
int setTransceiverEnableMask(uint32_t mask);
uint32_t getTransceiverEnableMask();
void setADCInvertRegister(uint32_t val);
uint32_t getADCInvertRegister();
#endif
@ -287,6 +289,8 @@ int getNumAnalogSamples();
#ifdef CHIPTESTBOARDD
int setNumDigitalSamples(int val);
int getNumDigitalSamples();
int setNumTransceiverSamples(int val);
int getNumTransceiverSamples();
#endif
#ifdef MYTHEN3D
void setCounterMask(uint32_t arg);
@ -677,7 +681,7 @@ int softwareTrigger();
#if defined(EIGERD) || defined(JUNGFRAUD) || defined(MOENCHD)
int softwareTrigger(int block);
#endif
#if defined(EIGERD) || defined(MYTHEN3D)
#if defined(EIGERD) || defined(MYTHEN3D) || defined(CHIPTESTBOARDD)
int startReadOut();
#endif
enum runStatus getRunStatus();
@ -690,7 +694,7 @@ void waitForAcquisitionEnd();
int validateUDPSocket();
void readandSendUDPFrames();
void unsetFifoReadStrobes();
void readSample(int ns);
int readSample(int ns);
uint32_t checkDataInFifo();
int checkFifoForEndOfAcquisition();
int readFrameFromFifo();

View File

@ -315,3 +315,7 @@ int get_frontend_firmware_version(int);
int get_bit(int);
int set_bit(int);
int clear_bit(int);
int get_num_transceiver_samples(int);
int set_num_transceiver_samples(int);
int get_transceiver_enable(int);
int set_transceiver_enable(int);

View File

@ -21,11 +21,14 @@ extern const enum detectorType myDetectorType;
extern int analogDataBytes;
extern int digitalDataBytes;
extern int transceiverDataBytes;
extern char *analogData;
extern char *digitalData;
extern char *transceiverData;
int analogOffset = 0;
int digitalOffset = 0;
int transceiverOffset = 0;
uint32_t udpPacketNumber = 0;
uint64_t udpFrameNumber = 0;
@ -51,27 +54,30 @@ void createUDPPacketHeader(char *buffer, uint16_t id) {
// reset offset
analogOffset = 0;
digitalOffset = 0;
transceiverOffset = 0;
// reset frame number
udpFrameNumber = 0;
}
int fillUDPPacket(char *buffer) {
LOG(logDEBUG2,
("Analog (databytes:%d, offset:%d)\n Digital (databytes:%d "
"offset:%d)\n",
analogDataBytes, analogOffset, digitalDataBytes, digitalOffset));
LOG(logDEBUG2, ("Analog (databytes:%d, offset:%d)\n Digital (databytes:%d "
"offset:%d)\n\n Transceiver (databytes:%d offset:%d)\n",
analogDataBytes, analogOffset, digitalDataBytes,
digitalOffset, transceiverDataBytes, transceiverOffset));
// reached end of data for one frame
if (analogOffset >= analogDataBytes && digitalOffset >= digitalDataBytes) {
if (analogOffset >= analogDataBytes && digitalOffset >= digitalDataBytes &&
transceiverOffset >= transceiverDataBytes) {
// reset offset
analogOffset = 0;
digitalOffset = 0;
transceiverOffset = 0;
return 0;
}
sls_detector_header *header = (sls_detector_header *)(buffer);
// update frame number, starts at 1 (reset packet number)
if (analogOffset == 0 && digitalOffset == 0) {
if (analogOffset == 0 && digitalOffset == 0 && transceiverOffset == 0) {
++udpFrameNumber;
header->frameNumber = udpFrameNumber;
udpPacketNumber = -1;
@ -117,10 +123,28 @@ int fillUDPPacket(char *buffer) {
freeBytes -= digitalBytes;
}
// transceiver data
int transceiverBytes = 0;
if (freeBytes && transceiverOffset < transceiverDataBytes) {
// bytes to copy
transceiverBytes =
((transceiverOffset + freeBytes) <= transceiverDataBytes)
? freeBytes
: (transceiverDataBytes - transceiverOffset);
// copy
memcpy(buffer + sizeof(sls_detector_header) + analogBytes +
digitalBytes,
transceiverData + transceiverOffset, transceiverBytes);
// increment offset
transceiverOffset += transceiverBytes;
// decrement free bytes
freeBytes -= transceiverBytes;
}
// pad data
if (freeBytes) {
memset(buffer + sizeof(sls_detector_header) + analogBytes +
digitalBytes,
digitalBytes + transceiverBytes,
0, freeBytes);
LOG(logDEBUG1, ("Padding %d bytes for fnum:%lld pnum:%d\n", freeBytes,
(long long int)udpFrameNumber, udpPacketNumber));

View File

@ -478,7 +478,10 @@ void function_table() {
flist[F_GET_BIT] = &get_bit;
flist[F_SET_BIT] = &set_bit;
flist[F_CLEAR_BIT] = &clear_bit;
flist[F_GET_NUM_TRANSCEIVER_SAMPLES] = &get_num_transceiver_samples;
flist[F_SET_NUM_TRANSCEIVER_SAMPLES] = &set_num_transceiver_samples;
flist[F_GET_TRANSCEIVER_ENABLE_MASK] = &get_transceiver_enable;
flist[F_SET_TRANSCEIVER_ENABLE_MASK] = &set_transceiver_enable;
// check
if (NUM_DET_FUNCTIONS >= RECEIVER_ENUM_START) {
LOG(logERROR, ("The last detector function enum has reached its "
@ -1876,7 +1879,8 @@ int acquire(int blocking, int file_des) {
getNumAnalogSamples());
LOG(logERROR, (mess));
} else if ((getReadoutMode() == ANALOG_AND_DIGITAL ||
getReadoutMode() == DIGITAL_ONLY) &&
getReadoutMode() == DIGITAL_ONLY ||
getReadoutMode() == DIGITAL_AND_TRANSCEIVER) &&
(getNumDigitalSamples() <= 0)) {
ret = FAIL;
sprintf(mess,
@ -1884,6 +1888,16 @@ int acquire(int blocking, int file_des) {
"samples: %d.\n",
getNumDigitalSamples());
LOG(logERROR, (mess));
} else if ((getReadoutMode() == TRANSCEIVER_ONLY ||
getReadoutMode() == DIGITAL_AND_TRANSCEIVER) &&
(getNumTransceiverSamples() <= 0)) {
ret = FAIL;
sprintf(
mess,
"Could not start acquisition. Invalid number of transceiver "
"samples: %d.\n",
getNumTransceiverSamples());
LOG(logERROR, (mess));
} else
#endif
#ifdef EIGERD
@ -4275,28 +4289,19 @@ int set_adc_enable_mask(int file_des) {
#else
// only set
if (Server_VerifyLock() == OK) {
if (arg == 0u) {
ret = FAIL;
sprintf(mess,
"Not allowed to set adc mask of 0 due to data readout. \n");
ret = setADCEnableMask(arg);
if (ret == FAIL) {
sprintf(mess, "Could not set 1Gb ADC Enable mask to 0x%x.\n", arg);
LOG(logERROR, (mess));
} else {
ret = setADCEnableMask(arg);
if (ret == FAIL) {
sprintf(mess, "Could not set 1Gb ADC Enable mask to 0x%x.\n",
arg);
LOG(logERROR, (mess));
} else {
uint32_t retval = getADCEnableMask();
if (arg != retval) {
ret = FAIL;
sprintf(
mess,
uint32_t retval = getADCEnableMask();
if (arg != retval) {
ret = FAIL;
sprintf(mess,
"Could not set 1Gb ADC Enable mask. Set 0x%x, but read "
"0x%x\n",
arg, retval);
LOG(logERROR, (mess));
}
LOG(logERROR, (mess));
}
}
}
@ -5662,6 +5667,8 @@ int set_readout_mode(int file_des) {
case ANALOG_ONLY:
case DIGITAL_ONLY:
case ANALOG_AND_DIGITAL:
case TRANSCEIVER_ONLY:
case DIGITAL_AND_TRANSCEIVER:
break;
default:
modeNotImplemented("Readout mode", (int)arg);
@ -5946,7 +5953,7 @@ int get_clock_phase(int file_des) {
if (receiveData(file_des, args, sizeof(args), INT32) < 0)
return printSocketReadError();
LOG(logINFOBLUE, ("Getting clock (%d) phase %s \n", args[0],
LOG(logDEBUG1, ("Getting clock (%d) phase %s \n", args[0],
(args[1] == 0 ? "" : "in degrees")));
#if !defined(CHIPTESTBOARDD) && !defined(JUNGFRAUD) && !defined(MOENCHD) && \
@ -5972,7 +5979,7 @@ int get_clock_phase(int file_des) {
#if defined(GOTTHARD2D) || defined(MYTHEN3D)
if (ind < NUM_CLOCKS) {
c = (enum CLKINDEX)ind;
LOG(logINFOBLUE, ("NUMclocks:%d c:%d\n", NUM_CLOCKS, c));
LOG(logDEBUG1, ("NUMclocks:%d c:%d\n", NUM_CLOCKS, c));
break;
}
#endif
@ -7384,6 +7391,26 @@ int get_receiver_parameters(int file_des) {
if (n < 0)
return printSocketReadError();
n += sendData(file_des, &i64, sizeof(i64), INT64);
if (n < 0)
return printSocketReadError();
// transceiver samples
#ifdef CHIPTESTBOARDD
i32 = getNumTransceiverSamples();
#else
i32 = 0;
#endif
n += sendData(file_des, &i32, sizeof(i32), INT32);
if (n < 0)
return printSocketReadError();
// transceiver mask
#if defined(CHIPTESTBOARDD)
u32 = getTransceiverEnableMask();
#else
u32 = 0;
#endif
n += sendData(file_des, &u32, sizeof(u32), INT32);
if (n < 0)
return printSocketReadError();
@ -8210,7 +8237,7 @@ int get_bursts_left(int file_des) {
int start_readout(int file_des) {
ret = OK;
memset(mess, 0, sizeof(mess));
#ifndef MYTHEN3D
#if !defined(MYTHEN3D) && !defined(CHIPTESTBOARDD)
functionNotImplemented();
#else
if (Server_VerifyLock() == OK) {
@ -8241,6 +8268,25 @@ int start_readout(int file_des) {
#endif
LOG(logERROR, (mess));
}
// only 1g real ctb needs to read from fifo
// to avoid blocking, in another thread
#if defined(CHIPTESTBOARDD) && !defined(VIRTUAL)
if (!enableTenGigabitEthernet(-1)) {
ret = validateUDPSocket();
if (ret == FAIL) {
strcpy(mess, "UDP socket not created!\n");
LOG(logERROR, (mess));
} else {
if (pthread_create(&pthread_tid_ctb_1g, NULL,
&start_reading_and_sending_udp_frames,
NULL)) {
ret = FAIL;
strcpy(mess, "Could not start read frames thread!\n");
LOG(logERROR, (mess));
}
}
}
#endif
}
}
#endif
@ -10401,34 +10447,138 @@ int get_bit(int file_des) {
int nBit = (int)args[1];
LOG(logDEBUG1, ("Getting bit %d of reg 0x%x\n", nBit, addr));
// only set
if (Server_VerifyLock() == OK) {
if (nBit < 0 || nBit > 31) {
ret = FAIL;
sprintf(
mess,
if (nBit < 0 || nBit > 31) {
ret = FAIL;
sprintf(mess,
"Could not get bit. Bit nr %d out of range. Must be 0-31\n",
nBit);
LOG(logERROR, (mess));
} else {
LOG(logERROR, (mess));
} else {
#ifdef EIGERD
ret = getBit(addr, nBit, &retval);
LOG(logDEBUG1, ("retval: %d\n", retval));
if (ret == FAIL) {
ret = getBit(addr, nBit, &retval);
LOG(logDEBUG1, ("retval: %d\n", retval));
if (ret == FAIL) {
sprintf(mess, "Could not get bit %d.\n", nBit);
LOG(logERROR, (mess));
}
#else
#ifdef GOTTHARDD
retval = readRegister16And32(addr);
uint32_t regval = readRegister16And32(addr);
#else
retval = readRegister(addr);
uint32_t regval = readRegister(addr);
#endif
LOG(logDEBUG1, ("retval: %d\n", retval));
if (retval & (1 << nBit)) {
ret = FAIL;
retval = (regval & (1 << nBit)) >> nBit;
LOG(logDEBUG1, ("regval: 0x%x bit value:0%d\n", regval, retval));
#endif
sprintf(mess, "Could not get bit %d.\n", nBit);
}
return Server_SendResult(file_des, INT32, &retval, sizeof(retval));
}
int get_num_transceiver_samples(int file_des) {
ret = OK;
memset(mess, 0, sizeof(mess));
int retval = -1;
#if !defined(CHIPTESTBOARDD)
functionNotImplemented();
#else
// get only
retval = getNumTransceiverSamples();
LOG(logDEBUG1, ("retval num transceiver samples %d\n", retval));
#endif
return Server_SendResult(file_des, INT32, &retval, sizeof(retval));
}
int set_num_transceiver_samples(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 transceiver samples %d\n", arg));
#if !defined(CHIPTESTBOARDD)
functionNotImplemented();
#else
// only set
if (Server_VerifyLock() == OK) {
ret = setNumTransceiverSamples(arg);
if (ret == FAIL) {
sprintf(
mess,
"Could not set number of transceiver samples to %d. Could not "
"allocate RAM\n",
arg);
LOG(logERROR, (mess));
} else {
int retval = getNumTransceiverSamples();
LOG(logDEBUG1, ("retval num transceiver samples %d\n", retval));
validate(&ret, mess, arg, retval,
"set number of transceiver samples", DEC);
}
}
#endif
return Server_SendResult(file_des, INT32, NULL, 0);
}
int set_transceiver_enable(int file_des) {
ret = OK;
memset(mess, 0, sizeof(mess));
uint32_t arg = 0;
if (receiveData(file_des, &arg, sizeof(arg), INT32) < 0)
return printSocketReadError();
LOG(logDEBUG1, ("Setting Transceiver Enable Mask to %u\n", arg));
#if (!defined(CHIPTESTBOARDD))
functionNotImplemented();
#else
// only set
if (Server_VerifyLock() == OK) {
if (arg > MAX_TRANSCEIVER_MASK) {
ret = FAIL;
sprintf(mess, "Invalid Transceiver Mask. Max: 0x%x\n",
MAX_TRANSCEIVER_MASK);
LOG(logERROR, (mess));
} else {
ret = setTransceiverEnableMask(arg);
if (ret == FAIL) {
sprintf(mess,
"Could not set Transceiver Enable mask to 0x%x.\n",
arg);
LOG(logERROR, (mess));
} else {
uint32_t retval = getTransceiverEnableMask();
if (arg != retval) {
ret = FAIL;
sprintf(mess,
"Could not set Transceiver Enable mask. Set 0x%x, "
"but read "
"0x%x\n",
arg, retval);
LOG(logERROR, (mess));
}
}
}
}
#endif
return Server_SendResult(file_des, INT32, NULL, 0);
}
int get_transceiver_enable(int file_des) {
ret = OK;
memset(mess, 0, sizeof(mess));
uint32_t retval = -1;
LOG(logDEBUG1, ("Getting Transceiver Enable Mask \n"));
#if (!defined(CHIPTESTBOARDD))
functionNotImplemented();
#else
// get
retval = getTransceiverEnableMask();
LOG(logDEBUG1, ("Transceiver Enable Mask retval: %u\n", retval));
#endif
return Server_SendResult(file_des, INT32, &retval, sizeof(retval));
}