feat: Moves TcpServer to another thread. Rewrites Firewall (#1660)
## Breaking Changes * The Firewall and IP Limiter have been rewritten. Please read the notes carefully! * `TcpServer.Instances` moved back to `NetState.Instances` - sorry - it was stupid to move it to begin with. > [!Note] > Sockets that fail the IP Limiter or Firewall will be immediately and forcibly disconnected. > This means they will be stuck at "Verifying account..." if it was a real client. ### Summary - Removes firewall wildcard support. - Removes `AccessRestrictions`. - Moves Firewall/IPLimiter to the core. - Moves `TcpServer` to its own thread. - Removes the `SocketConnect` and `SocketDisconnect` event sinks. - Moves `Instances` back to `NetState.Instances`. - Fixes a long standing bug with bad handling of duplicate listener addresses. #### Firewall The firewall has been completely rewritten. There is now an "Admin Firewall" which saves to the config file. Secondarily, there is an internal firewall used exclusively by the TcpServer while processing sockets. The Admin firewall mirrors it's additions/deletions to the internal firewall by adding requests to a queue. > [!IMPORTANT] > **Wildcard firewall entries, such as `X`, `*`, `?` are not allowed.** > **Ranges in between IP classes or sextets are not allowed.** > **Please make sure to use one of the following:** > * IP Address - `192.168.1.1` > * CIDR - `192.168.1.0/24` > * Range - `192.168.1.1-192.168.1.100` #### IP Limiter The IP Limiter has been completely rewritten. The available configurations are: ```json "ipLimiter.enable": "True", "ipLimiter.maxConnectionsPerIP": 10, "ipLimiter.clearConnectionAttemptsDuration": "00:00:00:10", "ipLimiter.clearThrottledDuration": "00:00:02:00", ``` The IP Limiter is set up to prevent spamming connections from the same IP. Every time an IP connects, it is added to a connection list. After 10 attempts, the IP is added to the throttle list. To keep the system fast, the connection list is entirely wiped every 10 seconds, and the throttle list is entirely wiped every 2 minutes.
This commit is contained in:
parent
5f3de6537b
commit
4cd668ef61
38 changed files with 1117 additions and 1030 deletions
|
|
@ -171,10 +171,10 @@ namespace Server.Gumps
|
|||
AddLabel(150, 150, LabelHue, banned.ToString());
|
||||
|
||||
AddLabel(20, 170, LabelHue, "Firewalled:");
|
||||
AddLabel(150, 170, LabelHue, Firewall.Set.Count.ToString());
|
||||
AddLabel(150, 170, LabelHue, AdminFirewall.Set.Count.ToString());
|
||||
|
||||
AddLabel(20, 190, LabelHue, "Clients:");
|
||||
AddLabel(150, 190, LabelHue, TcpServer.Instances.Count.ToString());
|
||||
AddLabel(150, 190, LabelHue, NetState.Instances.Count.ToString());
|
||||
|
||||
AddLabel(20, 210, LabelHue, "Mobiles:");
|
||||
AddLabel(150, 210, LabelHue, World.Mobiles.Count.ToString());
|
||||
|
|
@ -437,7 +437,7 @@ namespace Server.Gumps
|
|||
{
|
||||
if (m_List == null)
|
||||
{
|
||||
var states = TcpServer.Instances.ToList();
|
||||
var states = NetState.Instances.ToList();
|
||||
states.Sort(NetStateComparer.Instance);
|
||||
|
||||
m_List = states.ToList<object>();
|
||||
|
|
@ -1225,7 +1225,7 @@ namespace Server.Gumps
|
|||
{
|
||||
AddFirewallHeader();
|
||||
|
||||
m_List ??= Firewall.Set.ToList<object>();
|
||||
m_List ??= AdminFirewall.Set.ToList<object>();
|
||||
|
||||
AddLabelCropped(12, 120, 358, 20, LabelHue, "IP Address");
|
||||
|
||||
|
|
@ -1275,7 +1275,7 @@ namespace Server.Gumps
|
|||
{
|
||||
AddFirewallHeader();
|
||||
|
||||
if (state is not Firewall.IFirewallEntry firewallEntry)
|
||||
if (state is not IFirewallEntry firewallEntry)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
|
@ -1804,7 +1804,7 @@ namespace Server.Gumps
|
|||
{
|
||||
for (var i = 0; i < a.LoginIPs.Length; ++i)
|
||||
{
|
||||
Firewall.Add(a.LoginIPs[i]);
|
||||
AdminFirewall.Add(a.LoginIPs[i]);
|
||||
}
|
||||
|
||||
notice = "All addresses in the list have been firewalled.";
|
||||
|
|
@ -1828,7 +1828,7 @@ namespace Server.Gumps
|
|||
|
||||
if (okay)
|
||||
{
|
||||
Firewall.Add(toFirewall);
|
||||
AdminFirewall.Add(toFirewall);
|
||||
|
||||
notice = $"{toFirewall} : Added to firewall.";
|
||||
}
|
||||
|
|
@ -2427,7 +2427,7 @@ namespace Server.Gumps
|
|||
{
|
||||
var count = 0;
|
||||
|
||||
foreach (var ns in TcpServer.Instances)
|
||||
foreach (var ns in NetState.Instances)
|
||||
{
|
||||
var a = ns.Account;
|
||||
|
||||
|
|
@ -2533,7 +2533,7 @@ namespace Server.Gumps
|
|||
}
|
||||
else
|
||||
{
|
||||
foreach (var ns in TcpServer.Instances)
|
||||
foreach (var ns in NetState.Instances)
|
||||
{
|
||||
bool isMatch;
|
||||
|
||||
|
|
@ -3626,7 +3626,7 @@ namespace Server.Gumps
|
|||
}
|
||||
else
|
||||
{
|
||||
foreach (var check in Firewall.Set)
|
||||
foreach (var check in AdminFirewall.Set)
|
||||
{
|
||||
var checkStr = check.ToString();
|
||||
|
||||
|
|
@ -3692,42 +3692,47 @@ namespace Server.Gumps
|
|||
m_PageType,
|
||||
m_ListPage,
|
||||
m_List,
|
||||
"You must enter an address or pattern to add.",
|
||||
m_State
|
||||
)
|
||||
);
|
||||
}
|
||||
else if (!Utility.IsValidIP(text))
|
||||
{
|
||||
from.SendGump(
|
||||
new AdminGump(
|
||||
from,
|
||||
m_PageType,
|
||||
m_ListPage,
|
||||
m_List,
|
||||
"That is not a valid address or pattern.",
|
||||
"You must enter an address or CIDR to add.",
|
||||
m_State
|
||||
)
|
||||
);
|
||||
}
|
||||
else
|
||||
{
|
||||
object toAdd = Firewall.ToFirewallEntry(text);
|
||||
IFirewallEntry firewallEntry;
|
||||
try
|
||||
{
|
||||
firewallEntry = AdminFirewall.ToFirewallEntry(text);
|
||||
}
|
||||
catch
|
||||
{
|
||||
from.SendGump(
|
||||
new AdminGump(
|
||||
from,
|
||||
m_PageType,
|
||||
m_ListPage,
|
||||
m_List,
|
||||
"That is not a valid address or CIDR.",
|
||||
m_State
|
||||
)
|
||||
);
|
||||
break;
|
||||
}
|
||||
|
||||
CommandLogging.WriteLine(
|
||||
from,
|
||||
$"{from.AccessLevel} {CommandLogging.Format(from)} firewalling {toAdd}"
|
||||
$"{from.AccessLevel} {CommandLogging.Format(from)} firewalling {firewallEntry}"
|
||||
);
|
||||
|
||||
Firewall.Add(toAdd);
|
||||
AdminFirewall.Add(firewallEntry);
|
||||
from.SendGump(
|
||||
new AdminGump(
|
||||
from,
|
||||
AdminGumpPage.FirewallInfo,
|
||||
0,
|
||||
null,
|
||||
$"{toAdd} : Added to firewall.",
|
||||
toAdd
|
||||
$"{firewallEntry} : Added to firewall.",
|
||||
firewallEntry
|
||||
)
|
||||
);
|
||||
}
|
||||
|
|
@ -3751,14 +3756,14 @@ namespace Server.Gumps
|
|||
}
|
||||
case 3:
|
||||
{
|
||||
if (m_State is Firewall.IFirewallEntry)
|
||||
if (m_State is IFirewallEntry)
|
||||
{
|
||||
CommandLogging.WriteLine(
|
||||
from,
|
||||
$"{from.AccessLevel} {CommandLogging.Format(from)} removing {m_State} from firewall list"
|
||||
);
|
||||
|
||||
Firewall.Remove(m_State);
|
||||
AdminFirewall.Remove(m_State);
|
||||
from.SendGump(
|
||||
new AdminGump(
|
||||
from,
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue