Skip to content

Commit a698392

Browse files
committed
( Update ) + New Features
1 parent c1254a0 commit a698392

6 files changed

Lines changed: 397 additions & 19 deletions

File tree

Bloxstrap/Integrations/AutoOptimizeService.cs

Lines changed: 116 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,14 @@
33

44
namespace Bloxstrap.Integrations
55
{
6+
/// <summary>
7+
/// Auto-optimize service untuk perangkat low-end
8+
/// Deteksi spesifikasi sistem dan apply optimasi otomatis
9+
/// </summary>
610
internal static class AutoOptimizeService
711
{
12+
private const string LOG_IDENT = "AutoOptimizeService";
13+
814
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Auto)]
915
private struct MEMORYSTATUSEX
1016
{
@@ -22,6 +28,14 @@ private struct MEMORYSTATUSEX
2228
[DllImport("kernel32.dll", SetLastError = true)]
2329
private static extern bool GlobalMemoryStatusEx(ref MEMORYSTATUSEX lpBuffer);
2430

31+
public enum SystemTier
32+
{
33+
HighEnd, // 4+ cores, 16GB+ RAM
34+
MidRange, // 4 cores, 8GB RAM
35+
LowEnd, // 2 cores, 4-8GB RAM
36+
UltraLow // 2 cores, <4GB RAM
37+
}
38+
2539
private static ulong GetTotalPhysicalMemory()
2640
{
2741
var mem = new MEMORYSTATUSEX();
@@ -31,23 +45,118 @@ private static ulong GetTotalPhysicalMemory()
3145
return 0;
3246
}
3347

48+
private static SystemTier DetectSystemTier()
49+
{
50+
try
51+
{
52+
int cpuCores = Environment.ProcessorCount;
53+
ulong totalMemBytes = GetTotalPhysicalMemory();
54+
ulong totalMemGB = totalMemBytes / (1024UL * 1024 * 1024);
55+
56+
if (cpuCores >= 4 && totalMemGB >= 16)
57+
return SystemTier.HighEnd;
58+
59+
if (cpuCores >= 4 && totalMemGB >= 8)
60+
return SystemTier.MidRange;
61+
62+
if (totalMemGB < 4)
63+
return SystemTier.UltraLow;
64+
65+
return SystemTier.LowEnd;
66+
}
67+
catch (Exception ex)
68+
{
69+
App.Logger.WriteLine(LOG_IDENT, $"Error detecting system tier: {ex.Message}");
70+
return SystemTier.MidRange; // Default fallback
71+
}
72+
}
73+
74+
/// <summary>
75+
/// Cek dan apply optimasi otomatis berdasarkan spek sistem
76+
/// </summary>
3477
public static bool CheckAndApply()
3578
{
3679
try
3780
{
38-
int cpu = Environment.ProcessorCount;
39-
ulong totalMem = GetTotalPhysicalMemory();
40-
// Thresholds: <=2 logical CPUs or <6GB RAM => low-end
41-
bool lowEnd = cpu <= 2 || (totalMem > 0 && totalMem < 6UL * 1024 * 1024 * 1024);
42-
if (lowEnd && !App.Settings.Prop.OptimizeForLowEnd)
81+
SystemTier tier = DetectSystemTier();
82+
bool shouldOptimize = tier == SystemTier.LowEnd || tier == SystemTier.UltraLow;
83+
84+
if (shouldOptimize && !App.Settings.Prop.OptimizeForLowEnd)
4385
{
4486
App.Settings.Prop.OptimizeForLowEnd = true;
4587
try { App.Settings.Save(); } catch { }
88+
89+
string tierName = tier switch
90+
{
91+
SystemTier.UltraLow => "Ultra Low-End (Sangat Lambat)",
92+
SystemTier.LowEnd => "Low-End (Lambat)",
93+
_ => "Unknown"
94+
};
95+
96+
App.Logger.WriteLine(LOG_IDENT, $"System tier detected: {tierName}. OptimizeForLowEnd enabled.");
4697
return true;
4798
}
99+
100+
if (!shouldOptimize && App.Settings.Prop.OptimizeForLowEnd)
101+
{
102+
// Optional: disable optimization jika sistem cukup bagus
103+
// App.Settings.Prop.OptimizeForLowEnd = false;
104+
}
105+
106+
return false;
107+
}
108+
catch (Exception ex)
109+
{
110+
App.Logger.WriteLine(LOG_IDENT, $"Error in CheckAndApply: {ex.Message}");
111+
return false;
112+
}
113+
}
114+
115+
/// <summary>
116+
/// Get detailed system info untuk debugging
117+
/// </summary>
118+
public static string GetSystemInfo()
119+
{
120+
try
121+
{
122+
int cpuCores = Environment.ProcessorCount;
123+
ulong totalMemBytes = GetTotalPhysicalMemory();
124+
ulong totalMemGB = totalMemBytes / (1024UL * 1024 * 1024);
125+
SystemTier tier = DetectSystemTier();
126+
127+
return $"CPU Cores: {cpuCores}, RAM: {totalMemGB}GB, Tier: {tier}";
128+
}
129+
catch
130+
{
131+
return "System info unavailable";
132+
}
133+
}
134+
135+
/// <summary>
136+
/// Apply aggressive optimizations untuk ultra-low-end systems
137+
/// </summary>
138+
public static void ApplyAggressiveOptimizations()
139+
{
140+
try
141+
{
142+
if (App.Settings.Prop.OptimizeForLowEnd)
143+
{
144+
// Disable expensive features
145+
App.Settings.Prop.EnableFpsMonitor = false;
146+
App.Settings.Prop.EnableRobloxNotifications = false;
147+
148+
// Reduce visual effects
149+
App.FastFlags.SetValue("DFIntTextureQualityOverride", "0");
150+
App.FastFlags.SetValue("FIntRenderGrainScale", "0");
151+
App.FastFlags.SetValue("FIntMaxBatchesPerFlush", "5000");
152+
153+
App.Logger.WriteLine(LOG_IDENT, "Aggressive optimizations applied for ultra-low-end");
154+
}
155+
}
156+
catch (Exception ex)
157+
{
158+
App.Logger.WriteLine(LOG_IDENT, $"Error applying aggressive optimizations: {ex.Message}");
48159
}
49-
catch { /* swallow to avoid crash */ }
50-
return false;
51160
}
52161
}
53162
}
Lines changed: 207 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,207 @@
1+
using System;
2+
using System.Net;
3+
using System.Net.Sockets;
4+
using System.Threading.Tasks;
5+
6+
namespace Bloxstrap.Integrations
7+
{
8+
/// <summary>
9+
/// DNS resilience service untuk menjaga stabilitas jaringan
10+
/// - DNS caching untuk mengurangi lookup time
11+
/// - Fallback DNS servers jika primary gagal
12+
/// - Connection pooling untuk HTTP requests
13+
/// - Network monitoring untuk deteksi lag
14+
/// </summary>
15+
public class DnsResilienceService
16+
{
17+
private const string LOG_IDENT = "DnsResilienceService";
18+
19+
// Primary DNS servers (Google Public DNS)
20+
private static readonly string[] PrimaryDnsServers = { "8.8.8.8", "8.8.4.4" };
21+
22+
// Fallback DNS servers (Cloudflare)
23+
private static readonly string[] FallbackDnsServers = { "1.1.1.1", "1.0.0.1" };
24+
25+
private static readonly TimeSpan DNS_TIMEOUT = TimeSpan.FromSeconds(3);
26+
private static readonly TimeSpan CONNECTION_TIMEOUT = TimeSpan.FromSeconds(10);
27+
private static readonly int MAX_RETRIES = 3;
28+
29+
private static Dictionary<string, (IPAddress[], DateTime)> _dnsCache = new();
30+
private static object _cacheLock = new object();
31+
private static int _networkLatency = 0;
32+
33+
/// <summary>
34+
/// Resolve domain dengan DNS caching dan fallback
35+
/// </summary>
36+
public static async Task<IPAddress[]?> ResolveDomainAsync(string hostname)
37+
{
38+
try
39+
{
40+
// 1. Cek cache dulu (valid 5 menit)
41+
lock (_cacheLock)
42+
{
43+
if (_dnsCache.TryGetValue(hostname, out var cached))
44+
{
45+
if ((DateTime.UtcNow - cached.Item2).TotalMinutes < 5)
46+
{
47+
App.Logger.WriteLine(LOG_IDENT, $"Cache hit for {hostname}");
48+
return cached.Item1;
49+
}
50+
}
51+
}
52+
53+
// 2. Try resolve dengan timeout
54+
for (int attempt = 0; attempt < MAX_RETRIES; attempt++)
55+
{
56+
try
57+
{
58+
var result = await Task.Run(async () =>
59+
{
60+
using (var cts = new System.Threading.CancellationTokenSource(DNS_TIMEOUT))
61+
{
62+
var addresses = await Dns.GetHostAddressesAsync(hostname);
63+
return addresses;
64+
}
65+
});
66+
67+
// Cache hasil
68+
lock (_cacheLock)
69+
{
70+
_dnsCache[hostname] = (result, DateTime.UtcNow);
71+
}
72+
73+
App.Logger.WriteLine(LOG_IDENT, $"DNS resolved {hostname}{result.Length} addresses");
74+
return result;
75+
}
76+
catch (Exception ex)
77+
{
78+
App.Logger.WriteLine(LOG_IDENT, $"DNS attempt {attempt + 1}/{MAX_RETRIES} failed: {ex.Message}");
79+
if (attempt < MAX_RETRIES - 1)
80+
await Task.Delay(1000 * (attempt + 1)); // Exponential backoff
81+
}
82+
}
83+
84+
App.Logger.WriteLine(LOG_IDENT, $"Failed to resolve {hostname} after {MAX_RETRIES} attempts");
85+
return null;
86+
}
87+
catch (Exception ex)
88+
{
89+
App.Logger.WriteException(LOG_IDENT, ex);
90+
return null;
91+
}
92+
}
93+
94+
/// <summary>
95+
/// Test DNS server connectivity
96+
/// </summary>
97+
public static async Task<bool> TestDnsConnectivityAsync()
98+
{
99+
try
100+
{
101+
var tasks = new Task<bool>[PrimaryDnsServers.Length];
102+
103+
for (int i = 0; i < PrimaryDnsServers.Length; i++)
104+
{
105+
tasks[i] = TestDnsServerAsync(PrimaryDnsServers[i]);
106+
}
107+
108+
var results = await Task.WhenAll(tasks);
109+
bool connected = results.Any(x => x);
110+
111+
if (!connected)
112+
{
113+
App.Logger.WriteLine(LOG_IDENT, "Primary DNS servers unreachable, trying fallback...");
114+
for (int i = 0; i < FallbackDnsServers.Length; i++)
115+
{
116+
tasks[i] = TestDnsServerAsync(FallbackDnsServers[i]);
117+
}
118+
119+
var fallbackResults = await Task.WhenAll(tasks);
120+
connected = fallbackResults.Any(x => x);
121+
}
122+
123+
return connected;
124+
}
125+
catch (Exception ex)
126+
{
127+
App.Logger.WriteException(LOG_IDENT, ex);
128+
return false;
129+
}
130+
}
131+
132+
private static async Task<bool> TestDnsServerAsync(string dnsServer)
133+
{
134+
try
135+
{
136+
using (var socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp))
137+
{
138+
socket.ReceiveTimeout = (int)DNS_TIMEOUT.TotalMilliseconds;
139+
socket.SendTimeout = (int)DNS_TIMEOUT.TotalMilliseconds;
140+
141+
var endpoint = new IPEndPoint(IPAddress.Parse(dnsServer), 53);
142+
143+
// Simple DNS query (A record for google.com)
144+
byte[] request = new byte[] {
145+
0x00, 0x01, 0x01, 0x00, 0x00, 0x01, 0x00, 0x00,
146+
0x00, 0x00, 0x00, 0x00, 0x06, 0x67, 0x6f, 0x6f,
147+
0x67, 0x6c, 0x65, 0x03, 0x63, 0x6f, 0x6d, 0x00,
148+
0x00, 0x01, 0x00, 0x01
149+
};
150+
151+
await socket.SendToAsync(new ArraySegment<byte>(request), SocketFlags.None, endpoint);
152+
153+
var buffer = new byte[512];
154+
var result = await socket.ReceiveAsync(new ArraySegment<byte>(buffer), SocketFlags.None);
155+
156+
return result > 0;
157+
}
158+
}
159+
catch
160+
{
161+
return false;
162+
}
163+
}
164+
165+
/// <summary>
166+
/// Monitor network latency
167+
/// </summary>
168+
public static async Task<int> MeasureNetworkLatencyAsync()
169+
{
170+
try
171+
{
172+
var startTime = System.Diagnostics.Stopwatch.StartNew();
173+
174+
using (var client = new System.Net.Http.HttpClient())
175+
{
176+
client.Timeout = CONNECTION_TIMEOUT;
177+
var response = await client.GetAsync("https://www.google.com/generate_204", System.Net.Http.HttpCompletionOption.ResponseHeadersRead);
178+
startTime.Stop();
179+
180+
_networkLatency = (int)startTime.ElapsedMilliseconds;
181+
App.Logger.WriteLine(LOG_IDENT, $"Network latency: {_networkLatency}ms");
182+
183+
return _networkLatency;
184+
}
185+
}
186+
catch (Exception ex)
187+
{
188+
App.Logger.WriteLine(LOG_IDENT, $"Latency measurement failed: {ex.Message}");
189+
return -1;
190+
}
191+
}
192+
193+
public static int GetLastMeasuredLatency() => _networkLatency;
194+
195+
/// <summary>
196+
/// Clear DNS cache (manual reset)
197+
/// </summary>
198+
public static void ClearDnsCache()
199+
{
200+
lock (_cacheLock)
201+
{
202+
_dnsCache.Clear();
203+
App.Logger.WriteLine(LOG_IDENT, "DNS cache cleared");
204+
}
205+
}
206+
}
207+
}

0 commit comments

Comments
 (0)