LCOV - code coverage report
Current view: top level - lib/cwtch - ffi.dart (source / functions) Hit Total Coverage
Test: lcov.info Lines: 0 515 0.0 %
Date: 2024-09-23 18:17:55 Functions: 0 0 -

          Line data    Source code
       1             : import 'dart:collection';
       2             : import 'dart:convert';
       3             : import 'dart:ffi';
       4             : import 'dart:io';
       5             : import 'dart:isolate';
       6             : import 'package:cwtch/cwtch/cwtchNotifier.dart';
       7             : import 'package:path/path.dart' as path;
       8             : 
       9             : import 'package:ffi/ffi.dart';
      10             : import 'package:cwtch/cwtch/cwtch.dart';
      11             : 
      12             : import '../config.dart';
      13             : 
      14             : import "package:path/path.dart" show dirname, join;
      15             : 
      16             : /////////////////////
      17             : ///   Cwtch API   ///
      18             : /////////////////////
      19             : 
      20             : typedef start_cwtch_function = Int8 Function(Pointer<Utf8> str, Int32 length, Pointer<Utf8> str2, Int32 length2);
      21             : typedef StartCwtchFn = int Function(Pointer<Utf8> dir, int len, Pointer<Utf8> tor, int torLen);
      22             : 
      23             : typedef void_from_void_funtion = Void Function();
      24             : typedef VoidFromVoidFunction = void Function();
      25             : 
      26             : typedef free_function = Void Function(Pointer<Utf8>);
      27             : typedef FreeFn = void Function(Pointer<Utf8>);
      28             : 
      29             : typedef void_from_string_string_function = Void Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
      30             : typedef VoidFromStringStringFn = void Function(Pointer<Utf8>, int, Pointer<Utf8>, int);
      31             : typedef VoidFromStringFn = void Function(Pointer<Utf8>, int);
      32             : 
      33             : typedef void_from_string_string_string_function = Void Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
      34             : typedef VoidFromStringStringStringFn = void Function(Pointer<Utf8>, int, Pointer<Utf8>, int, Pointer<Utf8>, int);
      35             : 
      36             : typedef void_from_string_string_string_string_function = Void Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
      37             : typedef VoidFromStringStringStringStringFn = void Function(Pointer<Utf8>, int, Pointer<Utf8>, int, Pointer<Utf8>, int, Pointer<Utf8>, int);
      38             : 
      39             : // DownloadFile
      40             : typedef void_from_string_int_string_string_string_function = Void Function(Pointer<Utf8>, Int32, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
      41             : typedef VoidFromStringIntStringStringStringFn = void Function(Pointer<Utf8>, int, int, Pointer<Utf8>, int, Pointer<Utf8>, int, Pointer<Utf8>, int);
      42             : 
      43             : typedef void_from_string_string_int_int_function = Void Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Int64, Int64);
      44             : typedef VoidFromStringStringIntIntFn = void Function(Pointer<Utf8>, int, Pointer<Utf8>, int, int, int);
      45             : 
      46             : typedef void_from_string_bool_bool_bool = Void Function(Pointer<Utf8>, Int32, Bool, Bool, Bool);
      47             : typedef VoidFromStringBoolBoolBool = void Function(Pointer<Utf8>, int, bool, bool, bool);
      48             : 
      49             : typedef void_from_string_string_byte_function = Void Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Int8);
      50             : typedef VoidFromStringStringByteFn = void Function(Pointer<Utf8>, int, Pointer<Utf8>, int, int);
      51             : 
      52             : typedef string_from_string_string_byte_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Int8);
      53             : typedef StringFromStringStringByteFn = Pointer<Utf8> Function(Pointer<Utf8>, int, Pointer<Utf8>, int, int);
      54             : 
      55             : typedef string_to_void_function = Void Function(Pointer<Utf8> str, Int32 length);
      56             : typedef StringFn = void Function(Pointer<Utf8> dir, int);
      57             : 
      58             : typedef string_string_to_void_function = Void Function(Pointer<Utf8> str, Int32 length, Pointer<Utf8> str2, Int32 length2);
      59             : typedef StringStringFn = void Function(Pointer<Utf8>, int, Pointer<Utf8>, int);
      60             : 
      61             : typedef string_string_to_string_function = Pointer<Utf8> Function(Pointer<Utf8> str, Int32 length, Pointer<Utf8> str2, Int32 length2);
      62             : typedef StringFromStringStringFn = Pointer<Utf8> Function(Pointer<Utf8>, int, Pointer<Utf8>, int);
      63             : 
      64             : typedef string_int_to_void_function = Void Function(Pointer<Utf8> str, Int32 length, Int32 handle);
      65             : typedef VoidFromStringIntFn = void Function(Pointer<Utf8>, int, int);
      66             : 
      67             : typedef get_json_blob_string_function = Pointer<Utf8> Function(Pointer<Utf8> str, Int32 length);
      68             : typedef GetJsonBlobStringFn = Pointer<Utf8> Function(Pointer<Utf8> str, int len);
      69             : 
      70             : typedef get_json_blob_from_string_int_string_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Int32, Pointer<Utf8>, Int32);
      71             : typedef GetJsonBlobFromStrIntStrFn = Pointer<Utf8> Function(Pointer<Utf8>, int, int, Pointer<Utf8>, int);
      72             : 
      73             : //func GetMessage(profile_ptr *C.char, profile_len C.int, handle_ptr *C.char, handle_len C.int, message_index C.int) *C.char {
      74             : typedef get_json_blob_from_str_str_int_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Int32);
      75             : typedef GetJsonBlobFromStrStrIntFn = Pointer<Utf8> Function(Pointer<Utf8>, int, Pointer<Utf8>, int, int);
      76             : 
      77             : typedef get_json_blob_from_str_int_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Int32);
      78             : typedef GetJsonBlobFromStrIntFn = Pointer<Utf8> Function(Pointer<Utf8>, int, int);
      79             : 
      80             : typedef get_json_blob_from_str_str_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
      81             : typedef GetJsonBlobFromStrStrFn = Pointer<Utf8> Function(Pointer<Utf8>, int, Pointer<Utf8>, int);
      82             : 
      83             : typedef get_json_blob_from_str_int_int_str_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Int32, Int32, Pointer<Utf8>, Int32);
      84             : typedef GetJsonBlobFromStrIntIntStrFn = Pointer<Utf8> Function(
      85             :   Pointer<Utf8>,
      86             :   int,
      87             :   int,
      88             :   int,
      89             :   Pointer<Utf8>,
      90             :   int,
      91             : );
      92             : 
      93             : typedef get_json_blob_from_str_int_int_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Int32, Int32);
      94             : typedef GetJsonBlobFromStrIntIntFn = Pointer<Utf8> Function(Pointer<Utf8>, int, int, int);
      95             : 
      96             : typedef get_json_blob_from_str_int_int_int_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Int32, Int32, Int32);
      97             : typedef GetJsonBlobFromStrIntIntIntFn = Pointer<Utf8> Function(Pointer<Utf8>, int, int, int, int);
      98             : 
      99             : typedef get_json_blob_from_str_int_string_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Int32, Pointer<Utf8>, Int32);
     100             : typedef GetJsonBlobFromStrIntStringFn = Pointer<Utf8> Function(
     101             :   Pointer<Utf8>,
     102             :   int,
     103             :   int,
     104             :   Pointer<Utf8>,
     105             :   int,
     106             : );
     107             : 
     108             : // func c_GetMessagesByContentHash(profile_ptr *C.char, profile_len C.int, handle_ptr *C.char, handle_len C.int, contenthash_ptr *C.char, contenthash_len C.int) *C.char
     109             : typedef get_json_blob_from_str_str_str_function = Pointer<Utf8> Function(Pointer<Utf8>, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
     110             : typedef GetJsonBlobFromStrStrStrFn = Pointer<Utf8> Function(Pointer<Utf8>, int, Pointer<Utf8>, int, Pointer<Utf8>, int);
     111             : 
     112             : typedef void_from_string_int_string_function = Void Function(Pointer<Utf8>, Int32, Int32, Pointer<Utf8>, Int32);
     113             : typedef VoidFromStringIntStringFn = void Function(Pointer<Utf8>, int, int, Pointer<Utf8>, int);
     114             : 
     115             : typedef void_from_string_int_string_string_function = Void Function(Pointer<Utf8>, Int32, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
     116             : typedef VoidFromStringIntStringStringFn = void Function(Pointer<Utf8>, int, int, Pointer<Utf8>, int, Pointer<Utf8>, int);
     117             : 
     118             : typedef void_from_string_int_int_int_string_string_function = Void Function(Pointer<Utf8>, Int32, Int32, Int32, Int32, Pointer<Utf8>, Int32, Pointer<Utf8>, Int32);
     119             : typedef VoidFromStringIntIntIntStringStringFn = void Function(Pointer<Utf8>, int, int, int, int, Pointer<Utf8>, int, Pointer<Utf8>, int);
     120             : 
     121             : typedef void_from_string_int_int_function = Void Function(Pointer<Utf8>, Int32, Int32, Int32);
     122             : typedef VoidFromStringIntIntFn = void Function(Pointer<Utf8>, int, int, int);
     123             : 
     124             : typedef appbus_events_function = Pointer<Utf8> Function();
     125             : typedef AppbusEventsFn = Pointer<Utf8> Function();
     126             : 
     127             : typedef void_to_string = Pointer<Utf8> Function();
     128             : typedef StringFromVoid = Pointer<Utf8> Function();
     129             : 
     130             : const String UNSUPPORTED_OS = "unsupported-os";
     131             : 
     132             : class CwtchFfi implements Cwtch {
     133             :   late DynamicLibrary library;
     134             :   late CwtchNotifier cwtchNotifier;
     135             :   late Isolate cwtchIsolate;
     136             :   ReceivePort _receivePort = ReceivePort();
     137             :   bool _isL10nInit = false;
     138             :   String _assetsDir = path.join(Directory.current.path, "data", "flutter_assets");
     139             :   String _cwtchDir = "";
     140             : 
     141           0 :   static String getLibraryPath() {
     142           0 :     if (Platform.isWindows) {
     143             :       return "libCwtch.dll";
     144           0 :     } else if (Platform.isLinux) {
     145             :       return "libCwtch.so";
     146           0 :     } else if (Platform.isMacOS) {
     147           0 :       if (Abi.current() == Abi.macosX64) {
     148             :         return "libCwtch.x64.dylib";
     149             :       } else {
     150             :         return "libCwtch.arm64.dylib";
     151             :       }
     152             :     } else {
     153             :       return UNSUPPORTED_OS;
     154             :     }
     155             :   }
     156             : 
     157           0 :   CwtchFfi(CwtchNotifier _cwtchNotifier) {
     158           0 :     String libraryPath = getLibraryPath();
     159           0 :     if (libraryPath == UNSUPPORTED_OS) {
     160           0 :       print("OS ${Platform.operatingSystem} not supported by cwtch/ffi");
     161             :       // emergency, ideally the app stays on splash and just posts the error till user closes
     162           0 :       exit(0);
     163             :     }
     164           0 :     library = DynamicLibrary.open(libraryPath);
     165           0 :     cwtchNotifier = _cwtchNotifier;
     166           0 :     cwtchNotifier.setMessageSeenCallback((String profile, int conversation, DateTime time) => {this.SetConversationAttribute(profile, conversation, LastMessageSeenTimeKey, time.toIso8601String())});
     167             :   }
     168             : 
     169             :   // ignore: non_constant_identifier_names
     170           0 :   Future<void> Start() async {
     171             :     String home = "";
     172             :     String bundledTor = "";
     173           0 :     Map<String, String> envVars = Platform.environment;
     174           0 :     if (Platform.isLinux) {
     175           0 :       home = envVars['HOME'] ?? "";
     176             :       if (EnvironmentConfig.TEST_MODE) {
     177           0 :         _cwtchDir = envVars['CWTCH_HOME']!;
     178             :       } else {
     179           0 :         _cwtchDir = envVars['CWTCH_HOME'] ?? path.join(envVars['HOME']!, ".cwtch");
     180             :       }
     181             : 
     182           0 :       if (await File("linux/Tor/tor").exists()) {
     183             :         bundledTor = "linux/Tor/tor";
     184           0 :       } else if (await File("lib/Tor/tor").exists()) {
     185             :         bundledTor = "lib/Tor/tor";
     186           0 :       } else if (await File(path.join(home, ".local/lib/cwtch/Tor/tor")).exists()) {
     187           0 :         bundledTor = path.join(home, ".local/lib/cwtch/Tor/tor");
     188           0 :         _assetsDir = path.join(home, ".local", "share", "cwtch", "data", "flutter_assets");
     189           0 :       } else if (await File("/usr/lib/cwtch/Tor/tor").exists()) {
     190             :         bundledTor = "/usr/lib/cwtch/Tor/tor";
     191           0 :         _assetsDir = path.join("usr", "share", "cwtch", "data", "flutter_assets");
     192             :       } else {
     193             :         bundledTor = "tor";
     194             :       }
     195           0 :     } else if (Platform.isWindows) {
     196           0 :       _cwtchDir = envVars['CWTCH_DIR'] ?? path.join(envVars['UserProfile']!, ".cwtch");
     197           0 :       String currentTor = path.join(Directory.current.absolute.path, "Tor\\Tor\\tor.exe");
     198           0 :       if (await File(currentTor).exists()) {
     199             :         bundledTor = currentTor;
     200           0 :         _assetsDir = path.join(Directory.current.absolute.path, "data", "flutter_assets");
     201             :       } else {
     202           0 :         String exeDir = path.dirname(Platform.resolvedExecutable);
     203           0 :         bundledTor = path.join(exeDir, "Tor\\Tor\\tor.exe");
     204           0 :         _assetsDir = path.join(exeDir, "data", "flutter_assets");
     205             :       }
     206           0 :     } else if (Platform.isMacOS) {
     207           0 :       _cwtchDir = envVars['CWTCH_HOME'] ?? path.join(envVars['HOME']!, "Library/Application Support/Cwtch");
     208           0 :       _assetsDir = "/Applications/Cwtch.app/Contents/Frameworks/App.framework/Versions/Current/Resources/flutter_assets/";
     209           0 :       if (await File("Cwtch.app/Contents/MacOS/Tor/tor").exists()) {
     210             :         bundledTor = "Cwtch.app/Contents/MacOS/Tor/tor";
     211           0 :         _assetsDir = "Cwtch.app/Contents/Frameworks/App.framework/Versions/Current/Resources/flutter_assets/";
     212           0 :       } else if (await File("/Applications/Cwtch.app/Contents/MacOS/Tor/tor").exists()) {
     213             :         bundledTor = "/Applications/Cwtch.app/Contents/MacOS/Tor/tor";
     214           0 :       } else if (await File("/Volumes/Cwtch/Cwtch.app/Contents/MacOS/Tor/tor").exists()) {
     215             :         bundledTor = "/Volumes/Cwtch/Cwtch.app/Contents/MacOS/Tor/tor";
     216           0 :       } else if (await File("/Applications/Tor Browser.app/Contents/MacOS/Tor/tor").exists()) {
     217             :         bundledTor = "/Applications/Tor Browser.app/Contents/MacOS/Tor/tor";
     218           0 :         print("We couldn't find Tor in the Cwtch app directory, however we can fall back to the Tor Browser binary");
     219             :       } else {
     220           0 :         var splitPath = path.split(dirname(Platform.script.path));
     221           0 :         if (splitPath[0] == "/" && splitPath[1] == "Applications") {
     222           0 :           var appName = splitPath[2];
     223           0 :           print("We're running in /Applications in a non standard app name: $appName");
     224           0 :           if (await File("/Applications/$appName/Contents/MacOS/Tor/tor").exists()) {
     225           0 :             bundledTor = "/Applications/$appName/Contents/MacOS/Tor/tor";
     226             :           }
     227             :         }
     228             :       }
     229             :     }
     230             : 
     231             :     // the first Cwtch MacOS release (1.2) accidently was a dev build
     232             :     // we need to temporarily remedy this for a release or two then delete
     233             :     // if macOs and release build and no profile and is dev profile
     234             :     // copy dev profile to release profile
     235           0 :     if (Platform.isMacOS && EnvironmentConfig.BUILD_VER != dev_version) {
     236           0 :       var devProfileExists = await Directory(path.join(_cwtchDir, "dev", "profiles")).exists();
     237           0 :       var releaseProfileExists = await Directory(path.join(_cwtchDir, "profiles")).exists();
     238             :       if (devProfileExists && !releaseProfileExists) {
     239           0 :         print("MacOS one time dev -> release profile migration...");
     240           0 :         await Process.run("cp", ["-r", "-p", path.join(_cwtchDir, "dev", "profiles"), _cwtchDir]);
     241           0 :         await Process.run("cp", ["-r", "-p", path.join(_cwtchDir, "dev", "SALT"), _cwtchDir]);
     242           0 :         await Process.run("cp", ["-r", "-p", path.join(_cwtchDir, "dev", "ui.globals"), _cwtchDir]);
     243             :       }
     244             :     }
     245             : 
     246           0 :     if (EnvironmentConfig.BUILD_VER == dev_version) {
     247           0 :       _cwtchDir = path.join(_cwtchDir, "dev");
     248             :     }
     249             : 
     250           0 :     print("StartCwtch( cwtchdir: $_cwtchDir, torPath: $bundledTor )");
     251             : 
     252           0 :     var startCwtchC = library.lookup<NativeFunction<start_cwtch_function>>("c_StartCwtch");
     253             :     // ignore: non_constant_identifier_names
     254             :     final StartCwtch = startCwtchC.asFunction<StartCwtchFn>();
     255             : 
     256           0 :     final utf8CwtchDir = _cwtchDir.toNativeUtf8();
     257           0 :     StartCwtch(utf8CwtchDir, utf8CwtchDir.length, bundledTor.toNativeUtf8(), bundledTor.length);
     258           0 :     malloc.free(utf8CwtchDir);
     259             : 
     260             :     // Spawn an isolate to listen to events from libcwtch-go and then dispatch them when received on main thread to cwtchNotifier
     261           0 :     cwtchIsolate = await Isolate.spawn(_checkAppbusEvents, _receivePort.sendPort);
     262           0 :     _receivePort.listen((message) {
     263           0 :       var env = jsonDecode(message);
     264           0 :       cwtchNotifier.handleMessage(env["EventType"], env["Data"]);
     265             :     });
     266             :   }
     267             : 
     268           0 :   String getAssetsDir() {
     269           0 :     return _assetsDir;
     270             :   }
     271             : 
     272           0 :   Future<String> getCwtchDir() async {
     273           0 :     return _cwtchDir;
     274             :   }
     275             : 
     276             :   // Called on object being disposed to (presumably on app close) to close the isolate that's listening to libcwtch-go events
     277           0 :   @override
     278             :   void dispose() {
     279           0 :     EnvironmentConfig.debugLog("tearing down cwtch FFI isolate");
     280           0 :     library.close();
     281           0 :     cwtchIsolate.kill(priority: Isolate.immediate);
     282             :   }
     283             : 
     284             :   // Entry point for an isolate to listen to a stream of events pulled from libcwtch-go and return them on the sendPort
     285           0 :   static void _checkAppbusEvents(SendPort sendPort) async {
     286           0 :     var stream = pollAppbusEvents();
     287           0 :     await for (var value in stream) {
     288           0 :       sendPort.send(value);
     289             :     }
     290           0 :     print("checkAppBusEvents finished...");
     291             :   }
     292             : 
     293             :   // Steam of appbus events. Call blocks in libcwtch-go GetAppbusEvent.  Static so the isolate can use it
     294           0 :   static Stream<String> pollAppbusEvents() async* {
     295             :     late DynamicLibrary library = DynamicLibrary.open(getLibraryPath());
     296             : 
     297           0 :     var getAppbusEventC = library.lookup<NativeFunction<appbus_events_function>>("c_GetAppBusEvent");
     298             :     // ignore: non_constant_identifier_names
     299             :     final GetAppbusEvent = getAppbusEventC.asFunction<AppbusEventsFn>();
     300             : 
     301             :     // Embedded Version of _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved
     302           0 :     var free = library.lookup<NativeFunction<free_function>>("c_FreePointer");
     303             :     final Free = free.asFunction<FreeFn>();
     304             : 
     305             :     // ignore: non_constant_identifier_names
     306           0 :     final GetAppBusEvent = () {
     307             :       // ignore: non_constant_identifier_names
     308           0 :       Pointer<Utf8> result = GetAppbusEvent();
     309           0 :       String event = result.toDartString();
     310           0 :       Free(result);
     311             :       return event;
     312             :     };
     313             : 
     314             :     while (true) {
     315           0 :       final event = GetAppBusEvent();
     316             : 
     317           0 :       if (event.startsWith("{\"EventType\":\"Shutdown\"")) {
     318           0 :         print("Shutting down isolate thread: $event");
     319             :         return;
     320             :       }
     321             :       yield event;
     322             :     }
     323             :   }
     324             : 
     325             :   // ignore: non_constant_identifier_names
     326           0 :   Future<String> CreateProfile(String nick, String pass, bool autostart) async {
     327           0 :     var createProfileC = library.lookup<NativeFunction<string_from_string_string_byte_function>>("c_CreateProfile");
     328             :     // ignore: non_constant_identifier_names
     329             :     final CreateProfile = createProfileC.asFunction<StringFromStringStringByteFn>();
     330           0 :     final utf8nick = nick.toNativeUtf8();
     331           0 :     final ut8pass = pass.toNativeUtf8();
     332           0 :     Pointer<Utf8> resultUnsafe =  CreateProfile(utf8nick, utf8nick.length, ut8pass, ut8pass.length, autostart ? 1 : 0);
     333           0 :     String resultSafe = resultUnsafe.toDartString();
     334           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(resultUnsafe);
     335           0 :     malloc.free(utf8nick);
     336           0 :     malloc.free(ut8pass);
     337             :     return resultSafe;
     338             :   }
     339             : 
     340             :   // ignore: non_constant_identifier_names
     341           0 :   void ActivatePeerEngine(String profile) {
     342           0 :     var activatePeerEngineC = library.lookup<NativeFunction<string_to_void_function>>("c_ActivatePeerEngine");
     343             :     final ActivatePeerEngine = activatePeerEngineC.asFunction<StringFn>();
     344           0 :     final ut8profile = profile.toNativeUtf8();
     345           0 :     ActivatePeerEngine(ut8profile, ut8profile.length);
     346           0 :     malloc.free(ut8profile);
     347             :   }
     348             : 
     349             :   // ignore: non_constant_identifier_names
     350           0 :   void DeactivatePeerEngine(String profile) {
     351           0 :     var deactivatePeerEngineC = library.lookup<NativeFunction<string_to_void_function>>("c_DeactivatePeerEngine");
     352             :     final DeactivatePeerEngine = deactivatePeerEngineC.asFunction<StringFn>();
     353           0 :     final ut8profile = profile.toNativeUtf8();
     354           0 :     DeactivatePeerEngine(ut8profile, ut8profile.length);
     355           0 :     malloc.free(ut8profile);
     356             :   }
     357             : 
     358             :   // ignore: non_constant_identifier_names
     359           0 :   void LoadProfiles(String pass) {
     360           0 :     var loadProfileC = library.lookup<NativeFunction<string_to_void_function>>("c_LoadProfiles");
     361             :     // ignore: non_constant_identifier_names
     362             :     final LoadProfiles = loadProfileC.asFunction<StringFn>();
     363           0 :     final ut8pass = pass.toNativeUtf8();
     364           0 :     LoadProfiles(ut8pass, ut8pass.length);
     365           0 :     malloc.free(ut8pass);
     366             :   }
     367             : 
     368             :   // ignore: non_constant_identifier_names
     369           0 :   Future<String> GetMessage(String profile, int handle, int index) async {
     370           0 :     var getMessageC = library.lookup<NativeFunction<get_json_blob_from_str_int_int_function>>("c_GetMessage");
     371             :     // ignore: non_constant_identifier_names
     372             :     final GetMessage = getMessageC.asFunction<GetJsonBlobFromStrIntIntFn>();
     373           0 :     final utf8profile = profile.toNativeUtf8();
     374           0 :     Pointer<Utf8> jsonMessageBytes = GetMessage(utf8profile, utf8profile.length, handle, index);
     375           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     376           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     377           0 :     malloc.free(utf8profile);
     378             :     return jsonMessage;
     379             :   }
     380             : 
     381             :   // ignore: non_constant_identifier_names
     382           0 :   Future<dynamic> GetMessages(String profile, int handle, int index, int count) async {
     383           0 :     var getMessagesC = library.lookup<NativeFunction<get_json_blob_from_str_int_int_int_function>>("c_GetMessages");
     384             :     // ignore: non_constant_identifier_names
     385             :     final GetMessages = getMessagesC.asFunction<GetJsonBlobFromStrIntIntIntFn>();
     386           0 :     final utf8profile = profile.toNativeUtf8();
     387           0 :     Pointer<Utf8> jsonMessageBytes = GetMessages(utf8profile, utf8profile.length, handle, index, count);
     388           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     389           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     390           0 :     malloc.free(utf8profile);
     391             : 
     392             :     return jsonMessage;
     393             :   }
     394             : 
     395           0 :   @override
     396             :   // ignore: non_constant_identifier_names
     397             :   void AcceptContact(String profileOnion, int contactHandle) {
     398           0 :     var acceptContact = library.lookup<NativeFunction<string_int_to_void_function>>("c_AcceptConversation");
     399             :     // ignore: non_constant_identifier_names
     400             :     final AcceptContact = acceptContact.asFunction<VoidFromStringIntFn>();
     401           0 :     final u1 = profileOnion.toNativeUtf8();
     402           0 :     AcceptContact(u1, u1.length, contactHandle);
     403           0 :     malloc.free(u1);
     404             :   }
     405             : 
     406           0 :   @override
     407             :   // ignore: non_constant_identifier_names
     408             :   void BlockContact(String profileOnion, int contactHandle) {
     409           0 :     var blockContact = library.lookup<NativeFunction<string_int_to_void_function>>("c_BlockConversation");
     410             :     // ignore: non_constant_identifier_names
     411             :     final BlockContact = blockContact.asFunction<VoidFromStringIntFn>();
     412           0 :     final u1 = profileOnion.toNativeUtf8();
     413           0 :     BlockContact(u1, u1.length, contactHandle);
     414           0 :     malloc.free(u1);
     415             :   }
     416             : 
     417           0 :   @override
     418             :   // ignore: non_constant_identifier_names
     419             :   void UnblockContact(String profileOnion, int contactHandle) {
     420           0 :     var unblockContact = library.lookup<NativeFunction<string_int_to_void_function>>("c_UnblockConversation");
     421             :     // ignore: non_constant_identifier_names
     422             :     final UnblockContact = unblockContact.asFunction<VoidFromStringIntFn>();
     423           0 :     final u1 = profileOnion.toNativeUtf8();
     424           0 :     UnblockContact(u1, u1.length, contactHandle);
     425           0 :     malloc.free(u1);
     426             :   }
     427             : 
     428           0 :   @override
     429             :   // ignore: non_constant_identifier_names
     430             :   Future<dynamic> SendMessage(String profileOnion, int contactHandle, String message) async {
     431           0 :     var sendMessage = library.lookup<NativeFunction<get_json_blob_from_string_int_string_function>>("c_SendMessage");
     432             :     // ignore: non_constant_identifier_names
     433             :     final SendMessage = sendMessage.asFunction<GetJsonBlobFromStrIntStrFn>();
     434           0 :     final u1 = profileOnion.toNativeUtf8();
     435           0 :     final u3 = message.toNativeUtf8();
     436           0 :     Pointer<Utf8> jsonMessageBytes = SendMessage(u1, u1.length, contactHandle, u3, u3.length);
     437           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     438           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     439           0 :     malloc.free(u1);
     440           0 :     malloc.free(u3);
     441             :     return jsonMessage;
     442             :   }
     443             : 
     444           0 :   @override
     445             :   // ignore: non_constant_identifier_names
     446             :   Future<dynamic> SendInvitation(String profileOnion, int contactHandle, int target) async {
     447           0 :     var sendInvitation = library.lookup<NativeFunction<get_json_blob_from_str_int_int_function>>("c_SendInviteMessage");
     448             :     // ignore: non_constant_identifier_names
     449             :     final SendInvitation = sendInvitation.asFunction<GetJsonBlobFromStrIntIntFn>();
     450           0 :     final u1 = profileOnion.toNativeUtf8();
     451           0 :     Pointer<Utf8> jsonMessageBytes = SendInvitation(u1, u1.length, contactHandle, target);
     452           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     453           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     454           0 :     malloc.free(u1);
     455             :     return jsonMessage;
     456             :   }
     457             : 
     458           0 :   @override
     459             :   // ignore: non_constant_identifier_names
     460             :   Future<dynamic> ShareFile(String profileOnion, int contactHandle, String filepath) async {
     461           0 :     var shareFile = library.lookup<NativeFunction<get_json_blob_from_string_int_string_function>>("c_ShareFile");
     462             :     // ignore: non_constant_identifier_names
     463             :     final ShareFile = shareFile.asFunction<GetJsonBlobFromStrIntStrFn>();
     464           0 :     final u1 = profileOnion.toNativeUtf8();
     465           0 :     final u3 = filepath.toNativeUtf8();
     466           0 :     Pointer<Utf8> jsonMessageBytes = ShareFile(u1, u1.length, contactHandle, u3, u3.length);
     467           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     468           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     469           0 :     malloc.free(u1);
     470           0 :     malloc.free(u3);
     471             :     return jsonMessage;
     472             :   }
     473             : 
     474           0 :   @override
     475             :   // ignore: non_constant_identifier_names
     476             :   void DownloadFile(String profileOnion, int contactHandle, String filepath, String manifestpath, String filekey) {
     477           0 :     var dlFile = library.lookup<NativeFunction<void_from_string_int_string_string_string_function>>("c_DownloadFileDefaultLimit");
     478             :     // ignore: non_constant_identifier_names
     479             :     final DownloadFile = dlFile.asFunction<VoidFromStringIntStringStringStringFn>();
     480           0 :     final u1 = profileOnion.toNativeUtf8();
     481           0 :     final u3 = filepath.toNativeUtf8();
     482           0 :     final u4 = manifestpath.toNativeUtf8();
     483           0 :     final u5 = filekey.toNativeUtf8();
     484           0 :     DownloadFile(u1, u1.length, contactHandle, u3, u3.length, u4, u4.length, u5, u5.length);
     485           0 :     malloc.free(u1);
     486           0 :     malloc.free(u3);
     487           0 :     malloc.free(u4);
     488           0 :     malloc.free(u5);
     489             :   }
     490             : 
     491           0 :   @override
     492             :   // ignore: non_constant_identifier_names
     493             :   void CreateDownloadableFile(String profileOnion, int contactHandle, String filenameSuggestion, String filekey, String manifestPath) {
     494             :     // android only - do nothing
     495             :   }
     496             : 
     497             :   // ignore: non_constant_identifier_names
     498           0 :   void ExportPreviewedFile(String sourceFile, String suggestion) {
     499             :     // android only - do nothing
     500             :   }
     501             : 
     502           0 :   @override
     503             :   // ignore: non_constant_identifier_names
     504             :   void CheckDownloadStatus(String profileOnion, String fileKey) {
     505           0 :     var checkDownloadStatus = library.lookup<NativeFunction<string_string_to_void_function>>("c_CheckDownloadStatus");
     506             :     // ignore: non_constant_identifier_names
     507             :     final CheckDownloadStatus = checkDownloadStatus.asFunction<VoidFromStringStringFn>();
     508           0 :     final u1 = profileOnion.toNativeUtf8();
     509           0 :     final u2 = fileKey.toNativeUtf8();
     510           0 :     CheckDownloadStatus(u1, u1.length, u2, u2.length);
     511           0 :     malloc.free(u1);
     512           0 :     malloc.free(u2);
     513             :   }
     514             : 
     515           0 :   @override
     516             :   // ignore: non_constant_identifier_names
     517             :   void VerifyOrResumeDownload(String profileOnion, int contactHandle, String filekey) {
     518           0 :     var fn = library.lookup<NativeFunction<void_from_string_int_string_function>>("c_VerifyOrResumeDownloadDefaultLimit");
     519             :     // ignore: non_constant_identifier_names
     520             :     final VerifyOrResumeDownload = fn.asFunction<VoidFromStringIntStringFn>();
     521           0 :     final u1 = profileOnion.toNativeUtf8();
     522           0 :     final u3 = filekey.toNativeUtf8();
     523           0 :     VerifyOrResumeDownload(u1, u1.length, contactHandle, u3, u3.length);
     524           0 :     malloc.free(u1);
     525           0 :     malloc.free(u3);
     526             :   }
     527             : 
     528           0 :   @override
     529             :   // ignore: non_constant_identifier_names
     530             :   void ResetTor() {
     531           0 :     var resetTor = library.lookup<NativeFunction<Void Function()>>("c_ResetTor");
     532             :     // ignore: non_constant_identifier_names
     533             :     final ResetTor = resetTor.asFunction<void Function()>();
     534           0 :     ResetTor();
     535             :   }
     536             : 
     537           0 :   @override
     538             :   // ignore: non_constant_identifier_names
     539             :   Future<dynamic> ImportBundle(String profileOnion, String bundle) async {
     540           0 :     var importBundle = library.lookup<NativeFunction<string_string_to_string_function>>("c_ImportBundle");
     541             :     // ignore: non_constant_identifier_names
     542             :     final ImportBundle = importBundle.asFunction<StringFromStringStringFn>();
     543           0 :     final u1 = profileOnion.toNativeUtf8();
     544           0 :     final u2 = bundle.toNativeUtf8();
     545           0 :     Pointer<Utf8> responsePtr = ImportBundle(u1, u1.length, u2, u2.length);
     546           0 :     String response = responsePtr.toDartString();
     547           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(responsePtr);
     548           0 :     malloc.free(u1);
     549           0 :     malloc.free(u2);
     550             :     return response;
     551             :   }
     552             : 
     553           0 :   @override
     554             :   // ignore: non_constant_identifier_names
     555             :   void CreateGroup(String profileOnion, String server, String groupName) {
     556           0 :     var createGroup = library.lookup<NativeFunction<void_from_string_string_string_function>>("c_StartGroup");
     557             :     // ignore: non_constant_identifier_names
     558             :     final CreateGroup = createGroup.asFunction<VoidFromStringStringStringFn>();
     559           0 :     final u1 = profileOnion.toNativeUtf8();
     560           0 :     final u3 = server.toNativeUtf8();
     561           0 :     final u2 = groupName.toNativeUtf8();
     562           0 :     CreateGroup(u1, u1.length, u2, u2.length, u3, u3.length);
     563             : 
     564           0 :     malloc.free(u1);
     565           0 :     malloc.free(u2);
     566           0 :     malloc.free(u3);
     567             :   }
     568             : 
     569           0 :   @override
     570             :   // ignore: non_constant_identifier_names
     571             :   void ArchiveConversation(String profileOnion, int handle) {
     572           0 :     var archiveConversation = library.lookup<NativeFunction<string_int_to_void_function>>("c_ArchiveConversation");
     573             :     // ignore: non_constant_identifier_names
     574             :     final ArchiveConversation = archiveConversation.asFunction<VoidFromStringIntFn>();
     575           0 :     final u1 = profileOnion.toNativeUtf8();
     576           0 :     ArchiveConversation(u1, u1.length, handle);
     577           0 :     malloc.free(u1);
     578             :   }
     579             : 
     580           0 :   @override
     581             :   // ignore: non_constant_identifier_names
     582             :   void DeleteContact(String profileOnion, int handle) {
     583           0 :     var deleteContact = library.lookup<NativeFunction<string_int_to_void_function>>("c_DeleteConversation");
     584             :     // ignore: non_constant_identifier_names
     585             :     final DeleteContact = deleteContact.asFunction<VoidFromStringIntFn>();
     586           0 :     final u1 = profileOnion.toNativeUtf8();
     587           0 :     DeleteContact(u1, u1.length, handle);
     588           0 :     malloc.free(u1);
     589             :   }
     590             : 
     591           0 :   @override
     592             :   // ignore: non_constant_identifier_names
     593             :   void DeleteProfile(String onion, String currentPassword) {
     594           0 :     var deleteprofile = library.lookup<NativeFunction<string_string_to_void_function>>("c_DeleteProfile");
     595             :     // ignore: non_constant_identifier_names
     596             :     final DeleteProfile = deleteprofile.asFunction<VoidFromStringStringFn>();
     597           0 :     final u1 = onion.toNativeUtf8();
     598           0 :     final u2 = currentPassword.toNativeUtf8();
     599           0 :     DeleteProfile(u1, u1.length, u2, u2.length);
     600           0 :     malloc.free(u1);
     601           0 :     malloc.free(u2);
     602             :   }
     603             : 
     604           0 :   @override
     605             :   // ignore: non_constant_identifier_names
     606             :   void SetProfileAttribute(String profile, String key, String val) {
     607           0 :     var setProfileAttribute = library.lookup<NativeFunction<void_from_string_string_string_function>>("c_SetProfileAttribute");
     608             :     // ignore: non_constant_identifier_names
     609             :     final SetProfileAttribute = setProfileAttribute.asFunction<VoidFromStringStringStringFn>();
     610           0 :     final u1 = profile.toNativeUtf8();
     611           0 :     final u2 = key.toNativeUtf8();
     612           0 :     final u3 = val.toNativeUtf8();
     613           0 :     SetProfileAttribute(u1, u1.length, u2, u2.length, u3, u3.length);
     614           0 :     malloc.free(u1);
     615           0 :     malloc.free(u2);
     616           0 :     malloc.free(u3);
     617             :   }
     618             : 
     619           0 :   @override
     620             :   // ignore: non_constant_identifier_names
     621             :   void SetConversationAttribute(String profile, int contact, String key, String val) {
     622           0 :     var setContactAttribute = library.lookup<NativeFunction<void_from_string_int_string_string_function>>("c_SetConversationAttribute");
     623             :     // ignore: non_constant_identifier_names
     624             :     final SetContactAttribute = setContactAttribute.asFunction<VoidFromStringIntStringStringFn>();
     625           0 :     final u1 = profile.toNativeUtf8();
     626           0 :     final u3 = key.toNativeUtf8();
     627           0 :     final u4 = val.toNativeUtf8();
     628           0 :     SetContactAttribute(u1, u1.length, contact, u3, u3.length, u4, u4.length);
     629           0 :     malloc.free(u1);
     630           0 :     malloc.free(u3);
     631           0 :     malloc.free(u4);
     632             :   }
     633             : 
     634           0 :   @override
     635             :   // ignore: non_constant_identifier_names
     636             :   void SetMessageAttribute(String profile, int conversation, int channel, int message, String key, String val) {
     637           0 :     var setMessageAttribute = library.lookup<NativeFunction<void_from_string_int_int_int_string_string_function>>("c_UpdateMessageAttribute");
     638             :     // ignore: non_constant_identifier_names
     639             :     final SetMessageAttribute = setMessageAttribute.asFunction<VoidFromStringIntIntIntStringStringFn>();
     640           0 :     final u1 = profile.toNativeUtf8();
     641           0 :     final u3 = key.toNativeUtf8();
     642           0 :     final u4 = val.toNativeUtf8();
     643           0 :     SetMessageAttribute(u1, u1.length, conversation, channel, message, u3, u3.length, u4, u4.length);
     644           0 :     malloc.free(u1);
     645           0 :     malloc.free(u3);
     646           0 :     malloc.free(u4);
     647             :   }
     648             : 
     649           0 :   @override
     650             :   // ignore: non_constant_identifier_names
     651             :   void LoadServers(String password) {
     652           0 :     var loadServers = library.lookup<NativeFunction<string_to_void_function>>("c_LoadServers");
     653             :     // ignore: non_constant_identifier_names
     654             :     final LoadServers = loadServers.asFunction<StringFn>();
     655           0 :     final u1 = password.toNativeUtf8();
     656           0 :     LoadServers(u1, u1.length);
     657           0 :     malloc.free(u1);
     658             :   }
     659             : 
     660           0 :   @override
     661             :   // ignore: non_constant_identifier_names
     662             :   void CreateServer(String password, String description, bool autostart) {
     663           0 :     var createServer = library.lookup<NativeFunction<void_from_string_string_byte_function>>("c_CreateServer");
     664             :     // ignore: non_constant_identifier_names
     665             :     final CreateServer = createServer.asFunction<VoidFromStringStringByteFn>();
     666           0 :     final u1 = password.toNativeUtf8();
     667           0 :     final u2 = description.toNativeUtf8();
     668           0 :     CreateServer(u1, u1.length, u2, u2.length, autostart ? 1 : 0);
     669           0 :     malloc.free(u1);
     670           0 :     malloc.free(u2);
     671             :   }
     672             : 
     673           0 :   @override
     674             :   // ignore: non_constant_identifier_names
     675             :   void DeleteServer(String serverOnion, String password) {
     676           0 :     var deleteServer = library.lookup<NativeFunction<string_string_to_void_function>>("c_DeleteServer");
     677             :     // ignore: non_constant_identifier_names
     678             :     final DeleteServer = deleteServer.asFunction<VoidFromStringStringFn>();
     679           0 :     final u1 = serverOnion.toNativeUtf8();
     680           0 :     final u2 = password.toNativeUtf8();
     681           0 :     DeleteServer(u1, u1.length, u2, u2.length);
     682           0 :     malloc.free(u1);
     683           0 :     malloc.free(u2);
     684             :   }
     685             : 
     686           0 :   @override
     687             :   // ignore: non_constant_identifier_names
     688             :   void LaunchServers() {
     689           0 :     var launchServers = library.lookup<NativeFunction<Void Function()>>("c_LaunchServers");
     690             :     // ignore: non_constant_identifier_names
     691             :     final LaunchServers = launchServers.asFunction<void Function()>();
     692           0 :     LaunchServers();
     693             :   }
     694             : 
     695           0 :   @override
     696             :   // ignore: non_constant_identifier_names
     697             :   void LaunchServer(String serverOnion) {
     698           0 :     var launchServer = library.lookup<NativeFunction<string_to_void_function>>("c_LaunchServer");
     699             :     // ignore: non_constant_identifier_names
     700             :     final LaunchServer = launchServer.asFunction<StringFn>();
     701           0 :     final u1 = serverOnion.toNativeUtf8();
     702           0 :     LaunchServer(u1, u1.length);
     703           0 :     malloc.free(u1);
     704             :   }
     705             : 
     706           0 :   @override
     707             :   // ignore: non_constant_identifier_names
     708             :   void StopServer(String serverOnion) {
     709           0 :     var shutdownServer = library.lookup<NativeFunction<string_to_void_function>>("c_StopServer");
     710             :     // ignore: non_constant_identifier_names
     711             :     final ShutdownServer = shutdownServer.asFunction<StringFn>();
     712           0 :     final u1 = serverOnion.toNativeUtf8();
     713           0 :     ShutdownServer(u1, u1.length);
     714           0 :     malloc.free(u1);
     715             :   }
     716             : 
     717           0 :   @override
     718             :   // ignore: non_constant_identifier_names
     719             :   void StopServers() {
     720           0 :     var shutdownServers = library.lookup<NativeFunction<Void Function()>>("c_StopServers");
     721             :     // ignore: non_constant_identifier_names
     722             :     final ShutdownServers = shutdownServers.asFunction<void Function()>();
     723           0 :     ShutdownServers();
     724             :   }
     725             : 
     726           0 :   @override
     727             :   // ignore: non_constant_identifier_names
     728             :   void DestroyServers() {
     729           0 :     var destroyServers = library.lookup<NativeFunction<Void Function()>>("c_DestroyServers");
     730             :     // ignore: non_constant_identifier_names
     731             :     final DestroyServers = destroyServers.asFunction<void Function()>();
     732           0 :     DestroyServers();
     733             :   }
     734             : 
     735           0 :   @override
     736             :   // ignore: non_constant_identifier_names
     737             :   void SetServerAttribute(String serverOnion, String key, String val) {
     738           0 :     var setServerAttribute = library.lookup<NativeFunction<void_from_string_string_string_function>>("c_SetServerAttribute");
     739             :     // ignore: non_constant_identifier_names
     740             :     final SetServerAttribute = setServerAttribute.asFunction<VoidFromStringStringStringFn>();
     741           0 :     final u1 = serverOnion.toNativeUtf8();
     742           0 :     final u2 = key.toNativeUtf8();
     743           0 :     final u3 = val.toNativeUtf8();
     744           0 :     SetServerAttribute(u1, u1.length, u2, u2.length, u3, u3.length);
     745           0 :     malloc.free(u1);
     746           0 :     malloc.free(u2);
     747           0 :     malloc.free(u3);
     748             :   }
     749             : 
     750           0 :   @override
     751             :   // ignore: non_constant_identifier_names
     752             :   Future<void> Shutdown() async {
     753           0 :     var shutdown = library.lookup<NativeFunction<void_from_void_funtion>>("c_ShutdownCwtch");
     754             :     // ignore: non_constant_identifier_names
     755             : 
     756             :     // Shutdown Cwtch + Tor...
     757             :     // ignore: non_constant_identifier_names
     758             :     final Shutdown = shutdown.asFunction<VoidFromVoidFunction>();
     759           0 :     Shutdown();
     760             : 
     761             :     // Kill our Isolate
     762           0 :     cwtchIsolate.kill(priority: Isolate.immediate);
     763           0 :     print("Isolate killed");
     764             : 
     765           0 :     _receivePort.close();
     766           0 :     print("Receive Port Closed");
     767             :   }
     768             : 
     769           0 :   @override
     770             :   // ignore: non_constant_identifier_names
     771             :   Future GetMessageByContentHash(String profile, int handle, String contentHash) async {
     772           0 :     var getMessagesByContentHashC = library.lookup<NativeFunction<get_json_blob_from_str_int_string_function>>("c_GetMessageByContentHash");
     773             :     // ignore: non_constant_identifier_names
     774             :     final GetMessagesByContentHash = getMessagesByContentHashC.asFunction<GetJsonBlobFromStrIntStringFn>();
     775           0 :     final utf8profile = profile.toNativeUtf8();
     776           0 :     final utf8contentHash = contentHash.toNativeUtf8();
     777           0 :     Pointer<Utf8> jsonMessageBytes = GetMessagesByContentHash(utf8profile, utf8profile.length, handle, utf8contentHash, utf8contentHash.length);
     778           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     779             : 
     780           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     781           0 :     malloc.free(utf8profile);
     782           0 :     malloc.free(utf8contentHash);
     783             :     return jsonMessage;
     784             :   }
     785             : 
     786             :   // ignore: non_constant_identifier_names
     787             :   // Incredibly dangerous function which invokes a free in libCwtch, should only be used
     788             :   // as documented in `MEMORY.md` in libCwtch repo.
     789           0 :   void _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(Pointer<Utf8> ptr) {
     790           0 :     var free = library.lookup<NativeFunction<free_function>>("c_FreePointer");
     791             :     final Free = free.asFunction<FreeFn>();
     792           0 :     Free(ptr);
     793             :   }
     794             : 
     795           0 :   @override
     796             :   String? defaultDownloadPath() {
     797           0 :     Map<String, String> envVars = Platform.environment;
     798           0 :     String nominalPath = path.join(envVars[Platform.isWindows ? 'UserProfile' : 'HOME']!, "Downloads");
     799           0 :     if (Directory(nominalPath).existsSync() == false) {
     800           0 :       return Directory.current.path;
     801             :     }
     802             :     return nominalPath;
     803             :   }
     804             : 
     805           0 :   @override
     806             :   // ignore: non_constant_identifier_names
     807             :   Future<String> GetMessageByID(String profile, int handle, int index) async {
     808           0 :     var getMessageC = library.lookup<NativeFunction<get_json_blob_from_str_int_int_function>>("c_GetMessageById");
     809             :     // ignore: non_constant_identifier_names
     810             :     final GetMessage = getMessageC.asFunction<GetJsonBlobFromStrIntIntFn>();
     811           0 :     final utf8profile = profile.toNativeUtf8();
     812           0 :     Pointer<Utf8> jsonMessageBytes = GetMessage(utf8profile, utf8profile.length, handle, index);
     813           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     814           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     815           0 :     malloc.free(utf8profile);
     816             :     return jsonMessage;
     817             :   }
     818             : 
     819           0 :   @override
     820             :   // ignore: non_constant_identifier_names
     821             :   void ChangePassword(String profile, String pass, String newpass, String newpassAgain) {
     822           0 :     var changePasswordC = library.lookup<NativeFunction<void_from_string_string_string_string_function>>("c_ChangePassword");
     823             :     // ignore: non_constant_identifier_names
     824             :     final ChangePasswordFn = changePasswordC.asFunction<VoidFromStringStringStringStringFn>();
     825           0 :     final utf8profile = profile.toNativeUtf8();
     826           0 :     final utf8pass = pass.toNativeUtf8();
     827           0 :     final utf8newpass = newpass.toNativeUtf8();
     828           0 :     final utf8newpasssagain = newpassAgain.toNativeUtf8();
     829           0 :     ChangePasswordFn(utf8profile, utf8profile.length, utf8pass, utf8pass.length, utf8newpass, utf8newpass.length, utf8newpasssagain, utf8newpasssagain.length);
     830           0 :     malloc.free(utf8profile);
     831           0 :     malloc.free(utf8pass);
     832           0 :     malloc.free(utf8newpass);
     833           0 :     malloc.free(utf8newpasssagain);
     834             :   }
     835             : 
     836           0 :   @override
     837             :   bool isL10nInit() {
     838           0 :     return _isL10nInit;
     839             :   }
     840             : 
     841           0 :   @override
     842             :   void l10nInit(String notificationSimple, String notificationConversationInfo) {
     843           0 :     cwtchNotifier.l10nInit(notificationSimple, notificationConversationInfo);
     844           0 :     _isL10nInit = true;
     845             :   }
     846             : 
     847           0 :   @override
     848             :   // ignore: non_constant_identifier_names
     849             :   void ExportProfile(String profile, String file) {
     850           0 :     final utf8profile = profile.toNativeUtf8();
     851           0 :     final utf8file = file.toNativeUtf8();
     852           0 :     var exportProfileC = library.lookup<NativeFunction<void_from_string_string_function>>("c_ExportProfile");
     853             :     // ignore: non_constant_identifier_names
     854             :     final ExportProfileFn = exportProfileC.asFunction<VoidFromStringStringFn>();
     855           0 :     ExportProfileFn(utf8profile, utf8profile.length, utf8file, utf8file.length);
     856           0 :     malloc.free(utf8profile);
     857           0 :     malloc.free(utf8file);
     858             :   }
     859             : 
     860           0 :   @override
     861             :   // ignore: non_constant_identifier_names
     862             :   Future<String> ImportProfile(String file, String pass) async {
     863           0 :     final utf8pass = pass.toNativeUtf8();
     864           0 :     final utf8file = file.toNativeUtf8();
     865           0 :     var exportProfileC = library.lookup<NativeFunction<string_string_to_string_function>>("c_ImportProfile");
     866             :     // ignore: non_constant_identifier_names
     867             :     final ExportProfileFn = exportProfileC.asFunction<StringFromStringStringFn>();
     868           0 :     Pointer<Utf8> result = ExportProfileFn(utf8file, utf8file.length, utf8pass, utf8pass.length);
     869           0 :     String importResult = result.toDartString();
     870           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(result);
     871           0 :     malloc.free(utf8pass);
     872           0 :     malloc.free(utf8file);
     873             :     return importResult;
     874             :   }
     875             : 
     876           0 :   @override
     877             :   Future<String> GetDebugInfo() async {
     878           0 :     var getDebugInfo = library.lookup<NativeFunction<void_to_string>>("c_GetDebugInfo");
     879             :     final GetDebugInfo = getDebugInfo.asFunction<StringFromVoid>();
     880           0 :     Pointer<Utf8> result = GetDebugInfo();
     881           0 :     String debugResult = result.toDartString();
     882           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(result);
     883             :     return debugResult;
     884             :   }
     885             : 
     886           0 :   @override
     887             :   Future<String> GetSharedFiles(String profile, int handle) async {
     888           0 :     var getSharedFiles = library.lookup<NativeFunction<get_json_blob_from_str_int_function>>("c_GetSharedFiles");
     889             :     final GetSharedFiles = getSharedFiles.asFunction<GetJsonBlobFromStrIntFn>();
     890           0 :     final utf8profile = profile.toNativeUtf8();
     891           0 :     Pointer<Utf8> jsonMessageBytes = GetSharedFiles(utf8profile, utf8profile.length, handle);
     892           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     893           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     894           0 :     malloc.free(utf8profile);
     895             :     return jsonMessage;
     896             :   }
     897             : 
     898           0 :   @override
     899             :   void RestartSharing(String profile, String filekey) {
     900           0 :     var restartSharingC = library.lookup<NativeFunction<void_from_string_string_function>>("c_RestartFileShare");
     901             :     // ignore: non_constant_identifier_names
     902             :     final RestartSharing = restartSharingC.asFunction<VoidFromStringStringFn>();
     903           0 :     final utf8profile = profile.toNativeUtf8();
     904           0 :     final ut8filekey = filekey.toNativeUtf8();
     905           0 :     RestartSharing(utf8profile, utf8profile.length, ut8filekey, ut8filekey.length);
     906           0 :     malloc.free(utf8profile);
     907           0 :     malloc.free(ut8filekey);
     908             :   }
     909             : 
     910           0 :   @override
     911             :   void StopSharing(String profile, String filekey) {
     912           0 :     var stopSharingC = library.lookup<NativeFunction<void_from_string_string_function>>("c_StopFileShare");
     913             :     // ignore: non_constant_identifier_names
     914             :     final StopSharing = stopSharingC.asFunction<VoidFromStringStringFn>();
     915           0 :     final utf8profile = profile.toNativeUtf8();
     916           0 :     final ut8filekey = filekey.toNativeUtf8();
     917           0 :     StopSharing(utf8profile, utf8profile.length, ut8filekey, ut8filekey.length);
     918           0 :     malloc.free(utf8profile);
     919           0 :     malloc.free(ut8filekey);
     920             :   }
     921             : 
     922           0 :   @override
     923             :   void DeleteServerInfo(String profile, String handle) {
     924           0 :     var deleteServerInfoC = library.lookup<NativeFunction<void_from_string_string_function>>("c_DeleteServerInfo");
     925             :     // ignore: non_constant_identifier_names
     926             :     final StopSharing = deleteServerInfoC.asFunction<VoidFromStringStringFn>();
     927           0 :     final utf8profile = profile.toNativeUtf8();
     928           0 :     final ut8handle = handle.toNativeUtf8();
     929           0 :     StopSharing(utf8profile, utf8profile.length, ut8handle, ut8handle.length);
     930           0 :     malloc.free(utf8profile);
     931           0 :     malloc.free(ut8handle);
     932             :   }
     933             : 
     934           0 :   @override
     935             :   void UpdateSettings(String json) {
     936           0 :     var updateSettings = library.lookup<NativeFunction<string_to_void_function>>("c_UpdateSettings");
     937             :     // ignore: non_constant_identifier_names
     938             :     final UpdateSettingsFn = updateSettings.asFunction<VoidFromStringFn>();
     939           0 :     final u1 = json.toNativeUtf8();
     940           0 :     UpdateSettingsFn(u1, u1.length);
     941           0 :     malloc.free(u1);
     942             :   }
     943             : 
     944           0 :   @override
     945             :   bool IsServersCompiled() {
     946           0 :     return library.providesSymbol("c_LoadServers");
     947             :   }
     948             : 
     949           0 :   @override
     950             :   Future<String> SummarizeConversation(String profile, int conversation) async {
     951           0 :     if (!library.providesSymbol("c_Summarize")) {
     952           0 :       return Future.value("");
     953             :     }
     954           0 :     var summarize = library.lookup<NativeFunction<get_json_blob_from_str_int_function>>("c_Summarize");
     955             :     // ignore: non_constant_identifier_names
     956             :     final SummarizeFn = summarize.asFunction<GetJsonBlobFromStrIntFn>();
     957           0 :     final utf8profile = profile.toNativeUtf8();
     958           0 :     Pointer<Utf8> jsonMessageBytes = SummarizeFn(utf8profile, utf8profile.length, conversation);
     959           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     960           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     961           0 :     malloc.free(utf8profile);
     962             :     return jsonMessage;
     963             :   }
     964             : 
     965           0 :   @override
     966             :   Future<String> TranslateMessage(String profile, int conversation, int message, String language) async {
     967           0 :     if (!library.providesSymbol("c_Translate")) {
     968           0 :       return Future.value("");
     969             :     }
     970           0 :     var translate = library.lookup<NativeFunction<get_json_blob_from_str_int_int_str_function>>("c_Translate");
     971             :     // ignore: non_constant_identifier_names
     972             :     final TranslateFn = translate.asFunction<GetJsonBlobFromStrIntIntStrFn>();
     973           0 :     final utf8profile = profile.toNativeUtf8();
     974           0 :     final utf8lang = language.toNativeUtf8();
     975           0 :     Pointer<Utf8> jsonMessageBytes = TranslateFn(
     976             :       utf8profile,
     977           0 :       utf8profile.length,
     978             :       conversation,
     979             :       message,
     980             :       utf8lang,
     981           0 :       utf8lang.length,
     982             :     );
     983           0 :     String jsonMessage = jsonMessageBytes.toDartString();
     984           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
     985           0 :     malloc.free(utf8profile);
     986           0 :     malloc.free(utf8lang);
     987             :     return jsonMessage;
     988             :   }
     989             : 
     990           0 :   @override
     991             :   bool IsBlodeuweddSupported() {
     992           0 :     if (library.providesSymbol("c_Translate")) {
     993             :       return true;
     994             :     }
     995             :     return false;
     996             :   }
     997             : 
     998           0 :   @override
     999             :   Future<String?> GetProfileAttribute(String profile, String key) {
    1000           0 :     var getProfileAttributeC = library.lookup<NativeFunction<get_json_blob_from_str_str_function>>("c_GetProfileAttribute");
    1001             :     // ignore: non_constant_identifier_names
    1002             :     final GetProfileAttribute = getProfileAttributeC.asFunction<GetJsonBlobFromStrStrFn>();
    1003           0 :     final utf8profile = profile.toNativeUtf8();
    1004           0 :     final utf8key = key.toNativeUtf8();
    1005           0 :     Pointer<Utf8> jsonMessageBytes = GetProfileAttribute(utf8profile, utf8profile.length, utf8key, utf8key.length);
    1006           0 :     String jsonMessage = jsonMessageBytes.toDartString();
    1007           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
    1008           0 :     malloc.free(utf8profile);
    1009           0 :     malloc.free(utf8key);
    1010             : 
    1011             :     try {
    1012           0 :       dynamic attributeResult = json.decode(jsonMessage);
    1013           0 :       if (attributeResult["Exists"]) {
    1014           0 :         return Future.value(attributeResult["Value"]);
    1015             :       }
    1016             :     } catch (e) {
    1017           0 :       EnvironmentConfig.debugLog("error getting profile attribute: $e");
    1018             :     }
    1019             : 
    1020           0 :     return Future.value(null);
    1021             :   }
    1022             : 
    1023           0 :   @override
    1024             :   Future<String?> GetConversationAttribute(String profile, int conversation, String key) {
    1025           0 :     var getConversationAttributeC = library.lookup<NativeFunction<get_json_blob_from_str_int_string_function>>("c_GetConversationAttribute");
    1026             :     // ignore: non_constant_identifier_names
    1027             :     final GetConversationAttribute = getConversationAttributeC.asFunction<GetJsonBlobFromStrIntStringFn>();
    1028           0 :     final utf8profile = profile.toNativeUtf8();
    1029           0 :     final utf8key = key.toNativeUtf8();
    1030           0 :     Pointer<Utf8> jsonMessageBytes = GetConversationAttribute(utf8profile, utf8profile.length, conversation, utf8key, utf8key.length);
    1031           0 :     String jsonMessage = jsonMessageBytes.toDartString();
    1032           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(jsonMessageBytes);
    1033           0 :     malloc.free(utf8profile);
    1034           0 :     malloc.free(utf8key);
    1035             : 
    1036             :     try {
    1037           0 :       dynamic attributeResult = json.decode(jsonMessage);
    1038           0 :       if (attributeResult["Exists"]) {
    1039           0 :         return Future.value(attributeResult["Value"]);
    1040             :       }
    1041             :     } catch (e) {
    1042           0 :       EnvironmentConfig.debugLog("error getting profile attribute: $e");
    1043             :     }
    1044             : 
    1045           0 :     return Future.value(null);
    1046             :   }
    1047             : 
    1048           0 :   @override
    1049             :   void AttemptReconnection(String profile, String onion) {
    1050             :     // ignore: non_constant_identifier_names
    1051           0 :     var peerWithOnionC = library.lookup<NativeFunction<void_from_string_string_function>>("c_PeerWithOnion");
    1052             :     final PeerWithOnionF = peerWithOnionC.asFunction<VoidFromStringStringFn>();
    1053           0 :     final utf8profile = profile.toNativeUtf8();
    1054           0 :     final utf8onion = onion.toNativeUtf8();
    1055           0 :     PeerWithOnionF(utf8profile, utf8profile.length, utf8onion, utf8onion.length);
    1056           0 :     malloc.free(utf8profile);
    1057           0 :     malloc.free(utf8onion);
    1058             :   }
    1059             : 
    1060           0 :   @override
    1061             :   void AttemptReconnectionServer(String profile, String onion) {
    1062             :     // ignore: non_constant_identifier_names
    1063           0 :     var queueJoinServerC = library.lookup<NativeFunction<void_from_string_string_function>>("c_QueueJoinServer");
    1064             :     final QueueJoinServerC = queueJoinServerC.asFunction<VoidFromStringStringFn>();
    1065           0 :     final utf8profile = profile.toNativeUtf8();
    1066           0 :     final utf8onion = onion.toNativeUtf8();
    1067           0 :     QueueJoinServerC(utf8profile, utf8profile.length, utf8onion, utf8onion.length);
    1068           0 :     malloc.free(utf8profile);
    1069           0 :     malloc.free(utf8onion);
    1070             :   }
    1071             : 
    1072           0 :   @override
    1073             :   void DisconnectFromPeer(String profile, String onion) {
    1074             :     // ignore: non_constant_identifier_names
    1075           0 :     var disconnectFromPeerC = library.lookup<NativeFunction<void_from_string_string_function>>("c_DisconnectFromPeer");
    1076             :     final DisconnectFromPeerC = disconnectFromPeerC.asFunction<VoidFromStringStringFn>();
    1077           0 :     final utf8profile = profile.toNativeUtf8();
    1078           0 :     final utf8onion = onion.toNativeUtf8();
    1079           0 :     DisconnectFromPeerC(utf8profile, utf8profile.length, utf8onion, utf8onion.length);
    1080           0 :     malloc.free(utf8profile);
    1081           0 :     malloc.free(utf8onion);
    1082             :   }
    1083             : 
    1084           0 :   @override
    1085             :   void DisconnectFromServer(String profile, String onion) {
    1086             :     // ignore: non_constant_identifier_names
    1087           0 :     var disconnectFromServerC = library.lookup<NativeFunction<void_from_string_string_function>>("c_DisconnectFromServer");
    1088             :     final DisconnectFromServerC = disconnectFromServerC.asFunction<VoidFromStringStringFn>();
    1089           0 :     final utf8profile = profile.toNativeUtf8();
    1090           0 :     final utf8onion = onion.toNativeUtf8();
    1091           0 :     DisconnectFromServerC(utf8profile, utf8profile.length, utf8onion, utf8onion.length);
    1092           0 :     malloc.free(utf8profile);
    1093           0 :     malloc.free(utf8onion);
    1094             :   }
    1095             : 
    1096           0 :   @override
    1097             :   Future<String> SearchConversations(String profile, String pattern) async {
    1098           0 :     var searchConversationsC = library.lookup<NativeFunction<string_string_to_string_function>>("c_SearchConversations");
    1099             :     // ignore: non_constant_identifier_names
    1100             :     final SearchConversations = searchConversationsC.asFunction<StringFromStringStringFn>();
    1101           0 :     final utf8profile = profile.toNativeUtf8();
    1102           0 :     final utf8pattern = pattern.toNativeUtf8();
    1103           0 :     EnvironmentConfig.debugLog("Searching for $profile $pattern");
    1104           0 :     Pointer<Utf8> searchIDRaw = SearchConversations(utf8profile, utf8profile.length, utf8pattern, utf8pattern.length);
    1105           0 :     String searchID = searchIDRaw.toDartString();
    1106           0 :     _UnsafeFreePointerAnyUseOfThisFunctionMustBeDoubleApproved(searchIDRaw);
    1107           0 :     malloc.free(utf8profile);
    1108           0 :     malloc.free(utf8pattern);
    1109             :     return searchID;
    1110             :   }
    1111             : 
    1112           0 :   @override
    1113             :   Future<HashMap<String, String>> PlatformChannelInfo() {
    1114           0 :     return Future.value(HashMap<String, String>());
    1115             :   }
    1116             : 
    1117           0 :   @override
    1118             :   Future<void> ConfigureConnections(String profile, bool listen, bool peers, bool servers) async {
    1119           0 :     var configureConnections = library.lookup<NativeFunction<void_from_string_bool_bool_bool>>("c_ConfigureConnections");
    1120             :     // ignore: non_constant_identifier_names
    1121             :     final ConfigureConnections = configureConnections.asFunction<VoidFromStringBoolBoolBool>();
    1122           0 :     final utf8profile = profile.toNativeUtf8();
    1123           0 :     ConfigureConnections(utf8profile, utf8profile.length, listen, peers, servers);
    1124           0 :     malloc.free(utf8profile);
    1125             :     return;
    1126             :   }
    1127             : 
    1128           0 :   @override
    1129             :   void PublishServerUpdate(String profile) {
    1130           0 :     var publishServerUpdate = library.lookup<NativeFunction<string_to_void_function>>("c_PublishServerUpdate");
    1131             :     // ignore: non_constant_identifier_names
    1132             :     final PublishServerUpdate = publishServerUpdate.asFunction<StringFn>();
    1133           0 :     final utf8profile = profile.toNativeUtf8();
    1134           0 :     PublishServerUpdate(utf8profile, utf8profile.length);
    1135           0 :     malloc.free(utf8profile);
    1136             :   }
    1137             : 
    1138           0 :   @override
    1139             :   bool IsLoaded() {
    1140           0 :     bool check = library.providesSymbol("c_UpdateSettings");
    1141           0 :     EnvironmentConfig.debugLog("Checking that the FFI Interface is Correctly Loaded... $check");
    1142             :     return check;
    1143             :   }
    1144             : }

Generated by: LCOV version 1.14