19 #include <QTextStream>
21 #include <QMessageBox>
27 #include <QIntValidator>
28 #include <QMessageBox>
30 #include <QNetworkDatagram>
31 #include <QNetworkInterface>
33 #include "ui_udp_server.h"
41 ui->lineEditPort->setValidator(
new QIntValidator());
42 setWindowTitle(
"UDP Server");
44 connect(
ui->buttonBox, &QDialogButtonBox::accepted,
this, &QDialog::accept);
45 connect(
ui->buttonBox, &QDialogButtonBox::rejected,
this, &QDialog::reject);
49 while (
ui->layoutOptions->count() > 0)
51 auto item =
ui->layoutOptions->takeAt(0);
52 item->widget()->setParent(
nullptr);
56 Ui::UDPServerDialog*
ui;
77 QMessageBox::warning(
nullptr, tr(
"UDP Server"), tr(
"No available MessageParsers"),
89 dialog.
ui->comboBoxProtocol->addItem(it.first);
91 if (
auto widget = it.second->optionsWidget())
93 widget->setVisible(
false);
94 dialog.
ui->layoutOptions->addWidget(widget);
100 QString address_str = settings.value(
"UDP_Server::address",
"127.0.0.1").toString();
101 int port = settings.value(
"UDP_Server::port", 9870).toInt();
102 QString protocol = settings.value(
"UDP_Server::protocol").toString();
108 dialog.
ui->lineEditAddress->setText(address_str);
109 dialog.
ui->lineEditPort->setText(QString::number(port));
113 auto onComboChanged = [&](
const QString& selected_protocol) {
116 if (
auto prev_widget = parser_creator->optionsWidget())
118 prev_widget->setVisible(
false);
123 if (
auto widget = parser_creator->optionsWidget())
125 widget->setVisible(
true);
129 connect(dialog.
ui->comboBoxProtocol,
130 qOverload<const QString&>(&QComboBox::currentIndexChanged),
this,
133 dialog.
ui->comboBoxProtocol->setCurrentText(protocol);
134 onComboChanged(protocol);
136 int res = dialog.exec();
137 if (res == QDialog::Rejected)
143 address_str = dialog.
ui->lineEditAddress->text();
144 port = dialog.
ui->lineEditPort->text().toUShort(&
ok);
145 protocol = dialog.
ui->comboBoxProtocol->currentText();
150 settings.setValue(
"UDP_Server::protocol", protocol);
151 settings.setValue(
"UDP_Server::address", address_str);
152 settings.setValue(
"UDP_Server::port", port);
154 QHostAddress address(address_str);
157 success &= !address.isNull();
161 if (address.protocol() == QAbstractSocket::IPv6Protocol)
166 if (!address.isMulticast())
172 QHostAddress bind_address = address;
176 bind_address = QHostAddress::AnyIPv6;
179 QAbstractSocket::ShareAddress |
180 QAbstractSocket::ReuseAddressHint);
183 qDebug() << tr(
"Couldn't bind IPv%3 UDP socket (%1, %2)")
190 bool bound_one_interface =
false;
191 for (
const auto& interface : QNetworkInterface::allInterfaces())
193 QNetworkInterface::InterfaceFlags iflags = interface.flags();
194 if (success && interface.isValid() &&
195 !iflags.testFlag(QNetworkInterface::IsLoopBack) &&
196 iflags.testFlag(QNetworkInterface::CanMulticast) &&
197 iflags.testFlag(QNetworkInterface::IsRunning))
199 if (
_udp_socket->joinMulticastGroup(address, interface))
201 bound_one_interface =
true;
205 qDebug() << tr(
"Couldn't join IPv%4 multicast group (%1, %2) on interface %3")
208 .arg(interface.name().arg(ip_version));
212 success &= bound_one_interface;
221 qDebug() << tr(
"IPv%3 UDP listening on (%1, %2)")
228 QMessageBox::warning(
nullptr, tr(
"UDP Server"),
229 tr(
"Couldn't bind to IPv%4 UDP server at (%1, %2)")
253 QNetworkDatagram datagram =
_udp_socket->receiveDatagram();
255 using namespace std::chrono;
256 auto ts = high_resolution_clock::now().time_since_epoch();
257 double timestamp = 1e-6 * double(duration_cast<microseconds>(ts).
count());
259 QByteArray m = datagram.data();
260 MessageRef msg(
reinterpret_cast<uint8_t*
>(m.data()), m.count());
264 std::lock_guard<std::mutex> lock(
mutex());
268 catch (std::exception& err)
270 QMessageBox::warning(
nullptr, tr(
"UDP Server"),
271 tr(
"Problem parsing the message. UDP Server will be "