Skip to content

Commit

Permalink
Add Android tv server (#11245)
Browse files Browse the repository at this point in the history
* added app server jni

* added getQrCodeFromPayload in SetupPayloadParser

* added TVServer app for android

* fix BLE error

* fix ci issue

* fix restyled errors

* fix ci issue

* fix Tests / Test Suites - Linux (tsan) ci issue

* fix zap issue, we should not add unneed functions in zap but fix undefined issue
  • Loading branch information
xylophone21 authored and pull[bot] committed Nov 2, 2023
1 parent 2241df1 commit 2723475
Show file tree
Hide file tree
Showing 100 changed files with 3,753 additions and 145 deletions.
1 change: 1 addition & 0 deletions BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,7 @@ if (current_toolchain != "${dir_pw_toolchain}/default:default") {

if (current_os == "android") {
deps += [
"${chip_root}/src/app/server/java",
"${chip_root}/src/controller/java",
"${chip_root}/src/platform/android:java",
"${chip_root}/src/setup_payload/java",
Expand Down
5 changes: 5 additions & 0 deletions build/config/compiler/BUILD.gn
Original file line number Diff line number Diff line change
Expand Up @@ -435,6 +435,11 @@ config("size_default") {
"-ffunction-sections",
"-fdata-sections",
]

# do not export functions in jni, or --gc-sections will not work and will be some undefined issues
if (current_os == "android") {
cflags += [ "-fvisibility=hidden" ]
}
}

config("stack_protector_default") {
Expand Down
61 changes: 61 additions & 0 deletions examples/tv-app/android/BUILD.gn
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
# Copyright (c) 2021 Project CHIP Authors
#
# 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.

import("//build_overrides/build.gni")
import("//build_overrides/chip.gni")

import("${chip_root}/build/chip/tools.gni")

# Todo: copy from examples/tv-app/linux but later will be moved to jni and upto java workd
source_set("android-tv-app") {
sources = [
"${chip_root}/examples/tv-app/tv-common/include/CHIPProjectAppConfig.h",
"include/account-login/AccountLoginManager.cpp",
"include/account-login/AccountLoginManager.h",
"include/application-basic/ApplicationBasicManager.cpp",
"include/application-basic/ApplicationBasicManager.h",
"include/application-launcher/ApplicationLauncherManager.cpp",
"include/application-launcher/ApplicationLauncherManager.h",
"include/audio-output/AudioOutputManager.cpp",
"include/audio-output/AudioOutputManager.h",
"include/cluster-change-attribute.cpp",
"include/cluster-init.cpp",
"include/content-launcher/ContentLauncherManager.cpp",
"include/content-launcher/ContentLauncherManager.h",
"include/endpoint-configuration/EndpointConfigurationStorage.cpp",
"include/endpoint-configuration/EndpointConfigurationStorage.h",
"include/keypad-input/KeypadInputManager.cpp",
"include/keypad-input/KeypadInputManager.h",
"include/low-power/LowPowerManager.cpp",
"include/low-power/LowPowerManager.h",
"include/media-input/MediaInputManager.cpp",
"include/media-input/MediaInputManager.h",
"include/media-playback/MediaPlaybackManager.cpp",
"include/media-playback/MediaPlaybackManager.h",
"include/target-navigator/TargetNavigatorManager.cpp",
"include/target-navigator/TargetNavigatorManager.h",
"include/tv-channel/TvChannelManager.cpp",
"include/tv-channel/TvChannelManager.h",
"include/wake-on-lan/WakeOnLanManager.cpp",
"include/wake-on-lan/WakeOnLanManager.h",
]

deps = [
"${chip_root}/examples/tv-app/tv-common",
"${chip_root}/src/lib",
"${chip_root}/third_party/inipp",
]

cflags = [ "-Wconversion" ]
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
/*
*
* Copyright (c) 2021 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.
*/

#include "AccountLoginManager.h"
#include <app-common/zap-generated/attribute-id.h>
#include <app-common/zap-generated/attribute-type.h>
#include <app-common/zap-generated/cluster-id.h>
#include <app-common/zap-generated/command-id.h>
#include <app-common/zap-generated/enums.h>
#include <app/Command.h>
#include <app/util/af.h>

using namespace std;

bool AccountLoginManager::isUserLoggedIn(string requestTempAccountIdentifier, string requestSetupPin)
{
// TODO: Fix hardcoding length of strings
requestTempAccountIdentifier = requestTempAccountIdentifier.substr(0, 4);
requestSetupPin = requestSetupPin.substr(0, 10);
for (auto it = accounts.cbegin(); it != accounts.cend(); ++it)
{
ChipLogProgress(Zcl, "temporary account id: %s", it->first.c_str());
ChipLogProgress(Zcl, "setup pin %s", it->second.c_str());
}

if (accounts.find(requestTempAccountIdentifier) != accounts.end())
{
bool found = accounts[requestTempAccountIdentifier] == requestSetupPin;
if (!found)
{
ChipLogError(Zcl, "User is not logged in, failed to match request setup pin.");
}
return found;
}
else
{
ChipLogError(Zcl, "User is not logged in, failed to find temp account identifier.");
return false;
}
}

void AccountLoginManager::setTempAccountIdentifierForPin(string tempAccountIdentifier, string setupPin)
{
// TODO: Fix hardcoding length of strings
string tempId = tempAccountIdentifier.substr(0, 4);
accounts[tempId] = setupPin;
}

string AccountLoginManager::proxySetupPinRequest(string requestTempAccountIdentifier, chip::EndpointId endpoint)
{
// TODO: Insert your code here to send temp account identifier request
return "tempPin123";
}

bool accountLoginClusterIsUserLoggedIn(std::string requestTempAccountIdentifier, std::string requestSetupPin)
{
return AccountLoginManager().GetInstance().isUserLoggedIn(requestTempAccountIdentifier, requestSetupPin);
}

std::string accountLoginClusterGetSetupPin(std::string requestTempAccountIdentifier, chip::EndpointId endpoint)
{
string responseSetupPin = AccountLoginManager().proxySetupPinRequest(requestTempAccountIdentifier, endpoint);
AccountLoginManager().GetInstance().setTempAccountIdentifierForPin(requestTempAccountIdentifier, responseSetupPin);
return responseSetupPin;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
/*
*
* Copyright (c) 2021 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.
*/

#pragma once

#include <app/util/af-types.h>
#include <lib/core/CHIPError.h>
#include <map>
#include <string>

class AccountLoginManager
{
public:
bool isUserLoggedIn(std::string requestTempAccountIdentifier, std::string requestSetupPin);
std::string proxySetupPinRequest(std::string requestTempAccountIdentifier, chip::EndpointId endpoint);
void setTempAccountIdentifierForPin(std::string requestTempAccountIdentifier, std::string requestSetupPin);

static AccountLoginManager & GetInstance()
{
static AccountLoginManager instance;
return instance;
}

private:
std::map<std::string, std::string> accounts;
};
32 changes: 32 additions & 0 deletions examples/tv-app/android/include/application-basic/Application.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
/*
*
* Copyright (c) 2021 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.
*/

#pragma once

#include <app-common/zap-generated/enums.h>

struct Application
{
char vendorName[32] = "";
char name[32] = "";
char id[32] = "";
uint16_t vendorId = 0;
uint16_t productId = 0;
uint16_t catalogVendorId = 0;
EmberAfApplicationBasicStatus status = EMBER_ZCL_APPLICATION_BASIC_STATUS_STOPPED;
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,161 @@
/*
*
* Copyright (c) 2021 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.
*/

#include "ApplicationBasicManager.h"
#include <app-common/zap-generated/attribute-id.h>
#include <app-common/zap-generated/attribute-type.h>
#include <app-common/zap-generated/cluster-id.h>
#include <app-common/zap-generated/command-id.h>
#include <app-common/zap-generated/enums.h>
#include <app/Command.h>
#include <app/util/af.h>
#include <app/util/basic-types.h>
#include <lib/support/ZclString.h>

#include <inipp/inipp.h>

using namespace chip;

CHIP_ERROR ApplicationBasicManager::Init()
{
CHIP_ERROR err = CHIP_NO_ERROR;
EndpointConfigurationStorage & endpointConfiguration = EndpointConfigurationStorage::GetInstance();
err = endpointConfiguration.Init();
SuccessOrExit(err);
es = &endpointConfiguration;
exit:
return err;
}

void ApplicationBasicManager::store(chip::EndpointId endpoint, Application * application)
{
uint8_t bufferMemory[64];
MutableByteSpan zclString(bufferMemory);

MakeZclCharString(zclString, application->vendorName);
EmberAfStatus vendorNameStatus =
emberAfWriteServerAttribute(endpoint, ZCL_APPLICATION_BASIC_CLUSTER_ID, ZCL_APPLICATION_VENDOR_NAME_ATTRIBUTE_ID,
zclString.data(), ZCL_CHAR_STRING_ATTRIBUTE_TYPE);
if (vendorNameStatus != EMBER_ZCL_STATUS_SUCCESS)
{
ChipLogError(Zcl, "Failed to store vendor name attribute.");
}

EmberAfStatus vendorIdStatus =
emberAfWriteServerAttribute(endpoint, ZCL_APPLICATION_BASIC_CLUSTER_ID, ZCL_APPLICATION_VENDOR_ID_ATTRIBUTE_ID,
(uint8_t *) &application->vendorId, ZCL_INT16U_ATTRIBUTE_TYPE);
if (vendorIdStatus != EMBER_ZCL_STATUS_SUCCESS)
{
ChipLogError(Zcl, "Failed to store vendor id attribute.");
}

MakeZclCharString(zclString, application->name);
EmberAfStatus nameStatus =
emberAfWriteServerAttribute(endpoint, ZCL_APPLICATION_BASIC_CLUSTER_ID, ZCL_APPLICATION_NAME_ATTRIBUTE_ID, zclString.data(),
ZCL_CHAR_STRING_ATTRIBUTE_TYPE);
if (nameStatus != EMBER_ZCL_STATUS_SUCCESS)
{
ChipLogError(Zcl, "Failed to store name attribute.");
}

EmberAfStatus productIdStatus =
emberAfWriteServerAttribute(endpoint, ZCL_APPLICATION_BASIC_CLUSTER_ID, ZCL_APPLICATION_PRODUCT_ID_ATTRIBUTE_ID,
(uint8_t *) &application->productId, ZCL_INT16U_ATTRIBUTE_TYPE);
if (productIdStatus != EMBER_ZCL_STATUS_SUCCESS)
{
ChipLogError(Zcl, "Failed to store product id attribute.");
}

MakeZclCharString(zclString, application->id);
EmberAfStatus idStatus =
emberAfWriteServerAttribute(endpoint, ZCL_APPLICATION_BASIC_CLUSTER_ID, ZCL_APPLICATION_ID_ATTRIBUTE_ID, zclString.data(),
ZCL_CHAR_STRING_ATTRIBUTE_TYPE);
if (idStatus != EMBER_ZCL_STATUS_SUCCESS)
{
ChipLogError(Zcl, "Failed to store id attribute.");
}

EmberAfStatus catalogVendorIdStatus =
emberAfWriteServerAttribute(endpoint, ZCL_APPLICATION_BASIC_CLUSTER_ID, ZCL_CATALOG_VENDOR_ID_ATTRIBUTE_ID,
(uint8_t *) &application->catalogVendorId, ZCL_INT16U_ATTRIBUTE_TYPE);
if (catalogVendorIdStatus != EMBER_ZCL_STATUS_SUCCESS)
{
ChipLogError(Zcl, "Failed to store catalog vendor id attribute.");
}

EmberAfStatus applicationStatus =
emberAfWriteServerAttribute(endpoint, ZCL_APPLICATION_BASIC_CLUSTER_ID, ZCL_APPLICATION_STATUS_ATTRIBUTE_ID,
(uint8_t *) &application->status, ZCL_ENUM8_ATTRIBUTE_TYPE);
if (applicationStatus != EMBER_ZCL_STATUS_SUCCESS)
{
ChipLogError(Zcl, "Failed to store status attribute.");
}
}

Application ApplicationBasicManager::getApplicationForEndpoint(chip::EndpointId endpoint)
{
Application app = {};
uint16_t size = static_cast<uint16_t>(sizeof(app.name));

std::string section = "endpoint" + std::to_string(endpoint);

CHIP_ERROR err = es->get(section, "name", app.name, size);
if (err != CHIP_NO_ERROR)
{
ChipLogError(Zcl, "Failed to get app name. Error:%s", chip::ErrorStr(err));
}

err = es->get(section, "vendorName", app.vendorName, size);
if (err != CHIP_NO_ERROR)
{
ChipLogError(Zcl, "Failed to get app vendor name. Error:%s", chip::ErrorStr(err));
}

err = es->get(section, "id", app.id, size);
if (err != CHIP_NO_ERROR)
{
ChipLogError(Zcl, "Failed to get app id. Error:%s", chip::ErrorStr(err));
}

err = es->get(section, "catalogVendorId", app.catalogVendorId);
if (err != CHIP_NO_ERROR)
{
ChipLogError(Zcl, "Failed to get app catalog vendor id. Error:%s", chip::ErrorStr(err));
}

err = es->get(section, "productId", app.productId);
if (err != CHIP_NO_ERROR)
{
ChipLogError(Zcl, "Failed to get app product id. Error:%s", chip::ErrorStr(err));
}

err = es->get(section, "vendorId", app.vendorId);
if (err != CHIP_NO_ERROR)
{
ChipLogError(Zcl, "Failed to get app vendor id. Error:%s", chip::ErrorStr(err));
}

return app;
}

bool applicationBasicClusterChangeApplicationStatus(EmberAfApplicationBasicStatus status, chip::EndpointId endpoint)
{
// TODO: Insert code here
ChipLogProgress(Zcl, "Sent an application status change request %d for endpoint %d", status, endpoint);
return true;
}
Loading

0 comments on commit 2723475

Please sign in to comment.