Skip to content

Commit

Permalink
audio isnt being heard, dont know why yet
Browse files Browse the repository at this point in the history
  • Loading branch information
braindigitalis committed Nov 25, 2024
1 parent 8889aa9 commit a548c2c
Show file tree
Hide file tree
Showing 10 changed files with 96 additions and 124 deletions.
63 changes: 28 additions & 35 deletions include/dpp/discordvoiceclient.h
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@
#include <dpp/cluster.h>
#include <dpp/discordevents.h>
#include <dpp/socket.h>
#include <dpp/socketengine.h>
#include <queue>
#include <thread>
#include <deque>
Expand Down Expand Up @@ -267,16 +268,6 @@ class DPP_EXPORT discord_voice_client : public websocket_client
*/
std::deque<std::string> message_queue;

/**
* @brief Thread this connection is executing on
*/
std::thread* runner;

/**
* @brief Run shard loop under a thread
*/
void thread_run();

/**
* @brief Last connect time of voice session
*/
Expand Down Expand Up @@ -446,6 +437,16 @@ class DPP_EXPORT discord_voice_client : public websocket_client
*/
bool sent_stop_frames;

/**
* @brief Number of times we have tried to reconnect in the last few seconds
*/
size_t times_looped{0};

/**
* @brief Last time we reconnected
*/
time_t last_loop_time{0};

#ifdef HAVE_VOICE
/**
* @brief libopus encoder
Expand Down Expand Up @@ -623,33 +624,15 @@ class DPP_EXPORT discord_voice_client : public websocket_client
int udp_recv(char* data, size_t max_length);

/**
* @brief This hooks the ssl_client, returning the file
* descriptor if we want to send buffered data, or
* -1 if there is nothing to send
*
* @return int file descriptor or -1
*/
dpp::socket want_write();

/**
* @brief This hooks the ssl_client, returning the file
* descriptor if we want to receive buffered data, or
* -1 if we are not wanting to receive
*
* @return int file descriptor or -1
*/
dpp::socket want_read();

/**
* @brief Called by ssl_client when the socket is ready
* @brief Called by socketengine when the socket is ready
* for writing, at this point we pick the head item off
* the buffer and send it. So long as it doesn't error
* completely, we pop it off the head of the queue.
*/
void write_ready();

/**
* @brief Called by ssl_client when there is data to be
* @brief Called by socketengine when there is data to be
* read. At this point we insert that data into the
* input queue.
* @throw dpp::voice_exception if voice support is not compiled into D++
Expand Down Expand Up @@ -710,6 +693,16 @@ class DPP_EXPORT discord_voice_client : public websocket_client
*/
void update_ratchets(bool force = false);

/**
* @brief Called in constructor and on reconnection of websocket
*/
void setup();

/**
* @brief Events for UDP Socket IO
*/
dpp::socket_events udp_events;

public:

/**
Expand Down Expand Up @@ -747,11 +740,6 @@ class DPP_EXPORT discord_voice_client : public websocket_client
*/
time_t last_heartbeat;

/**
* @brief Thread ID
*/
std::thread::native_handle_type thread_id;

/**
* @brief Discord voice session token
*/
Expand Down Expand Up @@ -1269,6 +1257,11 @@ class DPP_EXPORT discord_voice_client : public websocket_client
* @param rmap Roster map
*/
void process_mls_group_rosters(const std::map<uint64_t, std::vector<uint8_t>>& rmap);

/**
* @brief Called on websocket disconnection
*/
void on_disconnect();
};

}
Expand Down
4 changes: 4 additions & 0 deletions include/dpp/socketengine.h
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,10 @@ struct DPP_EXPORT socket_events {
socket_events(dpp::socket socket_fd, uint8_t _flags, const socket_read_event& read_event, const socket_write_event& write_event = {}, const socket_error_event& error_event = {})
: fd(socket_fd), flags(_flags), on_read(read_event), on_write(write_event), on_error(error_event) { }

/**
* @brief Default constructor
*/
socket_events() = default;
};

/**
Expand Down
2 changes: 1 addition & 1 deletion src/davetest/dave.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ int main() {
dave_test.on_guild_create([&](const dpp::guild_create_t & event) {
if (event.created->id == TEST_GUILD_ID) {
dpp::discord_client* s = dave_test.get_shard(0);
bool muted = false, deaf = false, enable_dave = true;
bool muted = false, deaf = false, enable_dave = false;
s->connect_voice(TEST_GUILD_ID, TEST_VC_ID, muted, deaf, enable_dave);
}
});
Expand Down
9 changes: 3 additions & 6 deletions src/dpp/voice/enabled/cleanup.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -33,12 +33,6 @@ namespace dpp {

void discord_voice_client::cleanup()
{
if (runner) {
this->terminating = true;
runner->join();
delete runner;
runner = nullptr;
}
if (encoder) {
opus_encoder_destroy(encoder);
encoder = nullptr;
Expand All @@ -55,6 +49,9 @@ void discord_voice_client::cleanup()
voice_courier_shared_state.signal_iteration.notify_one();
voice_courier.join();
}
if (fd != INVALID_SOCKET) {
owner->socketengine->delete_socket(fd);
}
}

}
8 changes: 7 additions & 1 deletion src/dpp/voice/enabled/constructor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,13 +34,14 @@ namespace dpp {

discord_voice_client::discord_voice_client(dpp::cluster* _cluster, snowflake _channel_id, snowflake _server_id, const std::string &_token, const std::string &_session_id, const std::string &_host, bool enable_dave)
: websocket_client(_cluster, _host.substr(0, _host.find(':')), _host.substr(_host.find(':') + 1, _host.length()), "/?v=" + std::to_string(voice_protocol_version), OP_TEXT),
runner(nullptr),
connect_time(0),
mixer(std::make_unique<audio_mixer>()),
port(0),
ssrc(0),
timescale(1000000),
paused(false),
sent_stop_frames(false),
last_loop_time(time(nullptr)),
encoder(nullptr),
repacketizer(nullptr),
fd(INVALID_SOCKET),
Expand All @@ -60,6 +61,11 @@ discord_voice_client::discord_voice_client(dpp::cluster* _cluster, snowflake _ch
sessionid(_session_id),
server_id(_server_id),
channel_id(_channel_id)
{
setup();
}

void discord_voice_client::setup()
{
int opusError = 0;
encoder = opus_encoder_create(opus_sample_rate_hz, opus_channel_count, OPUS_APPLICATION_VOIP, &opusError);
Expand Down
15 changes: 11 additions & 4 deletions src/dpp/voice/enabled/handle_frame.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -461,10 +461,17 @@ bool discord_voice_client::handle_frame(const std::string &data, ws_opcode opcod

/* Hook poll() in the ssl_client to add a new file descriptor */
this->fd = newfd;
this->custom_writeable_fd = [this] { return want_write(); };
this->custom_readable_fd = [this] { return want_read(); };
this->custom_writeable_ready = [this] { write_ready(); };
this->custom_readable_ready = [this] { read_ready(); };

udp_events = dpp::socket_events(
fd,
WANT_READ | WANT_WRITE | WANT_ERROR,
[this](socket fd, const struct socket_events &e) { read_ready(); },
[this](socket fd, const struct socket_events &e) { write_ready(); },
[this](socket fd, const struct socket_events &e, int error_code) {
this->close();
}
);
owner->socketengine->register_socket(udp_events);

int bound_port = address_t().get_port(this->fd);
this->write(json({
Expand Down
18 changes: 4 additions & 14 deletions src/dpp/voice/enabled/read_write.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,20 +28,6 @@

namespace dpp {

dpp::socket discord_voice_client::want_write() {
std::lock_guard<std::mutex> lock(this->stream_mutex);
if (!this->sent_stop_frames && !outbuf.empty()) {
return fd;
}
return INVALID_SOCKET;

}

dpp::socket discord_voice_client::want_read() {
return fd;
}


void discord_voice_client::send(const char* packet, size_t len, uint64_t duration, bool send_now) {
if (!send_now) [[likely]] {
voice_out_packet frame;
Expand All @@ -50,6 +36,10 @@ void discord_voice_client::send(const char* packet, size_t len, uint64_t duratio

std::lock_guard<std::mutex> lock(this->stream_mutex);
outbuf.emplace_back(frame);
if (!this->sent_stop_frames) {
udp_events.flags = WANT_READ | WANT_WRITE | WANT_ERROR;
owner->socketengine->update_socket(udp_events);
}
} else [[unlikely]] {
this->udp_send(packet, len);
}
Expand Down
79 changes: 30 additions & 49 deletions src/dpp/voice/enabled/thread.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@
*
************************************************************************************/

#include <string_view>
#include <dpp/exception.h>
#include <dpp/isa_detection.h>
#include <dpp/discordvoiceclient.h>
Expand All @@ -29,60 +28,42 @@

namespace dpp {

void discord_voice_client::thread_run()
{
utility::set_thread_name(std::string("vc/") + std::to_string(server_id));
void discord_voice_client::on_disconnect() {

size_t times_looped = 0;
time_t last_loop_time = time(nullptr);
time_t current_time = time(nullptr);

do {
bool error = false;
ssl_client::read_loop();
ssl_client::close();
/* Here, we check if it's been longer than 3 seconds since the previous loop,
* this gives us time to see if it's an actual disconnect, or an error.
* This will prevent us from looping too much, meaning error codes do not cause an infinite loop.
*/
if (current_time - last_loop_time >= 3) {
times_looped = 0;
}

time_t current_time = time(nullptr);
/* Here, we check if it's been longer than 3 seconds since the previous loop,
* this gives us time to see if it's an actual disconnect, or an error.
* This will prevent us from looping too much, meaning error codes do not cause an infinite loop.
*/
if (current_time - last_loop_time >= 3) {
times_looped = 0;
}
/* This does mean we'll always have times_looped at a minimum of 1, this is intended. */
times_looped++;

/* This does mean we'll always have times_looped at a minimum of 1, this is intended. */
times_looped++;
/* If we've looped 5 or more times, abort the loop. */
if (times_looped >= 5) {
log(dpp::ll_warning, "Reached max loops whilst attempting to read from the websocket. Aborting websocket.");
break;
}
/* If we've looped 5 or more times, abort the loop. */
if (terminating || times_looped >= 5) {
log(dpp::ll_warning, "Reached max loops whilst attempting to read from the websocket. Aborting websocket.");
return;
}
last_loop_time = current_time;

last_loop_time = current_time;

if (!terminating) {
log(dpp::ll_debug, "Attempting to reconnect the websocket...");
do {
try {
ssl_client::connect();
websocket_client::connect();
}
catch (const std::exception &e) {
log(dpp::ll_error, std::string("Error establishing voice websocket connection, retry in 5 seconds: ") + e.what());
ssl_client::close();
std::this_thread::sleep_for(std::chrono::seconds(5));
error = true;
}
} while (error && !terminating);
}
} while(!terminating);
log(dpp::ll_debug, "Attempting to reconnect the websocket...");
owner->start_timer([this](auto handle) {
owner->stop_timer(handle);
cleanup();
setup();
terminating = false;
ssl_client::connect();
websocket_client::connect();
run();
}, 1);
}

void discord_voice_client::run()
{
this->runner = new std::thread(&discord_voice_client::thread_run, this);
this->thread_id = runner->native_handle();
void discord_voice_client::run() {
ssl_client::read_loop();
}


}
}
5 changes: 4 additions & 1 deletion src/dpp/voice/enabled/write_ready.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,10 @@ void discord_voice_client::write_ready() {
bufsize = outbuf[0].packet.length();
outbuf.erase(outbuf.begin());
}
if (!outbuf.empty()) {
udp_events.flags = WANT_READ | WANT_WRITE | WANT_ERROR;
owner->socketengine->update_socket(udp_events);
}
}
}
}
Expand Down Expand Up @@ -123,5 +127,4 @@ void discord_voice_client::write_ready() {
}
}


}
Loading

0 comments on commit a548c2c

Please sign in to comment.