Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,25 @@ Alternatively, you can install it via the .NET CLI:
dotnet add package LightningDB
```

### iOS

The package ships iOS binaries in two forms (minimum iOS 12.0; the arm64
simulator slice requires iOS 14.0):

- **.NET for iOS / MAUI**: works automatically. The dylibs under
`runtimes/ios-arm64` and `runtimes/iossimulator-*` carry an
`@rpath/lmdb.dylib` install name and an ad-hoc signature; the .NET iOS SDK
embeds them in the app bundle and re-signs them with your app identity at
build time.
- **Unity (and other Xcode-based pipelines)**: use the bundled
`ios/lmdb.xcframework`. A nupkg is a zip archive, so extract
`ios/lmdb.xcframework` from it and copy it into `Assets/Plugins/iOS`
(Unity 2021.3+ imports xcframework plugins directly). In the plugin
importer, enable the iOS platform and "Add to Embedded Binaries" so Xcode
embeds and re-signs the framework during the app build — required for
release/App Store builds. On older Unity versions, use the device slice
(`ios-arm64/lmdb.framework`) on its own instead.

## Basic Usage

Here's a simple example demonstrating how to create an environment, open a database, and perform basic put and get operations:
Expand Down
113 changes: 110 additions & 3 deletions lmdb/compile-lmdb-macos.sh
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,9 @@ git apply ../../../mingw-win32-fixes.patch

declare -A build_outputs
declare -A supported_targets=(
[ios-arm64/native/liblmdb.dylib]="make CC='xcrun --sdk iphoneos --toolchain iphoneos clang -arch arm64' LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[iossimulator-arm64/native/liblmdb.dylib]="make CC='xcrun --sdk iphonesimulator --toolchain iphoneos clang -arch arm64' LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[iossimulator-x64/native/liblmdb.dylib]="make CC='xcrun --sdk iphonesimulator --toolchain iphoneos clang -arch x86_64' LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[ios-arm64/native/lmdb.dylib]="make CC='xcrun --sdk iphoneos clang -arch arm64 -miphoneos-version-min=12.0' LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[iossimulator-arm64/native/lmdb.dylib]="make CC='xcrun --sdk iphonesimulator clang -arch arm64 -mios-simulator-version-min=12.0' LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[iossimulator-x64/native/lmdb.dylib]="make CC='xcrun --sdk iphonesimulator clang -arch x86_64 -mios-simulator-version-min=12.0' LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[osx-arm64/native/lmdb.dylib]="make LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[osx/native/lmdb.dylib]="make CC='clang -mmacosx-version-min=10.15 -arch x86_64' LDFLAGS='-s' XCFLAGS='-DNDEBUG' VERSION_OPT='-Wl,-current_version,1.0'"
[linux-arm/native/liblmdb.so]="docker run --mount type=bind,source=$(pwd),target=/lmdb --rm --platform=linux/arm/7 -w /lmdb gcc:latest make LDFLAGS='-s' XCFLAGS='-DNDEBUG'"
Expand Down Expand Up @@ -51,6 +51,110 @@ function compile_lib() {
#seems to be a stateful race condition on the docker run processes so this allows everything to succeed
}

RUNTIMES_DIR=../../../../src/LightningDB/runtimes
IOS_DIR=../../../../src/LightningDB/ios

function write_framework_plist() {
# $1 = framework dir, $2 = supported platform (iPhoneOS | iPhoneSimulator)
cat > "$1/Info.plist" <<PLIST
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>CFBundleDevelopmentRegion</key>
<string>en</string>
<key>CFBundleExecutable</key>
<string>lmdb</string>
<key>CFBundleIdentifier</key>
<string>io.github.coreykaylor.lmdb</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>lmdb</string>
<key>CFBundlePackageType</key>
<string>FMWK</string>
<key>CFBundleShortVersionString</key>
<string>1.0.0</string>
<key>CFBundleVersion</key>
<string>1.0.0</string>
<key>CFBundleSupportedPlatforms</key>
<array>
<string>$2</string>
</array>
<key>MinimumOSVersion</key>
<string>12.0</string>
</dict>
</plist>
PLIST
}

# iOS requires @rpath install names and code signatures; bare dylibs with the
# Makefile's default liblmdb.so install name load in dev but fail release builds.
function package_apple_artifacts() {
for rid in ios-arm64 iossimulator-arm64 iossimulator-x64; do
install_name_tool -id @rpath/lmdb.dylib "$RUNTIMES_DIR/$rid/native/lmdb.dylib"
codesign --force --sign - "$RUNTIMES_DIR/$rid/native/lmdb.dylib"
done

local scratch
scratch=$(mktemp -d)
mkdir -p "$scratch/device/lmdb.framework" "$scratch/simulator/lmdb.framework"
cp "$RUNTIMES_DIR/ios-arm64/native/lmdb.dylib" "$scratch/device/lmdb.framework/lmdb"
lipo -create \
"$RUNTIMES_DIR/iossimulator-arm64/native/lmdb.dylib" \
"$RUNTIMES_DIR/iossimulator-x64/native/lmdb.dylib" \
-output "$scratch/simulator/lmdb.framework/lmdb"
write_framework_plist "$scratch/device/lmdb.framework" iPhoneOS
write_framework_plist "$scratch/simulator/lmdb.framework" iPhoneSimulator
for fw in "$scratch/device/lmdb.framework" "$scratch/simulator/lmdb.framework"; do
install_name_tool -id @rpath/lmdb.framework/lmdb "$fw/lmdb"
codesign --force --sign - "$fw"
done

rm -rf "$IOS_DIR/lmdb.xcframework"
mkdir -p "$IOS_DIR"
xcodebuild -create-xcframework \
-framework "$scratch/device/lmdb.framework" \
-framework "$scratch/simulator/lmdb.framework" \
-output "$IOS_DIR/lmdb.xcframework"
rm -rf "$scratch"
}

function verify_apple_artifacts() {
local failed=0
local binaries=(
"$RUNTIMES_DIR/ios-arm64/native/lmdb.dylib"
"$RUNTIMES_DIR/iossimulator-arm64/native/lmdb.dylib"
"$RUNTIMES_DIR/iossimulator-x64/native/lmdb.dylib"
"$IOS_DIR"/lmdb.xcframework/*/lmdb.framework/lmdb
)
for bin in "${binaries[@]}"; do
if ! otool -D "$bin" | grep -q "@rpath/lmdb"; then
echo "FAIL: $bin install name is not @rpath-based: $(otool -D "$bin" | tail -1)"
failed=1
fi
# arm64 simulator slices are floored at 14.0 by the toolchain (no arm64
# simulators existed before iOS 14), so accept either minimum.
if ! otool -l "$bin" | grep -A4 LC_BUILD_VERSION | grep -Eq "minos (12|14)\.0"; then
echo "FAIL: $bin minos is not 12.0/14.0"
failed=1
fi
if ! codesign -dv "$bin" 2>/dev/null; then
echo "FAIL: $bin is not code signed"
failed=1
fi
done
if ! lipo -info "$IOS_DIR"/lmdb.xcframework/ios-*-simulator/lmdb.framework/lmdb | grep -q "x86_64 arm64"; then
echo "FAIL: simulator framework slice is not a fat x86_64+arm64 binary"
failed=1
fi
if [ $failed -eq 0 ]; then
echo "All iOS artifacts verified (install names, minos, signatures, simulator archs)"
else
exit 1
fi
}

for key in "${!supported_targets[@]}"; do
compile_lib "${supported_targets[$key]}" $key
done
Expand All @@ -60,3 +164,6 @@ if [ ${#supported_targets[@]} -eq ${#build_outputs[@]} ]; then
else
echo "Not all supported targets have produced unique output"
fi

package_apple_artifacts
verify_apple_artifacts
1 change: 1 addition & 0 deletions src/LightningDB/LightningDB.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
<PackagePath>runtimes</PackagePath>
</None>
<None Include="LightningDB.targets" Pack="true" PackagePath="build" />
<None Include="ios\lmdb.xcframework\**\*" Pack="true" PackagePath="ios\lmdb.xcframework" Visible="false" />
</ItemGroup>

<ItemGroup>
Expand Down
44 changes: 44 additions & 0 deletions src/LightningDB/ios/lmdb.xcframework/Info.plist
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>AvailableLibraries</key>
<array>
<dict>
<key>BinaryPath</key>
<string>lmdb.framework/lmdb</string>
<key>LibraryIdentifier</key>
<string>ios-arm64_x86_64-simulator</string>
<key>LibraryPath</key>
<string>lmdb.framework</string>
<key>SupportedArchitectures</key>
<array>
<string>arm64</string>
<string>x86_64</string>
</array>
<key>SupportedPlatform</key>
<string>ios</string>
<key>SupportedPlatformVariant</key>
<string>simulator</string>
</dict>
<dict>
<key>BinaryPath</key>
<string>lmdb.framework/lmdb</string>
<key>LibraryIdentifier</key>
<string>ios-arm64</string>
<key>LibraryPath</key>
<string>lmdb.framework</string>
<key>SupportedArchitectures</key>
<array>
<string>arm64</string>
</array>
<key>SupportedPlatform</key>
<string>ios</string>
</dict>
</array>
<key>CFBundlePackageType</key>
<string>XFWK</string>
<key>XCFrameworkFormatVersion</key>
<string>1.0</string>
</dict>
</plist>
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>CFBundleDevelopmentRegion</key>
<string>en</string>
<key>CFBundleExecutable</key>
<string>lmdb</string>
<key>CFBundleIdentifier</key>
<string>io.github.coreykaylor.lmdb</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>lmdb</string>
<key>CFBundlePackageType</key>
<string>FMWK</string>
<key>CFBundleShortVersionString</key>
<string>1.0.0</string>
<key>CFBundleVersion</key>
<string>1.0.0</string>
<key>CFBundleSupportedPlatforms</key>
<array>
<string>iPhoneOS</string>
</array>
<key>MinimumOSVersion</key>
<string>12.0</string>
</dict>
</plist>
Original file line number Diff line number Diff line change
@@ -0,0 +1,101 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>files</key>
<dict>
<key>Info.plist</key>
<data>
aeShFzK6fTG2/+0zy/ZOSx9k9DY=
</data>
</dict>
<key>files2</key>
<dict/>
<key>rules</key>
<dict>
<key>^.*</key>
<true/>
<key>^.*\.lproj/</key>
<dict>
<key>optional</key>
<true/>
<key>weight</key>
<real>1000</real>
</dict>
<key>^.*\.lproj/locversion.plist$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>1100</real>
</dict>
<key>^Base\.lproj/</key>
<dict>
<key>weight</key>
<real>1010</real>
</dict>
<key>^version.plist$</key>
<true/>
</dict>
<key>rules2</key>
<dict>
<key>.*\.dSYM($|/)</key>
<dict>
<key>weight</key>
<real>11</real>
</dict>
<key>^(.*/)?\.DS_Store$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>2000</real>
</dict>
<key>^.*</key>
<true/>
<key>^.*\.lproj/</key>
<dict>
<key>optional</key>
<true/>
<key>weight</key>
<real>1000</real>
</dict>
<key>^.*\.lproj/locversion.plist$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>1100</real>
</dict>
<key>^Base\.lproj/</key>
<dict>
<key>weight</key>
<real>1010</real>
</dict>
<key>^Info\.plist$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>20</real>
</dict>
<key>^PkgInfo$</key>
<dict>
<key>omit</key>
<true/>
<key>weight</key>
<real>20</real>
</dict>
<key>^embedded\.provisionprofile$</key>
<dict>
<key>weight</key>
<real>20</real>
</dict>
<key>^version\.plist$</key>
<dict>
<key>weight</key>
<real>20</real>
</dict>
</dict>
</dict>
</plist>
Binary file not shown.
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>CFBundleDevelopmentRegion</key>
<string>en</string>
<key>CFBundleExecutable</key>
<string>lmdb</string>
<key>CFBundleIdentifier</key>
<string>io.github.coreykaylor.lmdb</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>lmdb</string>
<key>CFBundlePackageType</key>
<string>FMWK</string>
<key>CFBundleShortVersionString</key>
<string>1.0.0</string>
<key>CFBundleVersion</key>
<string>1.0.0</string>
<key>CFBundleSupportedPlatforms</key>
<array>
<string>iPhoneSimulator</string>
</array>
<key>MinimumOSVersion</key>
<string>12.0</string>
</dict>
</plist>
Loading