Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Android, Java] Update ICD device Info parameter #31339

Merged
Merged
Show file tree
Hide file tree
Changes from 6 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
Original file line number Diff line number Diff line change
Expand Up @@ -57,12 +57,7 @@ open class GenericChipDeviceListener : ChipDeviceController.CompletionListener {
// No op
}

override fun onICDRegistrationComplete(
errorCode: Int,
icdNodeId: Long,
icdCounter: Long,
icdDeviceInfo: ICDDeviceInfo
) {
override fun onICDRegistrationComplete(errorCode: Int, icdDeviceInfo: ICDDeviceInfo) {
// No op
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -294,16 +294,22 @@ class DeviceProvisioningFragment : Fragment() {
)
}

override fun onICDRegistrationComplete(
errorCode: Int,
icdNodeId: Long,
icdCounter: Long,
icdDeviceInfo: ICDDeviceInfo
) {
override fun onICDRegistrationComplete(errorCode: Int, icdDeviceInfo: ICDDeviceInfo) {
Log.d(
TAG,
"onICDRegistrationComplete - errorCode: $errorCode, icdNodeId : $icdNodeId, icdCounter : $icdCounter, symmetricKey : ${icdDeviceInfo.symmetricKey.toHex()}"
"onICDRegistrationComplete - errorCode: $errorCode, symmetricKey : ${icdDeviceInfo.symmetricKey.toHex()}, icdDeviceInfo : $icdDeviceInfo"
)
requireActivity().runOnUiThread {
Toast.makeText(
requireActivity(),
getString(
R.string.icd_registration_completed,
icdDeviceInfo.userActiveModeTriggerHint.toString()
),
Toast.LENGTH_LONG
)
.show()
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -276,4 +276,5 @@
<string name="ota_provider_node_id_text">Node ID</string>

<string name="icd_btn_text">Intermittently Connected Device</string>
<string name="icd_registration_completed">ICD device registration completed, How to trigger to switch to Active Mode : %1$s</string>
</resources>
Original file line number Diff line number Diff line change
Expand Up @@ -186,15 +186,10 @@ abstract class PairingCommand(
.updateCommissioningICDRegistrationInfo(ICDRegistrationInfo.newBuilder().build())
}

override fun onICDRegistrationComplete(
errorCode: Int,
icdNodeId: Long,
icdCounter: Long,
icdDeviceInfo: ICDDeviceInfo
) {
override fun onICDRegistrationComplete(errorCode: Int, icdDeviceInfo: ICDDeviceInfo) {
logger.log(
Level.INFO,
"onICDRegistrationComplete with errorCode: $errorCode, icdNodeId: $icdNodeId, icdCounter: $icdCounter, symmetricKey: ${icdDeviceInfo.symmetricKey.toHex()}"
"onICDRegistrationComplete with errorCode: $errorCode, symmetricKey: ${icdDeviceInfo.symmetricKey.toHex()}, icdDeviceInfo: $icdDeviceInfo"
)
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -178,15 +178,10 @@ abstract class PairingCommand(
logger.log(Level.INFO, "onICDRegistrationInfoRequired")
}

override fun onICDRegistrationComplete(
errorCode: Int,
icdNodeId: Long,
icdCounter: Long,
icdDeviceInfo: ICDDeviceInfo
) {
override fun onICDRegistrationComplete(errorCode: Int, icdDeviceInfo: ICDDeviceInfo) {
logger.log(
Level.INFO,
"onICDRegistrationComplete with errorCode: $errorCode, icdNodeId: $icdNodeId, icdCounter: $icdCounter, symmetricKey: ${icdDeviceInfo.symmetricKey.toHex()}"
"onICDRegistrationComplete with errorCode: $errorCode, symmetricKey: ${icdDeviceInfo.symmetricKey.toHex()}, icdDeviceInfo: $icdDeviceInfo"
)
}

Expand Down
23 changes: 17 additions & 6 deletions src/controller/java/AndroidDeviceControllerWrapper.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -713,6 +713,10 @@ void AndroidDeviceControllerWrapper::OnReadCommissioningInfo(const chip::Control
&onReadCommissioningInfoMethod);
VerifyOrReturn(err == CHIP_NO_ERROR, ChipLogError(Controller, "Error finding Java method: %" CHIP_ERROR_FORMAT, err.Format()));

// For ICD
mUserActiveModeTriggerHint = info.icd.userActiveModeTriggerHint;
CopyCharSpanToMutableCharSpan(info.icd.userActiveModeTriggerInstruction, mUserActiveModeTriggerInstruction);

env->CallVoidMethod(mJavaObjectRef, onReadCommissioningInfoMethod, static_cast<jint>(info.basic.vendorId),
static_cast<jint>(info.basic.productId), static_cast<jint>(info.network.wifi.endpoint),
static_cast<jint>(info.network.thread.endpoint));
Expand Down Expand Up @@ -939,32 +943,39 @@ void AndroidDeviceControllerWrapper::OnICDRegistrationComplete(chip::NodeId icdN
mDeviceIsICD = true;

JNIEnv * env = JniReferences::GetInstance().GetEnvForCurrentThread();

JniLocalReferenceManager manager(env);
jmethodID onICDRegistrationCompleteMethod;
jclass icdDeviceInfoClass = nullptr;
jmethodID icdDeviceInfoStructCtor = nullptr;
jobject icdDeviceInfoObj = nullptr;
jbyteArray jSymmetricKey = nullptr;
CHIP_ERROR methodErr =
JniReferences::GetInstance().FindMethod(env, mJavaObjectRef, "onICDRegistrationComplete",
"(IJJLchip/devicecontroller/ICDDeviceInfo;)V", &onICDRegistrationCompleteMethod);
"(ILchip/devicecontroller/ICDDeviceInfo;)V", &onICDRegistrationCompleteMethod);
VerifyOrReturn(methodErr == CHIP_NO_ERROR,
ChipLogError(Controller, "Error finding Java method: %" CHIP_ERROR_FORMAT, methodErr.Format()));

methodErr = chip::JniReferences::GetInstance().GetClassRef(env, "chip/devicecontroller/ICDDeviceInfo", icdDeviceInfoClass);
methodErr = chip::JniReferences::GetInstance().GetLocalClassRef(env, "chip/devicecontroller/ICDDeviceInfo", icdDeviceInfoClass);
VerifyOrReturn(methodErr == CHIP_NO_ERROR, ChipLogError(Controller, "Could not find class ICDDeviceInfo"));

icdDeviceInfoStructCtor = env->GetMethodID(icdDeviceInfoClass, "<init>", "([B)V");
icdDeviceInfoStructCtor = env->GetMethodID(icdDeviceInfoClass, "<init>", "([BILjava/lang/String;JJJJJ)V");
VerifyOrReturn(icdDeviceInfoStructCtor != nullptr, ChipLogError(Controller, "Could not find ICDDeviceInfo constructor"));

methodErr =
JniReferences::GetInstance().N2J_ByteArray(env, symmetricKey.data(), static_cast<jint>(symmetricKey.size()), jSymmetricKey);
VerifyOrReturn(methodErr == CHIP_NO_ERROR,
ChipLogError(Controller, "Error Parsing Symmetric Key: %" CHIP_ERROR_FORMAT, methodErr.Format()));

icdDeviceInfoObj = env->NewObject(icdDeviceInfoClass, icdDeviceInfoStructCtor, jSymmetricKey);
jstring jUserActiveModeTriggerInstruction = env->NewStringUTF(mUserActiveModeTriggerInstruction.data());

icdDeviceInfoObj = env->NewObject(
icdDeviceInfoClass, icdDeviceInfoStructCtor, jSymmetricKey, static_cast<jint>(mUserActiveModeTriggerHint.Raw()),
jUserActiveModeTriggerInstruction, static_cast<jlong>(icdNodeId), static_cast<jlong>(icdCounter),
static_cast<jlong>(mAutoCommissioner.GetCommissioningParameters().GetICDMonitoredSubject().Value()),
static_cast<jlong>(Controller()->GetFabricId()), static_cast<jlong>(Controller()->GetFabricIndex()));

env->CallVoidMethod(mJavaObjectRef, onICDRegistrationCompleteMethod, static_cast<jint>(err.AsInteger()),
static_cast<jlong>(icdNodeId), static_cast<jlong>(icdCounter), icdDeviceInfoObj);
env->CallVoidMethod(mJavaObjectRef, onICDRegistrationCompleteMethod, static_cast<jint>(err.AsInteger()), icdDeviceInfoObj);
}

CHIP_ERROR AndroidDeviceControllerWrapper::SyncGetKeyValue(const char * key, void * value, uint16_t & size)
Expand Down
5 changes: 5 additions & 0 deletions src/controller/java/AndroidDeviceControllerWrapper.h
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,8 @@
#include "OTAProviderDelegateBridge.h"
#endif

constexpr uint8_t kUserActiveModeTriggerInstructionBufferLen =
128 + 1; // 128bytes is max UserActiveModeTriggerInstruction size and 1 byte is for escape sequence.
/**
* This class contains all relevant information for the JNI view of CHIPDeviceController
* to handle all controller-related processing.
Expand Down Expand Up @@ -256,6 +258,9 @@ class AndroidDeviceControllerWrapper : public chip::Controller::DevicePairingDel
#endif
bool mDeviceIsICD = false;
uint8_t mICDSymmetricKey[chip::Crypto::kAES_CCM128_Key_Length];
char mUserActiveModeTriggerInstructionBuffer[kUserActiveModeTriggerInstructionBufferLen];
chip::MutableCharSpan mUserActiveModeTriggerInstruction = chip::MutableCharSpan(mUserActiveModeTriggerInstructionBuffer);
chip::BitMask<chip::app::Clusters::IcdManagement::UserActiveModeTriggerBitmap> mUserActiveModeTriggerHint;

AndroidDeviceControllerWrapper(ChipDeviceControllerPtr controller,
#ifdef JAVA_MATTER_CONTROLLER_TEST
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -606,10 +606,9 @@ public void onICDRegistrationInfoRequired() {
}
}

public void onICDRegistrationComplete(
int errorCode, long icdNodeId, long icdCounter, ICDDeviceInfo icdDeviceInfo) {
public void onICDRegistrationComplete(int errorCode, ICDDeviceInfo icdDeviceInfo) {
if (completionListener != null) {
completionListener.onICDRegistrationComplete(errorCode, icdNodeId, icdCounter, icdDeviceInfo);
completionListener.onICDRegistrationComplete(errorCode, icdDeviceInfo);
}
}

Expand Down Expand Up @@ -1621,7 +1620,6 @@ void onReadCommissioningInfo(
void onICDRegistrationInfoRequired();

/** Notifies when the registration flow for the ICD completes. */
void onICDRegistrationComplete(
int errorCode, long icdNodeId, long icdCounter, ICDDeviceInfo icdDeviceInfo);
void onICDRegistrationComplete(int errorCode, ICDDeviceInfo icdDeviceInfo);
}
}
141 changes: 139 additions & 2 deletions src/controller/java/src/chip/devicecontroller/ICDDeviceInfo.java
Original file line number Diff line number Diff line change
Expand Up @@ -17,16 +17,153 @@
*/
package chip.devicecontroller;

import java.util.HashSet;
import java.util.Set;

/** Class for holding ICD Device information. */
public class ICDDeviceInfo {
private byte[] symmetricKey;
/** List of methods to trigger the ICD to switch to Active mode. */
public enum UserActiveModeTriggerBitmap {
PowerCycle(0),
yunhanw-google marked this conversation as resolved.
Show resolved Hide resolved
SettingsMenu(1),
CustomInstruction(2),
DeviceManual(3),
ActuateSensor(4),
ActuateSensorSeconds(5),
ActuateSensorTimes(6),
ActuateSensorLightsBlink(7),
ResetButton(8),
ResetButtonLightsBlink(9),
ResetButtonSeconds(10),
ResetButtonTimes(11),
SetupButton(12),
SetupButtonSeconds(13),
SetupButtonLightsBlink(14),
SetupButtonTimes(15),
AppDefinedButton(16);

private final int bitIndex;

public ICDDeviceInfo(byte[] symmetricKey) {
UserActiveModeTriggerBitmap(int bitIndex) {
this.bitIndex = bitIndex;
}

public int getBitIndex() {
return bitIndex;
}
}

private final byte[] symmetricKey;
private final Set<UserActiveModeTriggerBitmap> userActiveModeTriggerHint;
private final String userActiveModeTriggerInstruction;
private final long icdNodeId;
private final long icdCounter;
private final long monitoredSubject;
private final long fabricId;
private final long fabricIndex;

ICDDeviceInfo(
byte[] symmetricKey,
Set<UserActiveModeTriggerBitmap> userActiveModeTriggerHint,
String userActiveModeTriggerInstruction,
long icdNodeId,
yunhanw-google marked this conversation as resolved.
Show resolved Hide resolved
long icdCounter,
long monitoredSubject,
long fabricId,
long fabricIndex) {
this.symmetricKey = symmetricKey;
this.userActiveModeTriggerHint = userActiveModeTriggerHint;
this.userActiveModeTriggerInstruction = userActiveModeTriggerInstruction;
this.icdNodeId = icdNodeId;
this.icdCounter = icdCounter;
this.monitoredSubject = monitoredSubject;
this.fabricId = fabricId;
this.fabricIndex = fabricIndex;
}

ICDDeviceInfo(
byte[] symmetricKey,
int userActiveModeTriggerHintRaw,
String userActiveModeTriggerInstruction,
long icdNodeId,
long icdCounter,
long monitoredSubject,
long fabricId,
long fabricIndex) {
this.symmetricKey = symmetricKey;
this.userActiveModeTriggerInstruction = userActiveModeTriggerInstruction;
this.icdNodeId = icdNodeId;
this.icdCounter = icdCounter;
this.monitoredSubject = monitoredSubject;
this.fabricId = fabricId;
this.fabricIndex = fabricIndex;

this.userActiveModeTriggerHint = new HashSet<>();
for (UserActiveModeTriggerBitmap mode : UserActiveModeTriggerBitmap.values()) {
int bitmask = 1 << mode.getBitIndex();
if ((userActiveModeTriggerHintRaw & bitmask) != 0) {
userActiveModeTriggerHint.add(mode);
}
}
}

/** Returns the 16 bytes ICD symmetric key. */
public byte[] getSymmetricKey() {
return symmetricKey;
}

/** Returns the Set of UserActiveModeTriggerHint. */
public Set<UserActiveModeTriggerBitmap> getUserActiveModeTriggerHint() {
return userActiveModeTriggerHint;
}

/** Returns the UserActiveModeTriggerInstruction. */
public String getUserActiveModeTriggerInstruction() {
return userActiveModeTriggerInstruction;
}

/** Returns the ICD Node Id. */
public long getIcdNodeId() {
return icdNodeId;
}

/** Returns the ICD Counter. */
public long getIcdCounter() {
return icdCounter;
}

/** Returns the Monitored Subject. */
public long getMonitoredSubject() {
return monitoredSubject;
}

/** Returns the Fabric Id */
public long getFabricId() {
return fabricId;
}

/** Returns the Fabric Index */
public long getFabricIndex() {
return fabricIndex;
}

@Override
public String toString() {
return "ICDDeviceInfo : {"
+ "\n\tuserActiveModeTriggerHint : "
+ userActiveModeTriggerHint
+ "\n\tuserActiveModeTriggerInstruction : "
+ userActiveModeTriggerInstruction
+ "\n\ticdNodeId : "
+ icdNodeId
+ "\n\ticdCounter : "
+ icdCounter
+ "\n\tmonitoredSubject : "
+ monitoredSubject
+ "\n\tfabricId : "
+ fabricId
+ "\n\tfabricIndex : "
+ fabricIndex
+ "\n}";
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -52,12 +52,8 @@ class CompletionListenerAdapter(val listener: MatterController.CompletionListene

override fun onICDRegistrationInfoRequired() = listener.onICDRegistrationInfoRequired()

override fun onICDRegistrationComplete(
errorCode: Int,
icdNodeId: Long,
icdCounter: Long,
icdDeviceInfo: ICDDeviceInfo
) = listener.onICDRegistrationComplete(errorCode, icdNodeId, icdCounter, icdDeviceInfo)
override fun onICDRegistrationComplete(errorCode: Int, icdDeviceInfo: ICDDeviceInfo) =
yunhanw-google marked this conversation as resolved.
Show resolved Hide resolved
listener.onICDRegistrationComplete(errorCode, icdDeviceInfo)

override fun onError(error: Throwable) = listener.onError(error)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -66,12 +66,7 @@ interface MatterController : Closeable, InteractionClient {
fun onICDRegistrationInfoRequired()

/** Notifies when the registration flow for the ICD completes. */
fun onICDRegistrationComplete(
errorCode: Int,
icdNodeId: Long,
icdCounter: Long,
icdDeviceInfo: ICDDeviceInfo
)
fun onICDRegistrationComplete(errorCode: Int, icdDeviceInfo: ICDDeviceInfo)
yunhanw-google marked this conversation as resolved.
Show resolved Hide resolved
}

/**
Expand Down
Loading