Skip to content

Commit

Permalink
Merge pull request #157
Browse files Browse the repository at this point in the history
develop
  • Loading branch information
ksidirop-laerdal authored Nov 4, 2024
2 parents dd0d7f6 + f3c32b9 commit 77f1042
Show file tree
Hide file tree
Showing 179 changed files with 5,136 additions and 1,669 deletions.
28 changes: 20 additions & 8 deletions .github/workflows/github-actions.yml
Original file line number Diff line number Diff line change
Expand Up @@ -20,11 +20,17 @@ env:
SCL_DEPENDENCY_TRACKER_SERVER_URL: ${{ secrets.SCL_DEPENDENCY_TRACKER_SERVER_URL }}
SCL_DEPENDENCY_TRACKER_SIGNING_PRIVATE_KEY: ${{ secrets.SCL_DEPENDENCY_TRACKER_SIGNING_PRIVATE_KEY }}

BINDINGS_IOS___SDK_VERSION: "17.5"
BINDINGS_IOS___XCODE_IDE_DEV_PATH: "/Applications/Xcode_15.4.app/Contents/Developer"
DOTNET_TARGET_WORKLOAD_VERSION: "8.0.402" # dont upgrade this lightheartedly the workload snapshot implicitly defines which versions of Android/iOS/MacCatalyst SDKs are supported

BINDINGS_MACCATALYST___SDK_VERSION: "14.5"
BINDINGS_MACCATALYST___XCODE_IDE_DEV_PATH: "/Applications/Xcode_15.4.app/Contents/Developer"
BINDINGS_ANDROID___DOTNET_TARGET_PLATFORM_VERSION: "34" # for the csproj file

BINDINGS_IOS___SDK_VERSION: "17.5" # for xcodebuild
BINDINGS_IOS___XCODE_IDE_DEV_PATH: "/Applications/Xcode_15.4.app/Contents/Developer" # for xcodebuild
BINDINGS_IOS___DOTNET_TARGET_PLATFORM_VERSION: "17.0" # for the csproj file

BINDINGS_MACCATALYST___SDK_VERSION: "14.5" # for xcodebuild
BINDINGS_MACCATALYST___XCODE_IDE_DEV_PATH: "/Applications/Xcode_15.4.app/Contents/Developer" # for xcodebuild
BINDINGS_MACCATALYST___DOTNET_TARGET_PLATFORM_VERSION: "17.0" # for the csproj file

on:
workflow_call: # so that other workflows can trigger this
Expand Down Expand Up @@ -64,6 +70,7 @@ jobs:
chmod +x "${{env.BUILD_REPOSITORY_FOLDERPATH}}/Laerdal.Scripts/Laerdal.SetupBuildEnvironment.sh" \
&& \
"${{env.BUILD_REPOSITORY_FOLDERPATH}}/Laerdal.Scripts/Laerdal.SetupBuildEnvironment.sh" \
"${{env.DOTNET_TARGET_WORKLOAD_VERSION}}" \
"https://nuget.pkg.github.com/Laerdal/index.json" \
"${{env.SCL_GITHUB_NUGET_FEED_USERNAME}}" \
"${{env.SCL_GITHUB_ACCESS_TOKEN}}" \
Expand All @@ -85,26 +92,31 @@ jobs:
-p:Should_Skip_MacCatalyst="false" \
\
-p:PackageOutputPath="${{env.BUILD_REPOSITORY_FOLDERPATH}}/Artifacts" \
\
-p:Laerdal_Gradle_Path="/opt/homebrew/opt/gradle@7/bin/gradle" \
-p:Laerdal_Source_Branch="${{env.LAERDAL_SOURCE_BRANCH}}" \
-p:Laerdal_Repository_Path="${{env.LAERDAL_REPOSITORY_PATH}}" \
-p:Laerdal_Github_Access_Token="${{env.SCL_GITHUB_ACCESS_TOKEN}}" \
-p:Laerdal_Test_Results_Folderpath="${{env.BUILD_REPOSITORY_FOLDERPATH}}/TestResults" \
\
-p:Laerdal_Dependency_Tracker_Server_Url="${{env.SCL_DEPENDENCY_TRACKER_SERVER_URL}}" \
-p:Laerdal_Dependency_Tracker_Api_Key_File_Path="${{env.BUILD_REPOSITORY_FOLDERPATH}}/Laerdal.Scripts/dependency_tracker_api_key.ppk" \
-p:Laerdal_Dependency_Tracker_Private_Signing_Key_File_Path="${{env.BUILD_REPOSITORY_FOLDERPATH}}/Laerdal.Scripts/dependency_tracker_private_signing_key.ppk" \
-p:Laerdal_Bindings_Android___DotnetTargetPlatformVersion="${{env.BINDINGS_ANDROID___DOTNET_TARGET_PLATFORM_VERSION}}" \
\
-p:Laerdal_Bindings_iOS___Sdk_Version="${{env.BINDINGS_IOS___SDK_VERSION}}" \
-p:Laerdal_Bindings_iOS___Xcode_Ide_Dev_Path="${{env.BINDINGS_IOS___XCODE_IDE_DEV_PATH}}" \
-p:Laerdal_Bindings_iOS___DotnetTargetPlatformVersion="${{env.BINDINGS_IOS___DOTNET_TARGET_PLATFORM_VERSION}}" \
\
-p:Laerdal_Bindings_MacCatalyst___Sdk_Version="${{env.BINDINGS_MACCATALYST___SDK_VERSION}}" \
-p:Laerdal_Bindings_MacCatalyst___Xcode_Ide_Dev_Path="${{env.BINDINGS_MACCATALYST___XCODE_IDE_DEV_PATH}}" \
-p:Laerdal_Bindings_MacCatalyst___DotnetTargetPlatformVersion="${{env.BINDINGS_MACCATALYST___DOTNET_TARGET_PLATFORM_VERSION}}" \
\
-p:Laerdal_Dependency_Tracker_Server_Url="${{env.SCL_DEPENDENCY_TRACKER_SERVER_URL}}" \
-p:Laerdal_Dependency_Tracker_Api_Key_File_Path="${{env.BUILD_REPOSITORY_FOLDERPATH}}/Laerdal.Scripts/dependency_tracker_api_key.ppk" \
-p:Laerdal_Dependency_Tracker_Private_Signing_Key_File_Path="${{env.BUILD_REPOSITORY_FOLDERPATH}}/Laerdal.Scripts/dependency_tracker_private_signing_key.ppk" \
&& \
rm "./dependency_tracker_private_signing_key.ppk" "./dependency_tracker_api_key.ppk"
- name: '📡 Publish Test Results' # https://github.com/marketplace/actions/publish-test-results
uses: 'EnricoMi/publish-unit-test-result-action/macos@v2'
uses: 'EnricoMi/publish-unit-test-result-action/macos@master'
if: always()
with:
files: |
Expand Down
4 changes: 3 additions & 1 deletion Laerdal.McuMgr.Bindings.Android.Native/gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,9 @@ android.useAndroidX=true
# resources declared in the library itself and none from the library's dependencies,
# thereby reducing the size of the R class for that library
android.nonTransitiveRClass=true
# in macos just comment this one out
# as long as we use gradle 7.6 we will get warnings if we try to build against android 34 or above we suppress such warnings
android.suppressUnsupportedCompileSdk=34
# in macos just comment out the windows paths and keep the homebrew path
# org.gradle.java.home=C/://Program Files//Microsoft//jdk-11.0.15.10-hotspot
# org.gradle.java.home=C://Program Files//OpenJDK//jdk-17.0.2
org.gradle.java.home=/opt/homebrew/opt/openjdk@17
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,11 @@ tasks.register('wrapper', Wrapper) {
}

android {
compileSdk 33
compileSdk 34 // its best to keep this always aligned with the <TargetPlatformVersion> in the .csproj file and with BINDINGS_ANDROID___DOTNET_TARGET_PLATFORM_VERSION at the top of the github actions .yml file

defaultConfig {
minSdk 21
targetSdk 33
targetSdk 34 // its best to keep this always aligned with the <TargetPlatformVersion> in the .csproj file and with BINDINGS_ANDROID___DOTNET_TARGET_PLATFORM_VERSION at the top of the github actions .yml file

consumerProguardFiles "consumer-rules.pro"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
Expand All @@ -38,12 +38,12 @@ android {
}

dependencies {
implementation group: 'com.google.code.gson', name: 'gson', version: '2.9.1'
implementation group: 'com.google.code.gson', name: 'gson', version: '2.10.1'

implementation 'androidx.appcompat:appcompat:1.6.1'
implementation 'no.nordicsemi.android:mcumgr-ble:2.0.2'
implementation 'no.nordicsemi.android:mcumgr-core:2.0.2'
implementation 'com.google.android.material:material:1.8.0'
implementation 'androidx.appcompat:appcompat:1.7.0'
implementation 'no.nordicsemi.android:mcumgr-ble:2.2.1'
implementation 'no.nordicsemi.android:mcumgr-core:2.2.1'
implementation 'com.google.android.material:material:1.12.0'
}

// repositories {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,19 @@
import android.content.Context;
import androidx.annotation.NonNull;
import io.runtime.mcumgr.McuMgrCallback;
import io.runtime.mcumgr.McuMgrErrorCode;
import io.runtime.mcumgr.McuMgrTransport;
import io.runtime.mcumgr.ble.McuMgrBleTransport;
import io.runtime.mcumgr.exception.McuMgrException;
import io.runtime.mcumgr.managers.DefaultManager;
import io.runtime.mcumgr.response.HasReturnCode;
import io.runtime.mcumgr.response.dflt.McuMgrOsResponse;
import org.jetbrains.annotations.Contract;
import org.jetbrains.annotations.NotNull;

@SuppressWarnings("unused")
public class AndroidDeviceResetter {
public class AndroidDeviceResetter
{

private DefaultManager _manager;
private final McuMgrTransport _transport;
Expand All @@ -23,49 +27,59 @@ public class AndroidDeviceResetter {
* @param context the android-context of the calling environment
* @param bluetoothDevice the device to perform the firmware-install on
*/
public AndroidDeviceResetter(@NonNull final Context context, @NonNull final BluetoothDevice bluetoothDevice) {
public AndroidDeviceResetter(@NonNull final Context context, @NonNull final BluetoothDevice bluetoothDevice)
{
_transport = new McuMgrBleTransport(context, bluetoothDevice);
}

public void beginReset() {
public EAndroidDeviceResetterInitializationVerdict beginReset()
{
if (!IsCold())
{ //keep first
onError("[ADR.BR.000] Another reset operation is already in progress (state='" + _currentState + "')");

return EAndroidDeviceResetterInitializationVerdict.FAILED__OTHER_RESET_ALREADY_IN_PROGRESS;
}

try
{
_manager = new DefaultManager(_transport);
setState(EAndroidDeviceResetterState.IDLE); //order
_manager = new DefaultManager(_transport); //order
setState(EAndroidDeviceResetterState.RESETTING); //order

AndroidDeviceResetter self = this;
_manager.reset(new McuMgrCallback<McuMgrOsResponse>()
{
@Override
public void onResponse(@NotNull final McuMgrOsResponse response)
{
if (!response.isSuccess())
{ // check for an error return code
self.onError("[ADR.BR.002] Reset failed (error-code '" + response.getReturnCode().toString() + "')", response.getReturnCode(), response.getGroupReturnCode());
return;
}

setState(EAndroidDeviceResetterState.COMPLETE);
}

@Override
public void onError(@NotNull final McuMgrException exception)
{
self.onError("[ADR.BR.005] Reset failed '" + exception.getMessage() + "'", exception);
}
});
}
catch (final Exception ex)
{
setState(EAndroidDeviceResetterState.FAILED);
fatalErrorOccurredAdvertisement("Failed to create manager: '" + ex.getMessage() + "'");
return;
onError("[ADR.BR.010] Failed to initialize reset operation: '" + ex.getMessage() + "'", ex);
return EAndroidDeviceResetterInitializationVerdict.FAILED__ERROR_UPON_COMMENCING;
}

setState(EAndroidDeviceResetterState.RESETTING);

_manager.reset(new McuMgrCallback<McuMgrOsResponse>() {

@Override
public void onResponse(@NotNull final McuMgrOsResponse response) {
if (!response.isSuccess()) { // check for an error return code
fatalErrorOccurredAdvertisement("Reset failed (error-code '" + response.getReturnCode().toString() + "')");

setState(EAndroidDeviceResetterState.FAILED);
return;
}

setState(EAndroidDeviceResetterState.COMPLETE);
}

@Override
public void onError(@NotNull final McuMgrException error) {
fatalErrorOccurredAdvertisement("Reset failed '" + error.getMessage() + "'");

setState(EAndroidDeviceResetterState.FAILED);
}

});
return EAndroidDeviceResetterInitializationVerdict.SUCCESS;
}

public void disconnect() { //noinspection ConstantValue
public void disconnect()
{
if (_manager == null)
return;

Expand All @@ -76,38 +90,78 @@ public void disconnect() { //noinspection ConstantValue
mcuMgrTransporter.release();
}

public EAndroidDeviceResetterState getState() {
public EAndroidDeviceResetterState getState()
{
return _currentState;
}

private EAndroidDeviceResetterState _currentState = EAndroidDeviceResetterState.NONE;
private void setState(EAndroidDeviceResetterState newState) {

@Contract(pure = true)
private boolean IsCold()
{
return _currentState == EAndroidDeviceResetterState.NONE
|| _currentState == EAndroidDeviceResetterState.COMPLETE;
}

private void setState(final EAndroidDeviceResetterState newState)
{
final EAndroidDeviceResetterState oldState = _currentState; //order

_currentState = newState; //order

stateChangedAdvertisement(oldState, newState); //order
}

protected void onCleared() {
protected void onCleared()
{
// _manager.setFirmwareUpgradeCallback(null);
}

private String _lastFatalErrorMessage;

public String getLastFatalErrorMessage() {
@Contract(pure = true)
public String getLastFatalErrorMessage()
{
return _lastFatalErrorMessage;
}

public void fatalErrorOccurredAdvertisement(String errorMessage) {
_lastFatalErrorMessage = errorMessage; //this method is intentionally empty its meant to be overridden by csharp binding libraries to intercept updates
private void onError(final String errorMessage)
{
onError(errorMessage, null);
}

private void onError(final String errorMessage, final Exception exception)
{
onErrorImpl(errorMessage, McuMgrExceptionHelpers.DeduceGlobalErrorCodeFromException(exception));
}

private void onError(final String errorMessage, final McuMgrErrorCode exceptionCodeSpecs, final HasReturnCode.GroupReturnCode groupReturnCodeSpecs)
{
onErrorImpl(errorMessage, McuMgrExceptionHelpers.DeduceGlobalErrorCodeFromException(exceptionCodeSpecs, groupReturnCodeSpecs));
}

private void onErrorImpl(final String errorMessage, final int globalErrorCode)
{
setState(EAndroidDeviceResetterState.FAILED);

fatalErrorOccurredAdvertisement(errorMessage, globalErrorCode);
}

public void fatalErrorOccurredAdvertisement(final String errorMessage, final int globalErrorCode)
{ //this method is meant to be overridden by csharp binding libraries to intercept updates
_lastFatalErrorMessage = errorMessage;
}

public void logMessageAdvertisement(String message, String category, String level) {
@Contract(pure = true)
public void logMessageAdvertisement(final String message, final String category, final String level)
{
//this method is intentionally empty its meant to be overridden by csharp binding libraries to intercept updates
}

public void stateChangedAdvertisement(EAndroidDeviceResetterState oldState, EAndroidDeviceResetterState currentState) {
@Contract(pure = true)
public void stateChangedAdvertisement(final EAndroidDeviceResetterState oldState, final EAndroidDeviceResetterState currentState)
{
//this method is intentionally empty its meant to be overridden by csharp binding libraries to intercept updates
}

Expand Down
Loading

0 comments on commit 77f1042

Please sign in to comment.