mirror of
https://github.com/wpilibsuite/allwpilib
synced 2026-07-02 02:51:42 +00:00
[wpinet] Move network portions of wpiutil into new wpinet library (#4077)
This commit is contained in:
86
wpinet/src/main/native/macOS/MulticastServiceAnnouncer.cpp
Normal file
86
wpinet/src/main/native/macOS/MulticastServiceAnnouncer.cpp
Normal file
@@ -0,0 +1,86 @@
|
||||
// Copyright (c) FIRST and other WPILib contributors.
|
||||
// Open Source Software; you can modify and/or share it under the terms of
|
||||
// the WPILib BSD license file in the root directory of this project.
|
||||
|
||||
#include "wpinet/MulticastServiceAnnouncer.h"
|
||||
|
||||
#include <wpi/SmallString.h>
|
||||
|
||||
#include "dns_sd.h"
|
||||
|
||||
using namespace wpi;
|
||||
|
||||
struct MulticastServiceAnnouncer::Impl {
|
||||
std::string serviceName;
|
||||
std::string serviceType;
|
||||
int port;
|
||||
DNSServiceRef serviceRef{nullptr};
|
||||
TXTRecordRef txtRecord;
|
||||
|
||||
Impl() { TXTRecordCreate(&txtRecord, 0, nullptr); }
|
||||
|
||||
~Impl() noexcept { TXTRecordDeallocate(&txtRecord); }
|
||||
};
|
||||
|
||||
MulticastServiceAnnouncer::MulticastServiceAnnouncer(
|
||||
std::string_view serviceName, std::string_view serviceType, int port,
|
||||
wpi::span<const std::pair<std::string, std::string>> txt) {
|
||||
pImpl = std::make_unique<Impl>();
|
||||
pImpl->serviceName = serviceName;
|
||||
pImpl->serviceType = serviceType;
|
||||
pImpl->port = port;
|
||||
|
||||
for (auto&& i : txt) {
|
||||
TXTRecordSetValue(&pImpl->txtRecord, i.first.c_str(), i.second.length(),
|
||||
i.second.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
MulticastServiceAnnouncer::MulticastServiceAnnouncer(
|
||||
std::string_view serviceName, std::string_view serviceType, int port,
|
||||
wpi::span<const std::pair<std::string_view, std::string_view>> txt) {
|
||||
pImpl = std::make_unique<Impl>();
|
||||
pImpl->serviceName = serviceName;
|
||||
pImpl->serviceType = serviceType;
|
||||
pImpl->port = port;
|
||||
|
||||
wpi::SmallString<64> key;
|
||||
|
||||
for (auto&& i : txt) {
|
||||
key.clear();
|
||||
key.append(i.first);
|
||||
key.emplace_back('\0');
|
||||
|
||||
TXTRecordSetValue(&pImpl->txtRecord, key.data(), i.second.length(),
|
||||
i.second.data());
|
||||
}
|
||||
}
|
||||
|
||||
MulticastServiceAnnouncer::~MulticastServiceAnnouncer() noexcept {
|
||||
Stop();
|
||||
}
|
||||
|
||||
bool MulticastServiceAnnouncer::HasImplementation() const {
|
||||
return true;
|
||||
}
|
||||
|
||||
void MulticastServiceAnnouncer::Start() {
|
||||
if (pImpl->serviceRef) {
|
||||
return;
|
||||
}
|
||||
|
||||
uint16_t len = TXTRecordGetLength(&pImpl->txtRecord);
|
||||
const void* ptr = TXTRecordGetBytesPtr(&pImpl->txtRecord);
|
||||
|
||||
(void)DNSServiceRegister(&pImpl->serviceRef, 0, 0, pImpl->serviceName.c_str(),
|
||||
pImpl->serviceType.c_str(), "local", nullptr,
|
||||
htons(pImpl->port), len, ptr, nullptr, nullptr);
|
||||
}
|
||||
|
||||
void MulticastServiceAnnouncer::Stop() {
|
||||
if (!pImpl->serviceRef) {
|
||||
return;
|
||||
}
|
||||
DNSServiceRefDeallocate(pImpl->serviceRef);
|
||||
pImpl->serviceRef = nullptr;
|
||||
}
|
||||
Reference in New Issue
Block a user