Skip to content

Commit

Permalink
[Android] Implement Java TLV Decoder API (#27586)
Browse files Browse the repository at this point in the history
* Implement Android TLV Decoder

* Restyled by google-java-format

* Restyled by clang-format

* fix merge conflict

* restyle

---------

Co-authored-by: Restyled.io <[email protected]>
Co-authored-by: Andrei Litvin <[email protected]>
  • Loading branch information
3 people authored and pull[bot] committed Jan 13, 2024
1 parent a1116f5 commit 2344172
Show file tree
Hide file tree
Showing 5 changed files with 150 additions and 6 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ import android.view.ViewGroup
import androidx.fragment.app.Fragment
import androidx.lifecycle.lifecycleScope
import chip.devicecontroller.ChipDeviceController
import chip.devicecontroller.ChipStructs
import chip.devicecontroller.ChipTLVValueDecoder
import chip.devicecontroller.ClusterIDMapping.OperationalCredentials
import chip.devicecontroller.InvokeCallback
import chip.devicecontroller.ReportCallback
Expand Down Expand Up @@ -120,8 +122,37 @@ class OpCredClientFragment : Fragment() {
?.getAttributeState(attributeId)
?.value
?: "null"
Log.i(TAG, "OpCred $attributeName value: $value")
showMessage("OpCred $attributeName value: $value")
val tlv =
nodeState
?.getEndpointState(endpointId)
?.getClusterState(clusterId)
?.getAttributeState(attributeId)
?.tlv

if (tlv == null) {
Log.i(TAG, "OpCred $attributeName value: $value")
showMessage("OpCred $attributeName value: $value")
return
}

val attributePath = ChipAttributePath.newInstance(endpointId, clusterId, attributeId)
when (attribute) {
OperationalCredentials.Attribute.Fabrics -> {
val ret =
ChipTLVValueDecoder.decodeAttributeValue<
List<ChipStructs.OperationalCredentialsClusterFabricDescriptorStruct>
>(
attributePath,
tlv
)
Log.i(TAG, "OpCred $attributeName value: $value")
showMessage(ret.toString())
}
else -> {
Log.i(TAG, "OpCred $attributeName value: $value")
showMessage("OpCred $attributeName value: $value")
}
}
}
},
devicePtr,
Expand Down
2 changes: 2 additions & 0 deletions src/controller/java/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,7 @@ shared_library("jni") {
"CHIPDefaultCallbacks.cpp",
"CHIPDefaultCallbacks.h",
"CHIPDeviceController-JNI.cpp",
"CHIPTLVValueDecoder-JNI.cpp",
"DeviceAttestationDelegateBridge.cpp",
"DeviceAttestationDelegateBridge.h",
"zap-generated/CHIPAttributeTLVValueDecoder.cpp",
Expand Down Expand Up @@ -328,6 +329,7 @@ android_library("java") {
"src/chip/devicecontroller/ChipDeviceController.java",
"src/chip/devicecontroller/ChipDeviceControllerException.java",
"src/chip/devicecontroller/ChipIdLookup.java",
"src/chip/devicecontroller/ChipTLVValueDecoder.java",
"src/chip/devicecontroller/ControllerParams.java",
"src/chip/devicecontroller/DeviceAttestationDelegate.java",
"src/chip/devicecontroller/DiscoveredDevice.java",
Expand Down
8 changes: 4 additions & 4 deletions src/controller/java/CHIPDeviceController-JNI.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -81,11 +81,11 @@ static CHIP_ERROR N2J_NetworkLocation(JNIEnv * env, jstring ipAddress, jint port
static CHIP_ERROR GetChipPathIdValue(jobject chipPathId, uint32_t wildcardValue, uint32_t & outValue);
static CHIP_ERROR ParseAttributePathList(jobject attributePathList,
std::vector<app::AttributePathParams> & outAttributePathParamsList);
static CHIP_ERROR ParseAttributePath(jobject attributePath, EndpointId & outEndpointId, ClusterId & outClusterId,
AttributeId & outAttributeId);
CHIP_ERROR ParseAttributePath(jobject attributePath, EndpointId & outEndpointId, ClusterId & outClusterId,
AttributeId & outAttributeId);
static CHIP_ERROR ParseEventPathList(jobject eventPathList, std::vector<app::EventPathParams> & outEventPathParamsList);
static CHIP_ERROR ParseEventPath(jobject eventPath, EndpointId & outEndpointId, ClusterId & outClusterId, EventId & outEventId,
bool & outIsUrgent);
CHIP_ERROR ParseEventPath(jobject eventPath, EndpointId & outEndpointId, ClusterId & outClusterId, EventId & outEventId,
bool & outIsUrgent);
static CHIP_ERROR IsWildcardChipPathId(jobject chipPathId, bool & isWildcard);

namespace {
Expand Down
83 changes: 83 additions & 0 deletions src/controller/java/CHIPTLVValueDecoder-JNI.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,83 @@
#include "lib/core/CHIPError.h"
#include "lib/support/JniTypeWrappers.h"

// #include <lib/support/CHIPMem.h>
// #include <lib/support/CodeUtils.h>
#include <lib/support/JniReferences.h>
#include <lib/support/logging/CHIPLogging.h>

#include "CHIPAttributeTLVValueDecoder.h"
#include "CHIPEventTLVValueDecoder.h"

#include <jni.h>

using namespace chip;

#define JNI_METHOD(RETURN, METHOD_NAME) \
extern "C" JNIEXPORT RETURN JNICALL Java_chip_devicecontroller_ChipTLVValueDecoder_##METHOD_NAME

extern CHIP_ERROR ParseAttributePath(jobject attributePath, EndpointId & outEndpointId, ClusterId & outClusterId,
AttributeId & outAttributeId);
extern CHIP_ERROR ParseEventPath(jobject eventPath, EndpointId & outEndpointId, ClusterId & outClusterId, EventId & outEventId,
bool & outIsUrgent);

JNI_METHOD(jobject, decodeAttributeValue)(JNIEnv * env, jclass clazz, jobject attributePath, jbyteArray jTlv)
{
EndpointId endpointId;
ClusterId clusterId;
AttributeId attributeId;
CHIP_ERROR err = ParseAttributePath(attributePath, endpointId, clusterId, attributeId);
if (err != CHIP_NO_ERROR)
{
ChipLogProgress(Controller, "decode error attributePath");
return nullptr;
}

JniByteArray tlv(env, jTlv);

chip::app::ConcreteAttributePath path(endpointId, clusterId, attributeId);

chip::TLV::TLVReader reader;
reader.Init(tlv.byteSpan());
reader.Next();

jobject ret = DecodeAttributeValue(path, reader, &err);

if (err != CHIP_NO_ERROR)
{
ChipLogProgress(Controller, "decode error attributeValue");
return nullptr;
}

return ret;
}

JNI_METHOD(jobject, decodeEventValue)(JNIEnv * env, jclass clazz, jobject eventPath, jbyteArray jTlv)
{
EndpointId endpointId;
ClusterId clusterId;
EventId eventId;
bool isUrgent;
CHIP_ERROR err = ParseEventPath(eventPath, endpointId, clusterId, eventId, isUrgent);
if (err != CHIP_NO_ERROR)
{
return nullptr;
}

JniByteArray tlv(env, jTlv);

chip::app::ConcreteEventPath path(endpointId, clusterId, eventId);
chip::TLV::TLVReader reader;

reader.Init(tlv.byteSpan());
reader.Next();

jobject ret = DecodeEventValue(path, reader, &err);

if (err != CHIP_NO_ERROR)
{
return nullptr;
}

return ret;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/*
* Copyright (c) 2020-2023 Project CHIP Authors
* All rights reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/

package chip.devicecontroller;

import chip.devicecontroller.model.ChipAttributePath;
import chip.devicecontroller.model.ChipEventPath;

public class ChipTLVValueDecoder {
public static native <T> T decodeAttributeValue(ChipAttributePath attributePath, byte[] tlv);

public static native <T> T decodeEventValue(ChipEventPath eventPath, byte[] tlv);
}

0 comments on commit 2344172

Please sign in to comment.