Skip to content

Commit

Permalink
ui: implement tcp congestion algorithm
Browse files Browse the repository at this point in the history
modprobe tcp_congestion before use specified congestion algorithm.

`ls -la /lib/modules/$(uname -r)/kernel/net/ipv4`

Fixes #1071.
  • Loading branch information
Chilledheart committed Aug 26, 2024
1 parent 307da53 commit 00dbd8c
Show file tree
Hide file tree
Showing 19 changed files with 323 additions and 153 deletions.
8 changes: 2 additions & 6 deletions src/config/config.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -49,9 +49,6 @@ bool ReadConfig() {
config_impl->Read("fast_open", &FLAGS_tcp_fastopen);
config_impl->Read("fast_open_connect", &FLAGS_tcp_fastopen_connect);

#ifdef __linux__
config_impl->Read("congestion_algorithm", &FLAGS_congestion_algorithm);
#endif
config_impl->Read("doh_url", &FLAGS_doh_url);
config_impl->Read("dot_host", &FLAGS_dot_host);
config_impl->Read("connect_timeout", &FLAGS_connect_timeout);
Expand All @@ -62,6 +59,7 @@ bool ReadConfig() {
config_impl->Read("tcp_keep_alive_cnt", &FLAGS_tcp_keep_alive_cnt);
config_impl->Read("tcp_keep_alive_idle_timeout", &FLAGS_tcp_keep_alive_idle_timeout);
config_impl->Read("tcp_keep_alive_interval", &FLAGS_tcp_keep_alive_interval);
config_impl->Read("tcp_congestion_algorithm", &FLAGS_tcp_congestion_algorithm);

/* optional tls fields */
config_impl->Read("cacert", &FLAGS_cacert);
Expand Down Expand Up @@ -121,9 +119,6 @@ bool SaveConfig() {
all_fields_written &= config_impl->Write("fast_open", FLAGS_tcp_fastopen);
all_fields_written &= config_impl->Write("fast_open_connect", FLAGS_tcp_fastopen_connect);
static_cast<void>(config_impl->Delete("threads"));
#ifdef __linux__
all_fields_written &= config_impl->Write("congestion_algorithm", FLAGS_congestion_algorithm);
#endif
all_fields_written &= config_impl->Write("doh_url", FLAGS_doh_url);
all_fields_written &= config_impl->Write("dot_host", FLAGS_dot_host);
all_fields_written &= config_impl->Write("timeout", FLAGS_connect_timeout);
Expand All @@ -135,6 +130,7 @@ bool SaveConfig() {
all_fields_written &= config_impl->Write("tcp_keep_alive_cnt", FLAGS_tcp_keep_alive_cnt);
all_fields_written &= config_impl->Write("tcp_keep_alive_idle_timeout", FLAGS_tcp_keep_alive_idle_timeout);
all_fields_written &= config_impl->Write("tcp_keep_alive_interval", FLAGS_tcp_keep_alive_interval);
all_fields_written &= config_impl->Write("tcp_congestion_algorithm", FLAGS_tcp_congestion_algorithm);

all_fields_written &= config_impl->Write("cacert", FLAGS_cacert);
all_fields_written &= config_impl->Write("capath", FLAGS_capath);
Expand Down
4 changes: 1 addition & 3 deletions src/config/config_network.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,6 @@
ABSL_FLAG(bool, ipv6_mode, true, "Resolve names to IPv6 addresses");

ABSL_FLAG(bool, reuse_port, true, "Reuse the listening port");
#ifdef __linux__
ABSL_FLAG(std::string, congestion_algorithm, "", "TCP Congestion Algorithm");
#endif
ABSL_FLAG(bool, tcp_fastopen, false, "TCP fastopen");
ABSL_FLAG(bool, tcp_fastopen_connect, false, "TCP fastopen connect");
ABSL_FLAG(int32_t, connect_timeout, 0, "Connect timeout (in seconds)");
Expand All @@ -24,6 +21,7 @@ ABSL_FLAG(int32_t,
7200,
"The number of seconds a connection needs to be idle before TCP begins sending out keep-alive probes.");
ABSL_FLAG(int32_t, tcp_keep_alive_interval, 75, "The number of seconds between TCP keep-alive probes.");
ABSL_FLAG(std::string, tcp_congestion_algorithm, "", "TCP Congestion Algorithm (Linux Only)");
ABSL_FLAG(bool, redir_mode, false, "Enable TCP Redir mode support (linux only)");

ABSL_FLAG(std::string, doh_url, "", "Resolve host names over DoH");
Expand Down
4 changes: 1 addition & 3 deletions src/config/config_network.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,6 @@
ABSL_DECLARE_FLAG(bool, ipv6_mode);

ABSL_DECLARE_FLAG(bool, reuse_port);
#ifdef __linux__
ABSL_DECLARE_FLAG(std::string, congestion_algorithm);
#endif
ABSL_DECLARE_FLAG(bool, tcp_fastopen);
ABSL_DECLARE_FLAG(bool, tcp_fastopen_connect);
// same with proxy_connect_timeout no need for proxy_read_timeout
Expand All @@ -25,6 +22,7 @@ ABSL_DECLARE_FLAG(bool, tcp_keep_alive);
ABSL_DECLARE_FLAG(int32_t, tcp_keep_alive_cnt);
ABSL_DECLARE_FLAG(int32_t, tcp_keep_alive_idle_timeout);
ABSL_DECLARE_FLAG(int32_t, tcp_keep_alive_interval);
ABSL_DECLARE_FLAG(std::string, tcp_congestion_algorithm);
ABSL_DECLARE_FLAG(bool, redir_mode);

ABSL_DECLARE_FLAG(std::string, doh_url);
Expand Down
35 changes: 33 additions & 2 deletions src/gtk/option_dialog.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
#include "core/logging.hpp"
#include "core/utils.hpp"
#include "gtk/utils.hpp"
#include "net/network.hpp"

OptionDialog::OptionDialog(const std::string& title, GtkWindow* parent, bool modal)
: impl_(GTK_DIALOG(gtk_dialog_new_with_buttons(title.c_str(),
Expand All @@ -27,24 +28,34 @@ OptionDialog::OptionDialog(const std::string& title, GtkWindow* parent, bool mod
auto tcp_keep_alive_interval_label = gtk_label_new(_("TCP keep alive interval"));

auto enable_post_quantum_kyber_label = gtk_label_new(_("Kyber post-quantum key agreement for TLS"));
auto tcp_congestion_algorithm = gtk_label_new(_("TCP Congestion Algorithm"));

gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_label), 0, 0, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_cnt_label), 0, 1, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_idle_timeout_label), 0, 2, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_interval_label), 0, 3, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(enable_post_quantum_kyber_label), 0, 4, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_congestion_algorithm), 0, 5, 1, 1);

tcp_keep_alive_ = GTK_CHECK_BUTTON(gtk_check_button_new());
tcp_keep_alive_cnt_ = GTK_ENTRY(gtk_entry_new());
tcp_keep_alive_idle_timeout_ = GTK_ENTRY(gtk_entry_new());
tcp_keep_alive_interval_ = GTK_ENTRY(gtk_entry_new());
enable_post_quantum_kyber_ = GTK_CHECK_BUTTON(gtk_check_button_new());

algorithms_ = net::GetTCPAvailableCongestionAlgorithms();

tcp_congestion_algorithm_ = GTK_COMBO_BOX_TEXT(gtk_combo_box_text_new());
for (const auto& algorithm : algorithms_) {
gtk_combo_box_text_append_text(tcp_congestion_algorithm_, algorithm.c_str());
}

gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_), 1, 0, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_cnt_), 1, 1, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_idle_timeout_), 1, 2, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_keep_alive_interval_), 1, 3, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(enable_post_quantum_kyber_), 1, 4, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(tcp_congestion_algorithm_), 1, 5, 1, 1);

gtk_widget_set_margin_top(GTK_WIDGET(grid), 12);
gtk_widget_set_margin_bottom(GTK_WIDGET(grid), 12);
Expand Down Expand Up @@ -79,8 +90,8 @@ OptionDialog::OptionDialog(const std::string& title, GtkWindow* parent, bool mod

g_signal_connect(G_OBJECT(cancel_button_), "clicked", G_CALLBACK(*cancel_callback), this);

gtk_grid_attach(grid, GTK_WIDGET(okay_button_), 0, 5, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(cancel_button_), 1, 5, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(okay_button_), 0, 6, 1, 1);
gtk_grid_attach(grid, GTK_WIDGET(cancel_button_), 1, 6, 1, 1);

gtk_container_add(GTK_CONTAINER(gtk_dialog_get_content_area(impl_)), GTK_WIDGET(grid));

Expand Down Expand Up @@ -120,6 +131,19 @@ void OptionDialog::LoadChanges() {

gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(enable_post_quantum_kyber_),
absl::GetFlag(FLAGS_enable_post_quantum_kyber));

auto algorithm = absl::GetFlag(FLAGS_tcp_congestion_algorithm);
unsigned int i;
for (i = 0; i < std::size(algorithms_); ++i) {
if (algorithm == algorithms_[i])
break;
}

// first is unset
if (i == std::size(algorithms_)) {
i = 0;
}
gtk_combo_box_set_active(GTK_COMBO_BOX(tcp_congestion_algorithm_), i);
}

bool OptionDialog::OnSave() {
Expand All @@ -143,5 +167,12 @@ bool OptionDialog::OnSave() {

absl::SetFlag(&FLAGS_enable_post_quantum_kyber, enable_post_quantum_kyber);

gchar* algorithm_cstr = gtk_combo_box_text_get_active_text(tcp_congestion_algorithm_);
if (algorithm_cstr == nullptr || std::string_view(algorithm_cstr).empty()) {
absl::SetFlag(&FLAGS_tcp_congestion_algorithm, std::string());
} else {
absl::SetFlag(&FLAGS_tcp_congestion_algorithm, algorithm_cstr);
}

return true;
}
3 changes: 3 additions & 0 deletions src/gtk/option_dialog.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#include <gtk/gtk.h>

#include <string>
#include <vector>

class OptionDialog {
public:
Expand All @@ -26,6 +27,8 @@ class OptionDialog {
GtkEntry* tcp_keep_alive_idle_timeout_;
GtkEntry* tcp_keep_alive_interval_;
GtkCheckButton* enable_post_quantum_kyber_;
GtkComboBoxText* tcp_congestion_algorithm_;
std::vector<std::string> algorithms_;

GtkButton* okay_button_;
GtkButton* cancel_button_;
Expand Down
Loading

0 comments on commit 00dbd8c

Please sign in to comment.