From 45ddc7562cb867135aba316ac3a40a1112295ed1 Mon Sep 17 00:00:00 2001
From: Salanto <62221668+Salanto@users.noreply.github.com>
Date: Thu, 20 Jul 2023 00:12:49 +0200
Subject: [PATCH 1/4] Add converter script
---
scripts/maxmind2sqlite.ps1 | 95 ++++++++++++++++++++++++++++++++++++++
1 file changed, 95 insertions(+)
create mode 100644 scripts/maxmind2sqlite.ps1
diff --git a/scripts/maxmind2sqlite.ps1 b/scripts/maxmind2sqlite.ps1
new file mode 100644
index 0000000..5ef3d1f
--- /dev/null
+++ b/scripts/maxmind2sqlite.ps1
@@ -0,0 +1,95 @@
+<#PSScriptInfo
+.VERSION 1.0
+.GUID aca39872-c8c6-434f-98fe-a6e95be92aa7
+#>
+
+<#
+.DESCRIPTION
+ Best-effort MaxMind ASN CSV database to SQLite converter.
+#>
+
+$sDatabasePath= "$PSScriptRoot\storage\asn.sqlite3"
+$license_key = ""
+$uri_maxmind = [string]::Format("https://download.maxmind.com/app/geoip_download?edition_id=GeoLite2-ASN-CSV&license_key={0}&suffix=zip",$license_key)
+
+Write-Host("Checking and downloading dependencies.")
+
+$uri_sqlite = "https://system.data.sqlite.org/blobs/1.0.118.0/sqlite-netFx451-binary-bundle-x64-2013-1.0.118.0.zip"
+if (!(Test-Path -Path "$PSScriptRoot\bin\System.Data.SQLite.dll")) {
+ Write-Host("Downloading SQlite3!")
+ Start-BitsTransfer $uri_sqlite -Destination "$PSScriptRoot\sqlite3.zip" -HttpMethod GET
+ Expand-Archive -Path "$PSScriptRoot\sqlite3.zip" -DestinationPath "$PSScriptRoot\bin" -Force
+ Remove-Item -Path "$PSScriptRoot\sqlite3.zip" -Force
+}
+else {
+ Write-Host("sqlite3 found!") -ForegroundColor Green
+}
+
+if (!(Test-Path -Path "$PSScriptRoot\storage")) {
+ New-Item -Path "$PSScriptRoot\storage" -ItemType Directory
+}
+
+if (Test-Path -Path "$PSScriptRoot\storage\asn.sqlite3") {
+ Remove-Item -Path "$PSScriptRoot\storage\asn.sqlite3" -Force
+}
+New-Item -Path "$PSScriptRoot\storage\asn.sqlite3" -ItemType File -Force
+
+if (![string]::IsNullOrEmpty($license_key)) {
+
+Write-Host($uri_maxmind)
+ Write-Host("MaxMind License key available. Trying to download the database.")
+ #Maxmiund has issues when I use BITS. So sad.
+ try {
+ Invoke-WebRequest -Uri $uri_maxmind -OutFile "$PSScriptRoot\maxmind.zip" -Method GET -ErrorAction Stop
+ }
+ catch {
+ Write-Host("Unable to download MaxMind CSV database. Aborting script. Please check your license key and try again later.")
+ exit
+ }
+ Expand-Archive -Path "$PSScriptRoot\maxmind.zip" -DestinationPath "$PSScriptRoot\storage" -Force
+ Remove-Item -Path "$PSScriptRoot\maxmind.zip" -Force
+}
+
+
+$ipv4 = Get-ChildItem -Recurse -Path "$PSScriptRoot\storage\*IPv4.csv" | Get-Content | ConvertFrom-Csv -Delimiter ","
+$ipv6 = Get-ChildItem -Recurse -Path "$PSScriptRoot\storage\*IPv6.csv" | Get-Content | ConvertFrom-Csv -Delimiter ","
+
+[Reflection.Assembly]::LoadFile("$PSScriptRoot\bin\System.Data.SQLite.dll")
+$sDatabaseConnectionString=[string]::Format("data source={0}",$sDatabasePath)
+$oSQLiteDBConnection = New-Object System.Data.SQLite.SQLiteConnection
+$oSQLiteDBConnection.ConnectionString = $sDatabaseConnectionString
+$oSQLiteDBConnection.open()
+
+$oSQLiteDBCommand=$oSQLiteDBConnection.CreateCommand()
+$oSQLiteDBCommand.Commandtext='CREATE TABLE "maxmind" (
+ "ip" TEXT,
+ "asn" INTEGER,
+ "organization" TEXT,
+ "type" INTEGER
+);'
+$oSQLiteDBCommand.CommandType = [System.Data.CommandType]::Text
+$oSQLiteDBCommand.ExecuteReader()
+
+Write-Host("Inserting IPv4 entries.")
+foreach($entry in $ipv4) {
+ $oSQLiteDBInsertCommand = $oSQLiteDBConnection.CreateCommand()
+ $oSQLiteDBInsertCommand.Commandtext='INSERT INTO maxmind (ip, asn, organization, type) VALUES (@ip_addr, @asn_id, @org, 4)'
+ $oSQLiteDBInsertCommand.Parameters.AddWithValue("ip_addr", $entry.network) | Out-Null
+ $oSQLiteDBInsertCommand.Parameters.AddWithValue("asn_id", $entry.autonomous_system_number) | Out-Null
+ $oSQLiteDBInsertCommand.Parameters.AddWithValue("org", $entry.autonomous_system_organization) | Out-Null
+ $oSQLiteDBInsertCommand.CommandType = [System.Data.CommandType]::Text
+ $oSQLiteDBInsertCommand.ExecuteNonQuery() | Out-Null
+ $i++
+}
+
+Write-Host("Inserting IPv6 entries.")
+foreach($entry in $ipv6) {
+ $oSQLiteDBInsertCommand = $oSQLiteDBConnection.CreateCommand()
+ $oSQLiteDBInsertCommand.Commandtext='INSERT INTO maxmind (ip, asn, organization, type) VALUES (@ip_addr, @asn_id, @org, 6)'
+ $oSQLiteDBInsertCommand.Parameters.AddWithValue("ip_addr", $entry.network) | Out-Null
+ $oSQLiteDBInsertCommand.Parameters.AddWithValue("asn_id", $entry.autonomous_system_number) | Out-Null
+ $oSQLiteDBInsertCommand.Parameters.AddWithValue("org", $entry.autonomous_system_organization) | Out-Null
+ $oSQLiteDBInsertCommand.CommandType = [System.Data.CommandType]::Text
+ $oSQLiteDBInsertCommand.ExecuteNonQuery() | Out-Null
+}
+$oSQLiteDBConnection.Close()
\ No newline at end of file
From c3caba43e512f4bb4e704920e2d439d4fefdc3fe Mon Sep 17 00:00:00 2001
From: Salanto <62221668+Salanto@users.noreply.github.com>
Date: Mon, 24 Jul 2023 04:14:34 +0200
Subject: [PATCH 2/4] Add functional ASN ban code
You need a compatible DB to make this work.
---
bin/config_sample/ipbans.json | 14 ++++++++++++
core/src/config_manager.cpp | 42 ++++++++++++++++++++++++++---------
2 files changed, 46 insertions(+), 10 deletions(-)
create mode 100644 bin/config_sample/ipbans.json
diff --git a/bin/config_sample/ipbans.json b/bin/config_sample/ipbans.json
new file mode 100644
index 0000000..ca7f80c
--- /dev/null
+++ b/bin/config_sample/ipbans.json
@@ -0,0 +1,14 @@
+{
+ "ip_range": [
+ "192.0.2.0/24",
+ "198.51.100.0/24",
+ "192.88.99.0/24",
+ "203.0.113.0/24",
+ "2001:0000:/32",
+ "2001:db8::/32",
+ "2002::/16"
+ ],
+ "asn": [
+ "0"
+ ]
+}
\ No newline at end of file
diff --git a/core/src/config_manager.cpp b/core/src/config_manager.cpp
index 1b08f4e..f88a2df 100644
--- a/core/src/config_manager.cpp
+++ b/core/src/config_manager.cpp
@@ -16,8 +16,8 @@
// along with this program. If not, see . //
//////////////////////////////////////////////////////////////////////////////////////
#include "include/config_manager.h"
-
-#include
+#include
+#include
QSettings *ConfigManager::m_settings = new QSettings("config/config.ini", QSettings::IniFormat);
QSettings *ConfigManager::m_discord = new QSettings("config/discord.ini", QSettings::IniFormat);
@@ -43,7 +43,7 @@ bool ConfigManager::verifyServerConfig()
// Verify config files
QStringList l_config_files{"config/config.ini", "config/areas.ini", "config/backgrounds.txt", "config/characters.txt", "config/music.json",
"config/discord.ini", "config/text/8ball.txt", "config/text/gimp.txt", "config/text/praise.txt",
- "config/text/reprimands.txt", "config/text/commandhelp.json", "config/text/cdns.txt"};
+ "config/text/reprimands.txt", "config/text/commandhelp.json", "config/text/cdns.txt", "config/ipbans.json"};
for (const QString &l_file : l_config_files) {
if (!fileExists(QFileInfo(l_file))) {
qCritical() << l_file + " does not exist!";
@@ -252,14 +252,36 @@ QStringList ConfigManager::rawAreaNames()
QStringList ConfigManager::iprangeBans()
{
- QStringList l_iprange_bans;
- QFile l_file("config/iprange_bans.txt");
- l_file.open(QIODevice::ReadOnly | QIODevice::Text);
- while (!(l_file.atEnd())) {
- l_iprange_bans.append(l_file.readLine().trimmed());
+ QFile l_json_file("config/ipbans.json");
+ l_json_file.open(QIODevice::ReadOnly | QIODevice::Text);
+
+ QJsonParseError l_error;
+ QJsonDocument l_ip_bans = QJsonDocument::fromJson(l_json_file.readAll(), &l_error);
+ if (l_error.error != QJsonParseError::NoError) {
+ qDebug() << "Unable to parse JSON file. Error:" << l_error.errorString();
+ return {};
}
- l_file.close();
- return l_iprange_bans;
+
+ QJsonObject l_json_obj = l_ip_bans.object();
+
+ QStringList l_range_bans;
+ l_range_bans.append(l_json_obj["ip_range"].toVariant().toStringList());
+
+ if (QFile::exists("storage/asn.sqlite3")) {
+ QSqlDatabase asn_db = QSqlDatabase::addDatabase("QSQLITE", "ASN");
+ asn_db.setDatabaseName("storage/asn.sqlite3");
+ asn_db.open();
+
+ // This is a dumb hack. Idk how else I can do this, but who gives a shit?
+ QSqlQuery query("SELECT ip FROM maxmind WHERE asn in (" + l_json_obj["asn"].toVariant().toStringList().join(",") + ")", asn_db);
+ query.exec();
+ while (query.next()) {
+ l_range_bans.append(query.value(0).toString());
+ }
+ asn_db.close();
+ }
+ l_range_bans.removeDuplicates();
+ return l_range_bans;
}
void ConfigManager::reloadSettings()
From 9f4ba1c7bdf2d5167c32044abe9963376da9153b Mon Sep 17 00:00:00 2001
From: Salanto <62221668+Salanto@users.noreply.github.com>
Date: Mon, 24 Jul 2023 14:03:26 +0200
Subject: [PATCH 3/4] I should probably fix this proper in the CI in another PR
---
bin/config_sample/iprange_bans.txt | 10 ----------
bin_tests/config/ipbans.json | 14 ++++++++++++++
bin_tests/config/iprange_bans.txt | 10 ----------
3 files changed, 14 insertions(+), 20 deletions(-)
delete mode 100644 bin/config_sample/iprange_bans.txt
create mode 100644 bin_tests/config/ipbans.json
delete mode 100644 bin_tests/config/iprange_bans.txt
diff --git a/bin/config_sample/iprange_bans.txt b/bin/config_sample/iprange_bans.txt
deleted file mode 100644
index c04f87f..0000000
--- a/bin/config_sample/iprange_bans.txt
+++ /dev/null
@@ -1,10 +0,0 @@
-# Test nets
-192.0.2.0/24
-198.51.100.0/24
-192.88.99.0/24
-203.0.113.0/24
-
-# IPv6
-2001:0000:/32
-2001:db8::/32
-2002::/16
\ No newline at end of file
diff --git a/bin_tests/config/ipbans.json b/bin_tests/config/ipbans.json
new file mode 100644
index 0000000..ca7f80c
--- /dev/null
+++ b/bin_tests/config/ipbans.json
@@ -0,0 +1,14 @@
+{
+ "ip_range": [
+ "192.0.2.0/24",
+ "198.51.100.0/24",
+ "192.88.99.0/24",
+ "203.0.113.0/24",
+ "2001:0000:/32",
+ "2001:db8::/32",
+ "2002::/16"
+ ],
+ "asn": [
+ "0"
+ ]
+}
\ No newline at end of file
diff --git a/bin_tests/config/iprange_bans.txt b/bin_tests/config/iprange_bans.txt
deleted file mode 100644
index c04f87f..0000000
--- a/bin_tests/config/iprange_bans.txt
+++ /dev/null
@@ -1,10 +0,0 @@
-# Test nets
-192.0.2.0/24
-198.51.100.0/24
-192.88.99.0/24
-203.0.113.0/24
-
-# IPv6
-2001:0000:/32
-2001:db8::/32
-2002::/16
\ No newline at end of file
From 55cfd65954a34f8649f186b0f63218ea22343310 Mon Sep 17 00:00:00 2001
From: Salanto <62221668+Salanto@users.noreply.github.com>
Date: Mon, 24 Jul 2023 14:10:25 +0200
Subject: [PATCH 4/4] Pray tell why the fuck is the comment in the test
---
tests/unittest_config_manager/tst_unittest_config_manager.cpp | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/tests/unittest_config_manager/tst_unittest_config_manager.cpp b/tests/unittest_config_manager/tst_unittest_config_manager.cpp
index a4730fd..236761b 100644
--- a/tests/unittest_config_manager/tst_unittest_config_manager.cpp
+++ b/tests/unittest_config_manager/tst_unittest_config_manager.cpp
@@ -256,8 +256,8 @@ void tst_ConfigManager::CommandInfo()
void tst_ConfigManager::iprangeBans()
{
QStringList l_ipranges = ConfigManager::iprangeBans();
- QCOMPARE(l_ipranges.at(0), "# Test nets");
- QCOMPARE(l_ipranges.at(1), "192.0.2.0/24");
+ QCOMPARE(l_ipranges.at(0), "192.0.2.0/24");
+ QCOMPARE(l_ipranges.at(1), "198.51.100.0/24");
}
void tst_ConfigManager::maxPlayers()