WIP: More dynmaic path searching for generating bindings. #30
2 changed files with 192 additions and 23 deletions
32
pubspec.lock
32
pubspec.lock
|
|
@ -587,10 +587,10 @@ packages:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: idb_shim
|
name: idb_shim
|
||||||
sha256: d46b09e116508e817f5ea2d8e1f6f55fb98bf7966175152809fd29791bfba3b8
|
sha256: "48be1c95f06c4b059d0f5b9888dc5d7384e4a9e4d71824ae2deeb1e1546c6c07"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.9.1"
|
version: "2.9.2"
|
||||||
image:
|
image:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
|
@ -836,10 +836,10 @@ packages:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: meta
|
name: meta
|
||||||
sha256: "23f08335362185a5ea2ad3a4e597f1375e78bce8a040df5c600c8d3552ef2394"
|
sha256: "1741988757a65eb6b36abe716829688cf01910bbf91c34354ff7ec1c3de2b349"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.17.0"
|
version: "1.18.0"
|
||||||
mime:
|
mime:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
|
@ -1321,26 +1321,26 @@ packages:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: test
|
name: test
|
||||||
sha256: "280d6d890011ca966ad08df7e8a4ddfab0fb3aa49f96ed6de56e3521347a9ae7"
|
sha256: "8d9ceddbab833f180fbefed08afa76d7c03513dfdba87ffcec2718b02bbcbf20"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.30.0"
|
version: "1.31.0"
|
||||||
test_api:
|
test_api:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: test_api
|
name: test_api
|
||||||
sha256: "8161c84903fd860b26bfdefb7963b3f0b68fee7adea0f59ef805ecca346f0c7a"
|
sha256: "949a932224383300f01be9221c39180316445ecb8e7547f70a41a35bf421fb9e"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.7.10"
|
version: "0.7.11"
|
||||||
test_core:
|
test_core:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: test_core
|
name: test_core
|
||||||
sha256: "0381bd1585d1a924763c308100f2138205252fb90c9d4eeaf28489ee65ccde51"
|
sha256: "1991d4cfe85d5043241acac92962c3977c8d2f2add1ee73130c7b286417d1d34"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.6.16"
|
version: "0.6.17"
|
||||||
timeago:
|
timeago:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
|
|
@ -1401,10 +1401,10 @@ packages:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: url_launcher_android
|
name: url_launcher_android
|
||||||
sha256: "3bb000251e55d4a209aa0e2e563309dc9bb2befea2295fd0cec1f51760aac572"
|
sha256: "17bc677f0b301615530dd1d67e0a9828cafa2d0b6b6eae4cd3679b7eac4a273c"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "6.3.29"
|
version: "6.3.30"
|
||||||
url_launcher_ios:
|
url_launcher_ios:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
|
@ -1465,10 +1465,10 @@ packages:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: vector_graphics
|
name: vector_graphics
|
||||||
sha256: "4d35a36400983c3457c289d4d553b5308f506ea84f7e51c7a564651b5525209a"
|
sha256: "2306c03da2ba81724afeb589c351ebbc0aa7d86005925be8f8735856dbe5e42d"
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.2.1"
|
version: "1.2.2"
|
||||||
vector_graphics_codec:
|
vector_graphics_codec:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
|
@ -1481,10 +1481,10 @@ packages:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: vector_graphics_compiler
|
name: vector_graphics_compiler
|
||||||
sha256: "98e7e94de127b46a86ef46197fff84ff99f3d3b80a708390d717ad731efef598"
|
sha256: b9b3f391857781aa96acacef96066f2f49b4cd03cf9fce3ca4d8da2ef5ea129e
|
||||||
url: "https://pub.dev"
|
url: "https://pub.dev"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.2.2"
|
version: "1.2.3"
|
||||||
vector_math:
|
vector_math:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
|
|
||||||
|
|
@ -1,26 +1,195 @@
|
||||||
import "dart:io";
|
import "dart:io";
|
||||||
import "package:ffigen/ffigen.dart";
|
import "package:ffigen/ffigen.dart";
|
||||||
import "package:path/path.dart";
|
import "package:path/path.dart" as path;
|
||||||
|
|
||||||
void main(List<String> args) async {
|
void main(List<String> args) async {
|
||||||
final repoDir = Directory.fromUri(Platform.script.resolve("../gomuks"));
|
final Directory repoDir = Directory.fromUri(Platform.script.resolve("../gomuks"));
|
||||||
|
print("Generating FFI Bindings for ${Platform.operatingSystem}...");
|
||||||
|
|
||||||
print("Generating FFI Bindings...");
|
int? parseVersion(String name) {
|
||||||
|
final RegExpMatch? match = RegExp(r"^(\d+)(?:\.(\d+))?(?:\.(\d+))?$").firstMatch(name);
|
||||||
|
|
||||||
|
if (match == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
final int major = int.tryParse(match.group(1)!) ?? 0;
|
||||||
|
final int minor = int.tryParse(match.group(2) ?? "0") ?? 0;
|
||||||
|
final int patch = int.tryParse(match.group(3) ?? "0") ?? 0;
|
||||||
|
return major * 10000 + minor * 100 + patch;
|
||||||
|
}
|
||||||
|
|
||||||
|
final List<String> systemIncludePaths = [];
|
||||||
|
late String targetTriple;
|
||||||
|
late String libclangName;
|
||||||
|
|
||||||
|
if (Platform.isLinux) {
|
||||||
|
targetTriple = "x86_64-pc-linux-gnu";
|
||||||
|
libclangName = "libclang.so";
|
||||||
|
|
||||||
|
final Directory gccBaseDir = Directory("/usr/lib/gcc/x86_64-pc-linux-gnu");
|
||||||
|
|
||||||
|
if (await gccBaseDir.exists()) {
|
||||||
|
final List<Directory> dirs = gccBaseDir.listSync().whereType<Directory>().toList();
|
||||||
|
|
||||||
|
dirs.sort((a, b) {
|
||||||
|
final int va = parseVersion(path.basename(a.path)) ?? 0;
|
||||||
|
final int vb = parseVersion(path.basename(b.path)) ?? 0;
|
||||||
|
return vb.compareTo(va);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (dirs.isNotEmpty) {
|
||||||
|
final Directory latest = dirs.first;
|
||||||
|
final String inc = path.join(latest.path, "include");
|
||||||
|
systemIncludePaths.add(inc);
|
||||||
|
systemIncludePaths.add(path.dirname(inc));
|
||||||
|
print("Using GCC: ${path.basename(latest.path)}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
final Directory clangDir = Directory("/usr/lib/clang");
|
||||||
|
|
||||||
|
if (await clangDir.exists()) {
|
||||||
|
final List<Directory> dirs = clangDir.listSync().whereType<Directory>().toList();
|
||||||
|
dirs.sort((a, b) {
|
||||||
|
final int va = parseVersion(path.basename(a.path)) ?? 0;
|
||||||
|
final int vb = parseVersion(path.basename(b.path)) ?? 0;
|
||||||
|
return vb.compareTo(va);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (dirs.isNotEmpty) {
|
||||||
|
systemIncludePaths.add(path.join(dirs.first.path, "include"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
systemIncludePaths.addAll(["/usr/include", "/usr/include/x86_64-linux-gnu", "/usr/local/include"]);
|
||||||
|
|
||||||
|
} else if (Platform.isMacOS) {
|
||||||
|
final String arch = _detectMacArch();
|
||||||
|
targetTriple = "$arch-apple-darwin";
|
||||||
|
libclangName = "libclang.dylib";
|
||||||
|
|
||||||
|
final String? sdkPath = _runCommand("xcrun", ["--show-sdk-path"]);
|
||||||
|
if (sdkPath != null) {
|
||||||
|
systemIncludePaths.add(path.join(sdkPath, "usr", "include"));
|
||||||
|
print("Using Xcode SDK: $sdkPath");
|
||||||
|
}
|
||||||
|
|
||||||
|
final String? clangResDir = _runCommand("clang", ["-print-resource-dir"]);
|
||||||
|
if (clangResDir != null) {
|
||||||
|
final String inc = path.join(clangResDir, "include");
|
||||||
|
|
||||||
|
if (Directory(inc).existsSync()) {
|
||||||
|
systemIncludePaths.add(inc);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
final String brewPrefix = arch == "arm64" ? "/opt/homebrew" : "/usr/local";
|
||||||
|
final Directory brewGcc = Directory(path.join(brewPrefix, "opt", "gcc", "lib", "gcc", "current", "include"));
|
||||||
|
|
||||||
|
if (brewGcc.existsSync()) {
|
||||||
|
systemIncludePaths.add(brewGcc.path);
|
||||||
|
print("Using Homebrew GCC");
|
||||||
|
}
|
||||||
|
|
||||||
|
systemIncludePaths.addAll(["$brewPrefix/include", "/usr/local/include"]);
|
||||||
|
|
||||||
|
} else if (Platform.isWindows) {
|
||||||
|
|
||||||
|
targetTriple = "x86_64-pc-windows-msvc";
|
||||||
|
libclangName = "libclang.dll";
|
||||||
|
|
||||||
|
final String vswhere = r"C:\Program Files (x86)\Microsoft Visual Studio\Installer\vswhere.exe";
|
||||||
|
final String? vsPath = _runCommand(vswhere, ["-latest", "-property", "installationPath"]);
|
||||||
|
|
||||||
|
if (vsPath != null) {
|
||||||
|
final Directory msvcDir = Directory(path.join(vsPath, "VC", "Tools", "MSVC"));
|
||||||
|
|
||||||
|
if (msvcDir.existsSync()) {
|
||||||
|
final List<Directory> dirs = msvcDir.listSync().whereType<Directory>().toList();
|
||||||
|
dirs.sort((a, b) {
|
||||||
|
final int va = parseVersion(path.basename(a.path)) ?? 0;
|
||||||
|
final int vb = parseVersion(path.basename(b.path)) ?? 0;
|
||||||
|
return vb.compareTo(va);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (dirs.isNotEmpty) {
|
||||||
|
systemIncludePaths.add(path.join(dirs.first.path, "include"));
|
||||||
|
print("Using MSVC: ${path.basename(dirs.first.path)}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
final Directory sdkDir = Directory(r"C:\Program Files (x86)\Windows Kits\10\Include");
|
||||||
|
if (sdkDir.existsSync()) {
|
||||||
|
final List<Directory> dirs = sdkDir.listSync().whereType<Directory>().toList();
|
||||||
|
|
||||||
|
dirs.sort((a, b) {
|
||||||
|
final int va = parseVersion(path.basename(a.path)) ?? 0;
|
||||||
|
final int vb = parseVersion(path.basename(b.path)) ?? 0;
|
||||||
|
return vb.compareTo(va);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (dirs.isNotEmpty) {
|
||||||
|
final String sdkVer = dirs.first.path;
|
||||||
|
for (final String sub in ["um", "ucrt", "shared"]) {
|
||||||
|
final String p = path.join(sdkVer, sub);
|
||||||
|
if (Directory(p).existsSync()) systemIncludePaths.add(p);
|
||||||
|
}
|
||||||
|
print("Using Windows SDK: ${path.basename(sdkVer)}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
final Directory llvmDir = Directory(r"C:\Program Files\LLVM\include");
|
||||||
|
|
||||||
|
if (llvmDir.existsSync()) {
|
||||||
|
systemIncludePaths.add(llvmDir.path);
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
|
||||||
|
print("Error: Unsupported platform: ${Platform.operatingSystem}");
|
||||||
|
exit(1);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
print("Target: $targetTriple");
|
||||||
|
print("Include paths: ${systemIncludePaths.length} found");
|
||||||
|
|
||||||
|
final String? libclangPath = Platform.environment["LIBCLANG_PATH"];
|
||||||
|
|
||||||
final libclangPath = Platform.environment["LIBCLANG_PATH"];
|
|
||||||
FfiGenerator(
|
FfiGenerator(
|
||||||
output: Output(
|
output: Output(
|
||||||
dartFile: Platform.script.resolve("../lib/src/third_party/gomuks.g.dart"),
|
dartFile: Platform.script.resolve("../lib/src/third_party/gomuks.g.dart"),
|
||||||
),
|
),
|
||||||
headers: Headers(
|
headers: Headers(
|
||||||
entryPoints: [File(join(repoDir.path, "pkg", "ffi", "gomuksffi.h")).uri],
|
entryPoints: [File(path.join(repoDir.path, "pkg", "ffi", "gomuksffi.h")).uri],
|
||||||
compilerOptions: ["--no-warnings"],
|
compilerOptions: [
|
||||||
|
"--no-warnings",
|
||||||
|
"-target", targetTriple,
|
||||||
|
...systemIncludePaths.map((p) => "-I$p"),
|
||||||
|
],
|
||||||
),
|
),
|
||||||
functions: Functions.includeAll,
|
functions: Functions.includeAll,
|
||||||
).generate(
|
).generate(
|
||||||
libclangDylib: libclangPath == null
|
libclangDylib: libclangPath == null
|
||||||
? null
|
? null
|
||||||
: Uri.file(join(libclangPath, "libclang.so")),
|
: Uri.file(path.join(libclangPath, libclangName)),
|
||||||
);
|
);
|
||||||
|
|
||||||
print("Done!");
|
print("Done!");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
String _detectMacArch() {
|
||||||
|
final String? res = _runCommand("uname", ["-m"]);
|
||||||
|
return res?.trim() == "arm64" ? "arm64" : "x86_64";
|
||||||
|
}
|
||||||
|
|
||||||
|
String? _runCommand(String exe, List<String> args) {
|
||||||
|
try {
|
||||||
|
final ProcessResult res = Process.runSync(exe, args);
|
||||||
|
return res.exitCode == 0 ? (res.stdout as String).trim() : null;
|
||||||
|
} catch (_) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
Loading…
Add table
Add a link
Reference in a new issue