Использование протокола связи FTDI D2xx и Thorlabs APT приводит к задержкам в Linux

Я пытаюсь установить связь с контроллерами Thorlabs TDC001 (сервоконтроллер apt-dc) с помощью драйвера FTDI D2xx в Linux. Однако, когда я посылаю команды записи, возникают большие задержки (1-2 секунды) до тех пор, пока команда не будет фактически выполнена на TDC001.
В частности, это можно наблюдать, когда подключенный линейный каскад движется и отправляется новая команда положения. Требуется 1-2 секунды, пока сцена фактически не изменит свое направление. Кроме того, если я запрашиваю DCSTATUSUPDATE (который дает положение и скорость), а затем считываю очередь FTDI, я не получаю правильные данные. Только если я жду 1 секунду между запросом и чтением, я получаю (правильные) данные, но для прошлого. Я добавил код C ++ для этого случая.
Мне нужны живые данные и более быстрое выполнение команд записи для управления с обратной связью.

Я не уверен, если проблема на стороне Thorlabs или FTDI. Все работает, кроме больших задержек. Есть и другие команды, например MOVE_STOP, которые отвечают сразу. Кроме того, если я отправляю новую команду положения сразу после окончания поиска, она выполняется немедленно.
Всякий раз, когда я запрашиваю FT_GetStatus, в очереди Tx или Rx больше ничего нет, кроме 20 байтов в Rx для DCSTATUSUPDATE.

Ссылки на протоколы связи D2XX и APT можно найти здесь:

Руководство программиста FTDI

Коммуникационный протокол Thorlabs APT

Функция инициализации:

bool CommunicationFunctions::initializeKeyHandle(string serialnumber){
//INITIALIZATION//
/*
* This function initializes the TDC motor controller and finds its corresponding keyhandle.
*/
keyHandle = NULL;

// To open the device, the vendor and product ID must be set correctly
ftStatus = FT_SetVIDPID(0x403,0xfaf0);
}

//Open device:
const char* tmp = serialnumber.c_str();
int numAttempts=0;
while (keyHandle ==0){
ftStatus = FT_OpenEx(const_cast<char*>(tmp),FT_OPEN_BY_SERIAL_NUMBER, &keyHandle);
if (numAttempts++>20){
cerr << "Device Could Not Be Opened";
return false;
}
}

// Set baud rate to 115200
ftStatus = FT_SetBaudRate(keyHandle,115200);

// 8 data bits, 1 stop bit, no parity
ftStatus = FT_SetDataCharacteristics(keyHandle, FT_BITS_8, FT_STOP_BITS_1, FT_PARITY_NONE);

// Pre purge dwell 50ms.
usleep(50);

// Purge the device.
ftStatus = FT_Purge(keyHandle, FT_PURGE_RX | FT_PURGE_TX);

// Post purge dwell 50ms.
usleep(50);

// Reset device.
ftStatus = FT_ResetDevice(keyHandle);

// Set flow control to RTS/CTS.
ftStatus = FT_SetFlowControl(keyHandle, FT_FLOW_RTS_CTS, 0, 0);

// Set RTS.
ftStatus = FT_SetRts(keyHandle);

return true;
}

Как я зачитываю свои данные:

bool CommunicationFunctions::read_tdc(int32_t* position, uint16_t* velocity){
uint8_t *RxBuffer = new uint8_t[256]();
DWORD RxBytes;
DWORD BytesReceived = 0;

// Manually request status update:
uint8_t req_statusupdate[6] = {0x90,0x04,0x01,0x00,0x50,0x01};
ftStatus = FT_Write(keyHandle, req_statusupdate, (DWORD)6, &written);
if(ftStatus != FT_OK){
cerr << "Command could not be transmitted: Request status update" << endl;
return false;
}

//  sleep(1); //**this sleep() would lead to right result, but I don't want this delay**

// Get number of bytes in queue of TDC001
FT_GetQueueStatus(keyHandle,&RxBytes);

// Check if there are bytes in queue before reading them, otherwise do
// not read anything in
if(RxBytes>0){
ftStatus=FT_Read(keyHandle,RxBuffer,RxBytes,&BytesReceived);
if(ftStatus != FT_OK){
cerr << "Read device failed!" << endl;
return false;
}
}

// Check if enough bytes are received, i.e. if signal is right
if(!(BytesReceived >= 6)){
cerr << "Error in bytes received" << endl;
return false;
}

// Look for correct message in RxBuffer and read out velocity and position
getPosVel(position,velocity,RxBuffer);

// Delete receive buffer
delete[] RxBuffer;
RxBuffer = NULL;

return true;
}

Если я использую функцию read_tdc после возврата в исходное положение и при перемещении в абсолютное положение, я просто получаю сообщение «Завершение возврата в исходное положение» с первой попытки. Когда я снова пытаюсь прочитать read_tdc, я получаю старое значение (вероятно, предыдущее). Я не понимаю, что здесь происходит. Почему эти старые данные даже остаются в очереди (задержка составляет 10 мс). Кто-нибудь может помочь мне получить более быстрые ответы и реакции?

1

Решение

Задача ещё не решена.

Другие решения

Других решений пока нет …