| 1745 | while (received) |
| 1746 | { |
| 1747 | msg = received; |
| 1748 | received = msg->next; |
| 1749 | msg->next = nullptr; |
| 1750 | leaveRcv(); |
| 1751 | |
| 1752 | // Intercept VoN data packets before they reach the game message handler |
| 1753 | if (vonIsDataPacket(msg->getData(), msg->getLength())) |
| 1754 | { |
| 1755 | auto* c = _vonSystem.client(); |
| 1756 | if (c && msg->getLength() >= VoNDataPacket::HEADER_SIZE) |
| 1757 | { |
| 1758 | VoNDataPacket hdr; |
| 1759 | std::memcpy(&hdr, msg->getData(), VoNDataPacket::HEADER_SIZE); |
| 1760 | c->onDataPacket(hdr, reinterpret_cast<const uint8_t*>(msg->getData()) + VoNDataPacket::HEADER_SIZE); |
| 1761 | _vonSpeakerChannels[hdr.channel] = hdr.chatChan; |
| 1762 | LOG_TRACE(Network, "VoN: rx voice pkt ch={} origin={} size={}B", hdr.channel, hdr.origin, hdr.size); |
| 1763 | |
| 1764 | // Auto-create speaker if we don't have one for this sender |
| 1765 | auto& spk = _vonSpeakers[hdr.channel]; |
| 1766 | if (!spk) |
| 1767 | { |
| 1768 | spk = std::make_unique<VoNSpeaker>(); |
| 1769 | spk->init(); |
| 1770 | LOG_INFO(Network, "VoN: auto-created speaker for channel {}", hdr.channel); |
| 1771 | } |
| 1772 | spk->setChannel(hdr.chatChan); |
| 1773 | } |
| 1774 | } |
| 1775 | else |
| 1776 | { |
| 1777 | (*callback)((char*)msg->getData(), msg->getLength(), context); |
| 1778 | } |
| 1779 | |
| 1780 | enterRcv(); |
| 1781 | } |
| 1782 | leaveRcv(); |
| 1783 | |
| 1784 | // Drive VoN client: capture → encode → send via packet sink |
| 1785 | if (auto* c = _vonSystem.client()) |
| 1786 | { |
| 1787 | c->update(); |
| 1788 | PumpVoiceSpeakers(); |
| 1789 | } |
| 1790 | } |
| 1791 | |
| 1792 | void NetClient::insertReceived(NetMessage* msg) |
| 1793 | // must be called inside enterRcv() |
no test coverage detected