diff --git a/lib/wireguard/peers.dart b/lib/wireguard/peers.dart index f8b07ec..1a0bfab 100644 --- a/lib/wireguard/peers.dart +++ b/lib/wireguard/peers.dart @@ -96,7 +96,9 @@ Future deletePeer(String publicKey) async { } Future setSpeedLimit(String publicKey, int speedKbps) async { + print('Setting speed limit for peer $publicKey to ${speedKbps}kbps'); final peerIP = await _getPeerIP(publicKey); + print('Found peer IP: $peerIP for publicKey: $publicKey'); if (peerIP == null) throw Exception('Peer not found'); await TrafficControlService.setSpeedLimit(peerIP, speedKbps); diff --git a/lib/wireguard/traffic_control.dart b/lib/wireguard/traffic_control.dart index a0c5d9d..0526ab8 100644 --- a/lib/wireguard/traffic_control.dart +++ b/lib/wireguard/traffic_control.dart @@ -3,12 +3,24 @@ import 'dart:io'; class TrafficControlService { static Future setSpeedLimit(String peerIP, int speedKbps) async { final mark = _getMarkForIP(peerIP); + print('Setting speed limit for peer $peerIP to ${speedKbps}kbps (mark: $mark)'); - await _runIptablesCommand(['-I', 'FORWARD', '-s', peerIP, '-j', 'MARK', '--set-mark', mark.toString()]); - await _runIptablesCommand(['-I', 'FORWARD', '-d', peerIP, '-j', 'MARK', '--set-mark', mark.toString()]); - - await _runTcCommand(['class', 'add', 'dev', 'wg0', 'parent', '1:1', 'classid', '1:$mark', 'htb', 'rate', '${speedKbps}kbit', 'ceil', '${speedKbps}kbit']); - await _runTcCommand(['filter', 'add', 'dev', 'wg0', 'protocol', 'ip', 'parent', '1:', 'prio', '1', 'handle', mark.toString(), 'fw', 'flowid', '1:$mark']); + try { + print('Running iptables MARK commands for $peerIP...'); + await _runIptablesCommand(['-I', 'FORWARD', '-s', peerIP, '-j', 'MARK', '--set-mark', mark.toString()]); + await _runIptablesCommand(['-I', 'FORWARD', '-d', peerIP, '-j', 'MARK', '--set-mark', mark.toString()]); + + print('Running tc class add command...'); + await _runTcCommand(['class', 'add', 'dev', 'wg0', 'parent', '1:1', 'classid', '1:$mark', 'htb', 'rate', '${speedKbps}kbit', 'ceil', '${speedKbps}kbit']); + + print('Running tc filter add command...'); + await _runTcCommand(['filter', 'add', 'dev', 'wg0', 'protocol', 'ip', 'parent', '1:', 'prio', '1', 'handle', mark.toString(), 'fw', 'flowid', '1:$mark']); + + print('Speed limit set successfully for $peerIP'); + } catch (e) { + print('ERROR setting speed limit for $peerIP: $e'); + rethrow; + } } static Future setDataCap(String peerIP, int dataCapMB) async { @@ -25,14 +37,32 @@ class TrafficControlService { } static Future _runIptablesCommand(List args) async { + final command = 'iptables ${args.join(' ')}'; + print('Executing: $command'); final result = await Process.run('iptables', args); + print('iptables exit code: ${result.exitCode}'); + if (result.stdout.toString().isNotEmpty) { + print('iptables stdout: ${result.stdout}'); + } + if (result.stderr.toString().isNotEmpty) { + print('iptables stderr: ${result.stderr}'); + } if (result.exitCode != 0) { throw Exception('iptables command failed: ${result.stderr}'); } } static Future _runTcCommand(List args) async { + final command = 'tc ${args.join(' ')}'; + print('Executing: $command'); final result = await Process.run('tc', args); + print('tc exit code: ${result.exitCode}'); + if (result.stdout.toString().isNotEmpty) { + print('tc stdout: ${result.stdout}'); + } + if (result.stderr.toString().isNotEmpty) { + print('tc stderr: ${result.stderr}'); + } if (result.exitCode != 0) { throw Exception('tc command failed: ${result.stderr}'); }