diff options
Diffstat (limited to 'src/OutputUHDFeedback.cpp')
-rw-r--r-- | src/OutputUHDFeedback.cpp | 287 |
1 files changed, 156 insertions, 131 deletions
diff --git a/src/OutputUHDFeedback.cpp b/src/OutputUHDFeedback.cpp index 2a99e6b..b370885 100644 --- a/src/OutputUHDFeedback.cpp +++ b/src/OutputUHDFeedback.cpp @@ -43,6 +43,7 @@ DESCRIPTION: #include <sys/socket.h> #include <errno.h> #include <poll.h> +#include <boost/date_time/posix_time/posix_time.hpp> #include "OutputUHDFeedback.h" #include "Utils.h" @@ -218,152 +219,176 @@ static ssize_t sendall(int socket, const void *buffer, size_t buflen) return buflen; } -void OutputUHDFeedback::ServeFeedbackThread() +void OutputUHDFeedback::ServeFeedback() { - set_thread_name("uhdservefeedback"); + if ((m_server_sock = socket(PF_INET, SOCK_STREAM, 0)) < 0) { + throw std::runtime_error("Can't create TCP socket"); + } + + struct sockaddr_in addr; + addr.sin_family = AF_INET; + addr.sin_port = htons(m_port); + addr.sin_addr.s_addr = htonl(INADDR_ANY); + + const int reuse = 1; + if (setsockopt(m_server_sock, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) + < 0) { + throw std::runtime_error("Can't reuse address for TCP socket"); + } + + if (bind(m_server_sock, (struct sockaddr*)&addr, sizeof(addr)) < 0) { + close(m_server_sock); + throw std::runtime_error("Can't bind TCP socket"); + } + + if (listen(m_server_sock, 1) < 0) { + close(m_server_sock); + throw std::runtime_error("Can't listen TCP socket"); + } + + etiLog.level(info) << "DPD Feedback server listening on port " << m_port; - try { - if ((m_server_sock = socket(PF_INET, SOCK_STREAM, 0)) < 0) { - throw std::runtime_error("Can't create TCP socket"); + while (m_running) { + struct sockaddr_in client; + int client_sock = accept_with_timeout(m_server_sock, 1000, &client); + + if (client_sock == -1) { + close(m_server_sock); + throw runtime_error("Could not establish new connection"); + } + else if (client_sock == -2) { + continue; } - struct sockaddr_in addr; - addr.sin_family = AF_INET; - addr.sin_port = htons(m_port); - addr.sin_addr.s_addr = htonl(INADDR_ANY); + uint8_t request_version = 0; + ssize_t read = recv(client_sock, &request_version, 1, 0); + if (!read) break; // done reading + if (read < 0) { + etiLog.level(info) << + "DPD Feedback Server Client read request version failed: " << strerror(errno); + break; + } - if (bind(m_server_sock, (struct sockaddr*)&addr, sizeof(addr)) < 0) { - throw std::runtime_error("Can't bind TCP socket"); + if (request_version != 1) { + etiLog.level(info) << "DPD Feedback Server wrong request version"; + break; } - if (listen(m_server_sock, 1) < 0) { - throw std::runtime_error("Can't listen TCP socket"); + uint32_t num_samples = 0; + read = recv(client_sock, &num_samples, 4, 0); + if (!read) break; // done reading + if (read < 0) { + etiLog.level(info) << + "DPD Feedback Server Client read num samples failed"; + break; } - etiLog.level(info) << "DPD Feedback server listening on port " << m_port; - - while (m_running) { - struct sockaddr_in client; - int client_sock = accept_with_timeout(m_server_sock, 1000, &client); - - if (client_sock == -1) { - throw runtime_error("Could not establish new connection"); - } - else if (client_sock == -2) { - continue; - } - - uint8_t request_version = 0; - ssize_t read = recv(client_sock, &request_version, 1, 0); - if (!read) break; // done reading - if (read < 0) { - etiLog.level(info) << - "DPD Feedback Server Client read request version failed: " << strerror(errno); - break; - } - - if (request_version != 1) { - etiLog.level(info) << "DPD Feedback Server wrong request version"; - break; - } - - uint32_t num_samples = 0; - read = recv(client_sock, &num_samples, 4, 0); - if (!read) break; // done reading - if (read < 0) { - etiLog.level(info) << - "DPD Feedback Server Client read num samples failed"; - break; - } - - // We are ready to issue the request now - { - boost::mutex::scoped_lock lock(burstRequest.mutex); - burstRequest.num_samples = num_samples; - burstRequest.state = BurstRequestState::SaveTransmitFrame; - - lock.unlock(); - } - - // Wait for the result to be ready + // We are ready to issue the request now + { boost::mutex::scoped_lock lock(burstRequest.mutex); - while (burstRequest.state != BurstRequestState::Acquired) { - if (not m_running) break; - burstRequest.mutex_notification.wait(lock); - } + burstRequest.num_samples = num_samples; + burstRequest.state = BurstRequestState::SaveTransmitFrame; - burstRequest.state = BurstRequestState::None; lock.unlock(); + } + + // Wait for the result to be ready + boost::mutex::scoped_lock lock(burstRequest.mutex); + while (burstRequest.state != BurstRequestState::Acquired) { + if (not m_running) break; + burstRequest.mutex_notification.wait(lock); + } + + burstRequest.state = BurstRequestState::None; + lock.unlock(); + + burstRequest.num_samples = std::min(burstRequest.num_samples, + std::min( + burstRequest.tx_samples.size() / sizeof(complexf), + burstRequest.rx_samples.size() / sizeof(complexf))); - burstRequest.num_samples = std::min(burstRequest.num_samples, - std::min( - burstRequest.tx_samples.size() / sizeof(complexf), - burstRequest.rx_samples.size() / sizeof(complexf))); - - uint32_t num_samples_32 = burstRequest.num_samples; - if (sendall(client_sock, &num_samples_32, sizeof(num_samples_32)) < 0) { - etiLog.level(info) << - "DPD Feedback Server Client send num_samples failed"; - break; - } - - if (sendall(client_sock, - &burstRequest.tx_second, - sizeof(burstRequest.tx_second)) < 0) { - etiLog.level(info) << - "DPD Feedback Server Client send tx_second failed"; - break; - } - - if (sendall(client_sock, - &burstRequest.tx_pps, - sizeof(burstRequest.tx_pps)) < 0) { - etiLog.level(info) << - "DPD Feedback Server Client send tx_pps failed"; - break; - } - - const size_t frame_bytes = burstRequest.num_samples * sizeof(complexf); - - assert(burstRequest.tx_samples.size() >= frame_bytes); - if (sendall(client_sock, - &burstRequest.tx_samples[0], - frame_bytes) < 0) { - etiLog.level(info) << - "DPD Feedback Server Client send tx_frame failed"; - break; - } - - if (sendall(client_sock, - &burstRequest.rx_second, - sizeof(burstRequest.rx_second)) < 0) { - etiLog.level(info) << - "DPD Feedback Server Client send rx_second failed"; - break; - } - - if (sendall(client_sock, - &burstRequest.rx_pps, - sizeof(burstRequest.rx_pps)) < 0) { - etiLog.level(info) << - "DPD Feedback Server Client send rx_pps failed"; - break; - } - - assert(burstRequest.rx_samples.size() >= frame_bytes); - if (sendall(client_sock, - &burstRequest.rx_samples[0], - frame_bytes) < 0) { - etiLog.level(info) << - "DPD Feedback Server Client send rx_frame failed"; - break; - } - - close(client_sock); + uint32_t num_samples_32 = burstRequest.num_samples; + if (sendall(client_sock, &num_samples_32, sizeof(num_samples_32)) < 0) { + etiLog.level(info) << + "DPD Feedback Server Client send num_samples failed"; + break; } + + if (sendall(client_sock, + &burstRequest.tx_second, + sizeof(burstRequest.tx_second)) < 0) { + etiLog.level(info) << + "DPD Feedback Server Client send tx_second failed"; + break; + } + + if (sendall(client_sock, + &burstRequest.tx_pps, + sizeof(burstRequest.tx_pps)) < 0) { + etiLog.level(info) << + "DPD Feedback Server Client send tx_pps failed"; + break; + } + + const size_t frame_bytes = burstRequest.num_samples * sizeof(complexf); + + assert(burstRequest.tx_samples.size() >= frame_bytes); + if (sendall(client_sock, + &burstRequest.tx_samples[0], + frame_bytes) < 0) { + etiLog.level(info) << + "DPD Feedback Server Client send tx_frame failed"; + break; + } + + if (sendall(client_sock, + &burstRequest.rx_second, + sizeof(burstRequest.rx_second)) < 0) { + etiLog.level(info) << + "DPD Feedback Server Client send rx_second failed"; + break; + } + + if (sendall(client_sock, + &burstRequest.rx_pps, + sizeof(burstRequest.rx_pps)) < 0) { + etiLog.level(info) << + "DPD Feedback Server Client send rx_pps failed"; + break; + } + + assert(burstRequest.rx_samples.size() >= frame_bytes); + if (sendall(client_sock, + &burstRequest.rx_samples[0], + frame_bytes) < 0) { + etiLog.level(info) << + "DPD Feedback Server Client send rx_frame failed"; + break; + } + + close(client_sock); } - catch (runtime_error &e) { - etiLog.level(error) << "DPD Feedback Server fault: " << e.what(); +} + +void OutputUHDFeedback::ServeFeedbackThread() +{ + set_thread_name("uhdservefeedback"); + + while (m_running) { + try { + ServeFeedback(); + } + catch (const runtime_error &e) { + etiLog.level(error) << "DPD Feedback Server runtime error: " << e.what(); + } + catch (const std::exception &e) { + etiLog.level(error) << "DPD Feedback Server exception: " << e.what(); + } + catch (...) { + etiLog.level(error) << "DPD Feedback Server unknown exception!"; + } + + boost::this_thread::sleep(boost::posix_time::seconds(5)); } m_running = false; |