From 2a05b8f5df6958c702a4573072c1286b3b288ebd Mon Sep 17 00:00:00 2001 From: Brian W Date: Tue, 29 Mar 2022 16:42:12 -0700 Subject: [PATCH 01/14] Move lightranger app to different folder --- .gitmodules | 6 ------ avnet_lightranger5/AzureSphereDevX | 1 - .../avnet_lightranger5}/.vscode/launch.json | 0 .../avnet_lightranger5}/.vscode/settings.json | 0 .../avnet_lightranger5}/CMakeLists.txt | 0 .../avnet_lightranger5}/CMakeSettings.json | 0 .../avnet_lightranger5}/README.md | 0 .../avnet_lightranger5}/app_exit_codes.h | 0 .../avnet_lightranger5}/app_manifest.json | 0 .../avnet_lightranger5}/applibs_versions.h | 0 .../avnet_lightranger5}/azsphere_board.txt | 0 .../avnet_lightranger5}/launch.vs.json | 0 .../avnet_lightranger5}/lightranger5_click.h | 0 .../avnet_lightranger5}/main.c | 0 .../avnet_lightranger5}/main.h | 0 15 files changed, 7 deletions(-) delete mode 160000 avnet_lightranger5/AzureSphereDevX rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/.vscode/launch.json (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/.vscode/settings.json (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/CMakeLists.txt (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/CMakeSettings.json (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/README.md (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/app_exit_codes.h (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/app_manifest.json (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/applibs_versions.h (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/azsphere_board.txt (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/launch.vs.json (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/lightranger5_click.h (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/main.c (100%) rename {avnet_lightranger5 => avnet_sensors_converge/avnet_lightranger5}/main.h (100%) diff --git a/.gitmodules b/.gitmodules index 2024270..97ddfa5 100644 --- a/.gitmodules +++ b/.gitmodules @@ -160,9 +160,3 @@ [submodule ".\\avnet_rsl10_2devices\\HardwareDefinitions"] path = .\\avnet_rsl10_2devices\\HardwareDefinitions url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git -[submodule "avnet_lightranger5/AzureSphereDevX"] - path = avnet_lightranger5/AzureSphereDevX - url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.git -[submodule "avnet_lightranger5/HardwareDefinitions"] - path = avnet_lightranger5/HardwareDefinitions - url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git diff --git a/avnet_lightranger5/AzureSphereDevX b/avnet_lightranger5/AzureSphereDevX deleted file mode 160000 index 32fb212..0000000 --- a/avnet_lightranger5/AzureSphereDevX +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 diff --git a/avnet_lightranger5/.vscode/launch.json b/avnet_sensors_converge/avnet_lightranger5/.vscode/launch.json similarity index 100% rename from avnet_lightranger5/.vscode/launch.json rename to avnet_sensors_converge/avnet_lightranger5/.vscode/launch.json diff --git a/avnet_lightranger5/.vscode/settings.json b/avnet_sensors_converge/avnet_lightranger5/.vscode/settings.json similarity index 100% rename from avnet_lightranger5/.vscode/settings.json rename to avnet_sensors_converge/avnet_lightranger5/.vscode/settings.json diff --git a/avnet_lightranger5/CMakeLists.txt b/avnet_sensors_converge/avnet_lightranger5/CMakeLists.txt similarity index 100% rename from avnet_lightranger5/CMakeLists.txt rename to avnet_sensors_converge/avnet_lightranger5/CMakeLists.txt diff --git a/avnet_lightranger5/CMakeSettings.json b/avnet_sensors_converge/avnet_lightranger5/CMakeSettings.json similarity index 100% rename from avnet_lightranger5/CMakeSettings.json rename to avnet_sensors_converge/avnet_lightranger5/CMakeSettings.json diff --git a/avnet_lightranger5/README.md b/avnet_sensors_converge/avnet_lightranger5/README.md similarity index 100% rename from avnet_lightranger5/README.md rename to avnet_sensors_converge/avnet_lightranger5/README.md diff --git a/avnet_lightranger5/app_exit_codes.h b/avnet_sensors_converge/avnet_lightranger5/app_exit_codes.h similarity index 100% rename from avnet_lightranger5/app_exit_codes.h rename to avnet_sensors_converge/avnet_lightranger5/app_exit_codes.h diff --git a/avnet_lightranger5/app_manifest.json b/avnet_sensors_converge/avnet_lightranger5/app_manifest.json similarity index 100% rename from avnet_lightranger5/app_manifest.json rename to avnet_sensors_converge/avnet_lightranger5/app_manifest.json diff --git a/avnet_lightranger5/applibs_versions.h b/avnet_sensors_converge/avnet_lightranger5/applibs_versions.h similarity index 100% rename from avnet_lightranger5/applibs_versions.h rename to avnet_sensors_converge/avnet_lightranger5/applibs_versions.h diff --git a/avnet_lightranger5/azsphere_board.txt b/avnet_sensors_converge/avnet_lightranger5/azsphere_board.txt similarity index 100% rename from avnet_lightranger5/azsphere_board.txt rename to avnet_sensors_converge/avnet_lightranger5/azsphere_board.txt diff --git a/avnet_lightranger5/launch.vs.json b/avnet_sensors_converge/avnet_lightranger5/launch.vs.json similarity index 100% rename from avnet_lightranger5/launch.vs.json rename to avnet_sensors_converge/avnet_lightranger5/launch.vs.json diff --git a/avnet_lightranger5/lightranger5_click.h b/avnet_sensors_converge/avnet_lightranger5/lightranger5_click.h similarity index 100% rename from avnet_lightranger5/lightranger5_click.h rename to avnet_sensors_converge/avnet_lightranger5/lightranger5_click.h diff --git a/avnet_lightranger5/main.c b/avnet_sensors_converge/avnet_lightranger5/main.c similarity index 100% rename from avnet_lightranger5/main.c rename to avnet_sensors_converge/avnet_lightranger5/main.c diff --git a/avnet_lightranger5/main.h b/avnet_sensors_converge/avnet_lightranger5/main.h similarity index 100% rename from avnet_lightranger5/main.h rename to avnet_sensors_converge/avnet_lightranger5/main.h From a5d7472fdf91c82a8069f9475b48d70463927abc Mon Sep 17 00:00:00 2001 From: Brian W Date: Tue, 29 Mar 2022 16:48:16 -0700 Subject: [PATCH 02/14] Add submodules --- .gitmodules | 6 ++++++ avnet_sensors_converge/avnet_lightranger5/.gitignore | 1 + avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX | 1 + .../avnet_lightranger5/HardwareDefinitions | 1 + 4 files changed, 9 insertions(+) create mode 100644 avnet_sensors_converge/avnet_lightranger5/.gitignore create mode 160000 avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX create mode 160000 avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions diff --git a/.gitmodules b/.gitmodules index 97ddfa5..edf6f32 100644 --- a/.gitmodules +++ b/.gitmodules @@ -160,3 +160,9 @@ [submodule ".\\avnet_rsl10_2devices\\HardwareDefinitions"] path = .\\avnet_rsl10_2devices\\HardwareDefinitions url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git +[submodule "avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX"] + path = avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX + url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.git +[submodule "avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions"] + path = avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions + url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git diff --git a/avnet_sensors_converge/avnet_lightranger5/.gitignore b/avnet_sensors_converge/avnet_lightranger5/.gitignore new file mode 100644 index 0000000..2a94754 --- /dev/null +++ b/avnet_sensors_converge/avnet_lightranger5/.gitignore @@ -0,0 +1 @@ +out/* \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX b/avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX new file mode 160000 index 0000000..32fb212 --- /dev/null +++ b/avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX @@ -0,0 +1 @@ +Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 diff --git a/avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions b/avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions new file mode 160000 index 0000000..871149b --- /dev/null +++ b/avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions @@ -0,0 +1 @@ +Subproject commit 871149bd855184ac1d42ee6e61def5da18e9dc8f From c6b53165d2373921ab5ebdebf5c5b6af1b6e621d Mon Sep 17 00:00:00 2001 From: Brian W Date: Tue, 29 Mar 2022 16:51:48 -0700 Subject: [PATCH 03/14] HLApp before changes --- .gitmodules | 6 + .../avnet_tempHum13/.gitignore | 1 + .../avnet_tempHum13/.vscode/launch.json | 27 ++ .../avnet_tempHum13/.vscode/settings.json | 15 + .../avnet_tempHum13/AzureSphereDevX | 1 + .../avnet_tempHum13/CMakeLists.txt | 64 ++++ .../avnet_tempHum13/CMakeSettings.json | 47 +++ .../avnet_tempHum13/HardwareDefinitions | 1 + .../avnet_tempHum13/README.md | 17 + .../avnet_tempHum13/app_exit_codes.h | 14 + .../avnet_tempHum13/app_manifest.json | 16 + .../avnet_tempHum13/applibs_versions.h | 25 ++ .../avnet_tempHum13/azsphere_board.txt | 7 + .../avnet_tempHum13/launch.vs.json | 21 ++ .../avnet_tempHum13/lightranger5_click.h | 39 ++ avnet_sensors_converge/avnet_tempHum13/main.c | 342 ++++++++++++++++++ avnet_sensors_converge/avnet_tempHum13/main.h | 161 +++++++++ 17 files changed, 804 insertions(+) create mode 100644 avnet_sensors_converge/avnet_tempHum13/.gitignore create mode 100644 avnet_sensors_converge/avnet_tempHum13/.vscode/launch.json create mode 100644 avnet_sensors_converge/avnet_tempHum13/.vscode/settings.json create mode 160000 avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX create mode 100644 avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt create mode 100644 avnet_sensors_converge/avnet_tempHum13/CMakeSettings.json create mode 160000 avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions create mode 100644 avnet_sensors_converge/avnet_tempHum13/README.md create mode 100644 avnet_sensors_converge/avnet_tempHum13/app_exit_codes.h create mode 100644 avnet_sensors_converge/avnet_tempHum13/app_manifest.json create mode 100644 avnet_sensors_converge/avnet_tempHum13/applibs_versions.h create mode 100644 avnet_sensors_converge/avnet_tempHum13/azsphere_board.txt create mode 100644 avnet_sensors_converge/avnet_tempHum13/launch.vs.json create mode 100644 avnet_sensors_converge/avnet_tempHum13/lightranger5_click.h create mode 100644 avnet_sensors_converge/avnet_tempHum13/main.c create mode 100644 avnet_sensors_converge/avnet_tempHum13/main.h diff --git a/.gitmodules b/.gitmodules index edf6f32..688c5ea 100644 --- a/.gitmodules +++ b/.gitmodules @@ -166,3 +166,9 @@ [submodule "avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions"] path = avnet_sensors_converge/avnet_lightranger5/HardwareDefinitions url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git +[submodule "avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX"] + path = avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX + url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.git +[submodule "avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions"] + path = avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions + url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git diff --git a/avnet_sensors_converge/avnet_tempHum13/.gitignore b/avnet_sensors_converge/avnet_tempHum13/.gitignore new file mode 100644 index 0000000..2a94754 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/.gitignore @@ -0,0 +1 @@ +out/* \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/.vscode/launch.json b/avnet_sensors_converge/avnet_tempHum13/.vscode/launch.json new file mode 100644 index 0000000..fcace73 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/.vscode/launch.json @@ -0,0 +1,27 @@ +{ + // Use IntelliSense to learn about possible attributes. + // Hover to view descriptions of existing attributes. + // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 + "version": "0.2.0", + "configurations": [ + { + "name": "Launch for Azure Sphere High-Level Applications (gdb)", + "type": "azurespheredbg", + "request": "launch", + "args": [], + "stopAtEntry": false, + "cwd": "${workspaceFolder}", + "environment": [], + "externalConsole": true, + "partnerComponents": [ "f6768b9a-e086-4f5a-8219-5ffe9684b001" ], + "MIMode": "gdb", + "setupCommands": [ + { + "description": "Enable pretty-printing for gdb", + "text": "-enable-pretty-printing", + "ignoreFailures": true + } + ] + } + ] +} \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/.vscode/settings.json b/avnet_sensors_converge/avnet_tempHum13/.vscode/settings.json new file mode 100644 index 0000000..94d6c8e --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/.vscode/settings.json @@ -0,0 +1,15 @@ +{ + "cmake.generator": "Ninja", + "cmake.buildDirectory": "${workspaceRoot}/out/ARM-${buildType}", + "cmake.buildToolArgs": [ "-v" ], + "cmake.configureSettings": { + "CMAKE_TOOLCHAIN_FILE": "${command:azuresphere.AzureSphereSdkDir}/CMakeFiles/AzureSphereToolchain.cmake", + "AZURE_SPHERE_TARGET_API_SET": "latest-lts" + }, + "cmake.configureOnOpen": true, + "C_Cpp.default.configurationProvider": "ms-vscode.cmake-tools", + "files.associations": { + "dx_avnet_iot_connect.h": "c", + "dx_json_serializer.h": "c" + } +} \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX b/avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX new file mode 160000 index 0000000..32fb212 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX @@ -0,0 +1 @@ +Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 diff --git a/avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt b/avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt new file mode 100644 index 0000000..9659192 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt @@ -0,0 +1,64 @@ +# Copyright (c) Microsoft Corporation. All rights reserved. +# Licensed under the MIT License. + +cmake_minimum_required (VERSION 3.10) + +project (avnet_lightranger5_TMF8801_HLApp-V1 C) + +# Check if there is a global azsphere_board.cmake file +get_filename_component(PARENT_DIR ${PROJECT_SOURCE_DIR} DIRECTORY) + +if (EXISTS "${PARENT_DIR}/azsphere_board.global.txt") + include("${PARENT_DIR}/azsphere_board.global.txt") +else() + include(azsphere_board.txt) +endif() + +if (EXISTS "${PARENT_DIR}/tools/cmake/azsphere_config.cmake") + include(../tools/cmake/azsphere_config.cmake) + auto_generate_azsphere_config() +else() + + # For information on setting tools revision and target api set see + # https://docs.microsoft.com/en-us/azure-sphere/app-development/using-cmake-functions + + azsphere_configure_tools(TOOLS_REVISION "21.07") + azsphere_configure_api(TARGET_API_SET "12") + +endif() + +add_subdirectory("AzureSphereDevX" out) + +# Create executable +add_executable (${PROJECT_NAME} main.c) +target_link_libraries (${PROJECT_NAME} applibs pthread gcc_s c azure_sphere_devx) +target_include_directories(${PROJECT_NAME} PUBLIC AzureSphereDevX/include ) + + +set(BOARD_COUNTER 0) + +if(AVNET) + MATH(EXPR BOARD_COUNTER "${BOARD_COUNTER}+1") + add_definitions( -DOEM_AVNET=TRUE ) + azsphere_target_hardware_definition(${PROJECT_NAME} TARGET_DIRECTORY "HardwareDefinitions/avnet_mt3620_sk" TARGET_DEFINITION "sample_appliance.json") + message(STATUS "Azure Sphere board selected: AVNET REV 1") +endif(AVNET) + +if(AVNET_REV_2) + MATH(EXPR BOARD_COUNTER "${BOARD_COUNTER}+1") + add_definitions( -DOEM_AVNET=TRUE ) + azsphere_target_hardware_definition(${PROJECT_NAME} TARGET_DIRECTORY "HardwareDefinitions/avnet_mt3620_sk_rev2" TARGET_DEFINITION "sample_appliance.json") + message(STATUS "Azure Sphere board selected: AVNET REV 2") +endif(AVNET_REV_2) + + +if(BOARD_COUNTER EQUAL 0) + message(FATAL_ERROR "No Azure Sphere boards selected. Ensure one board set") +endif() + +if(BOARD_COUNTER GREATER 1) + message(FATAL_ERROR "Multiple (${BOARD_COUNTER}) Azure Sphere boards selected. Ensure only one board set") +endif() + + +azsphere_target_add_image_package(${PROJECT_NAME}) \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/CMakeSettings.json b/avnet_sensors_converge/avnet_tempHum13/CMakeSettings.json new file mode 100644 index 0000000..004e70d --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/CMakeSettings.json @@ -0,0 +1,47 @@ +{ + "environments": [ + { + "environment": "AzureSphere" + } + ], + "configurations": [ + { + "name": "ARM-Debug", + "generator": "Ninja", + "configurationType": "Debug", + "inheritEnvironments": [ + "AzureSphere" + ], + "buildRoot": "${projectDir}\\out\\${name}", + "installRoot": "${projectDir}\\out\\${name}", + "cmakeToolchain": "${env.AzureSphereDefaultSDKDir}CMakeFiles\\AzureSphereToolchain.cmake", + "buildCommandArgs": "-v", + "ctestCommandArgs": "", + "variables": [ + { + "name": "AZURE_SPHERE_TARGET_API_SET", + "value": "latest-lts" + } + ] + }, + { + "name": "ARM-Release", + "generator": "Ninja", + "configurationType": "Release", + "inheritEnvironments": [ + "AzureSphere" + ], + "buildRoot": "${projectDir}\\out\\${name}", + "installRoot": "${projectDir}\\out\\${name}", + "cmakeToolchain": "${env.AzureSphereDefaultSDKDir}CMakeFiles\\AzureSphereToolchain.cmake", + "buildCommandArgs": "-v", + "ctestCommandArgs": "", + "variables": [ + { + "name": "AZURE_SPHERE_TARGET_API_SET", + "value": "latest-lts" + } + ] + } + ] +} diff --git a/avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions b/avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions new file mode 160000 index 0000000..871149b --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions @@ -0,0 +1 @@ +Subproject commit 871149bd855184ac1d42ee6e61def5da18e9dc8f diff --git a/avnet_sensors_converge/avnet_tempHum13/README.md b/avnet_sensors_converge/avnet_tempHum13/README.md new file mode 100644 index 0000000..c95b1c3 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/README.md @@ -0,0 +1,17 @@ +# Azure IoT Starter Project (empty) + +This is an empty (starter) project that can be used for new Azure Sphere applications based on the DevX library. The project connects to an Azure IoTHub, +IoTCentral, or Avnet's IoTConnect and nothing more. Use the other examples in this folder to help you see how to build out the project to meet your requirements. Search the project for "TODO" to see where to add definitions, declarations and code. +## Config app_manifest.json sample + +1. Set ID Scope +1. Set Allowed connections +1. Set DeviceAuthentication + +For more information refer to: + +1. [Adding the Azure Sphere DevX library](https://github.com/gloveboxes/AzureSphereDevX/wiki/Adding-the-DevX-Library) +1. [Azure Messaging](https://github.com/gloveboxes/AzureSphereDevX/wiki/IoT-Hub-Sending-messages) +1. [Device Twins](https://github.com/gloveboxes/AzureSphereDevX/wiki/IoT-Hub-Device-Twins) +1. [Direct Methods](https://github.com/gloveboxes/AzureSphereDevX/wiki/IoT-Hub-Direct-Methods) +1. [GPIO](https://github.com/gloveboxes/AzureSphereDevX/wiki/Working-with-GPIO) diff --git a/avnet_sensors_converge/avnet_tempHum13/app_exit_codes.h b/avnet_sensors_converge/avnet_tempHum13/app_exit_codes.h new file mode 100644 index 0000000..f9b6a1c --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/app_exit_codes.h @@ -0,0 +1,14 @@ +#pragma once + +/* Copyright (c) Microsoft Corporation. All rights reserved. + Licensed under the MIT License. */ + +/// +/// Exit codes for this application. Application exit codes +/// must be between 1 and 149, where 0 is reserved for successful +// termination. dx_exit_codes.h owns/defines exit codes 0 and +/// 150 - 254. +/// +typedef enum { + APP_ExitCode_Telemetry_Buffer_Too_Small = 1 +} App_Exit_Code; \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/app_manifest.json b/avnet_sensors_converge/avnet_tempHum13/app_manifest.json new file mode 100644 index 0000000..c119d6b --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/app_manifest.json @@ -0,0 +1,16 @@ +{ + "SchemaVersion": 1, + "Name": "avnet_lightranger5_TMF8801_HLApp-V1", + "ComponentId": "b8f5931e-173a-40f5-a4f8-3d98240f53ec", + "EntryPoint": "/bin/app", + "CmdArgs": [ "--ScopeID", "0ne00000000" ], + "Capabilities": { + "Gpio": [], + "Pwm": [ "$SAMPLE_LED_PWM_CONTROLLER" ], + "AllowedConnections": [ "global.azure-devices-provisioning.net", + "YOUR_IOT_HUB-HOSTNAME.azure-devices.net"], + "DeviceAuthentication": "00000000-0000-0000-0000-000000000000", + "AllowedApplicationConnections": [ "f6768b9a-e086-4f5a-8219-5ffe9684b001" ] + }, + "ApplicationType": "Default" +} diff --git a/avnet_sensors_converge/avnet_tempHum13/applibs_versions.h b/avnet_sensors_converge/avnet_tempHum13/applibs_versions.h new file mode 100644 index 0000000..22f5880 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/applibs_versions.h @@ -0,0 +1,25 @@ +#pragma once + +/// +/// This identifier should be defined before including any of the networking-related header files. +/// It indicates which version of the Wi-Fi data structures the application uses. +/// +#define NETWORKING_STRUCTS_VERSION 1 + +/// +/// This identifier must be defined before including any of the Wi-Fi related header files. +/// It indicates which version of the Wi-Fi data structures the application uses. +/// +#define WIFICONFIG_STRUCTS_VERSION 1 + +/// +/// This identifier must be defined before including any of the UART-related header files. +/// It indicates which version of the UART data structures the application uses. +/// +#define UART_STRUCTS_VERSION 1 + +/// +/// This identifier must be defined before including any of the SPI-related header files. +/// It indicates which version of the SPI data structures the application uses. +/// +#define SPI_STRUCTS_VERSION 1 \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/azsphere_board.txt b/avnet_sensors_converge/avnet_tempHum13/azsphere_board.txt new file mode 100644 index 0000000..011bb0e --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/azsphere_board.txt @@ -0,0 +1,7 @@ +# Select your developer board by removing the # tag from the beginning of the line +# If you are NOT using the AVNET Revision 1 board be sure to comment out the AVNET board + +# set(AVNET TRUE "AVNET Azure Sphere Starter Kit Revision 1") +set(AVNET_REV_2 TRUE "AVNET Azure Sphere Starter Kit Revision 2") +# set(SEEED_STUDIO_RDB TRUE "Seeed Studio Azure Sphere MT3620 Development Kit (aka Reference Design Board or RDB)") +# set(SEEED_STUDIO_MINI TRUE "Seeed Studio Azure Sphere MT3620 Mini Dev Board") \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/launch.vs.json b/avnet_sensors_converge/avnet_tempHum13/launch.vs.json new file mode 100644 index 0000000..09ab6f1 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/launch.vs.json @@ -0,0 +1,21 @@ +{ + "version": "0.2.1", + "defaults": {}, + "configurations": [ + { + "type": "azurespheredbg", + "name": "GDB Debugger (HLCore)", + "project": "CMakeLists.txt", + "inheritEnvironments": [ + "AzureSphere" + ], + "customLauncher": "AzureSphereLaunchOptions", + "workingDirectory": "${workspaceRoot}", + "applicationPath": "${debugInfo.target}", + "imagePath": "${debugInfo.targetImage}", + "targetCore": "HLCore", + "targetApiSet": "${env.AzureSphereTargetApiSet}", + "partnerComponents": [ "f6768b9a-e086-4f5a-8219-5ffe9684b001" ] + } + ] +} diff --git a/avnet_sensors_converge/avnet_tempHum13/lightranger5_click.h b/avnet_sensors_converge/avnet_tempHum13/lightranger5_click.h new file mode 100644 index 0000000..03748d1 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/lightranger5_click.h @@ -0,0 +1,39 @@ +#pragma once + +/* Copyright (c) Avnet Incorporated. All rights reserved. + Licensed under the MIT License. */ + +#define JSON_STRING_MAX_SIZE 100 + +// Define the different messages IDs we can send to real time applications +// If this enum is changed, it also needs to be changed for the high level application +typedef enum +{ + IC_LIGHTRANGER5_CLICK_UNKNOWN, + IC_LIGHTRANGER5_CLICK_HEARTBEAT, + IC_LIGHTRANGER5_CLICK_READ_SENSOR_RESPOND_WITH_TELEMETRY, + IC_LIGHTRANGER5_CLICK_SET_AUTO_TELEMETRY_RATE, + IC_LIGHTRANGER5_CLICK_READ_SENSOR +} INTER_CORE_CMD_LIGHTRANGER5_CLICK; +typedef uint8_t cmdType; + +// Define the expected data structure. +typedef struct __attribute__((packed)) +{ + uint8_t cmd; + uint32_t telemtrySendRate; + //////////////////////////////////////////////////////////////////////////////////////// + // Don't change the declarations above or the generic RTApp implementation will break // + //////////////////////////////////////////////////////////////////////////////////////// +} IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT; + +typedef struct __attribute__((packed)) +{ + uint8_t cmd; + uint32_t telemtrySendRate; + char telemetryJSON[JSON_STRING_MAX_SIZE]; + //////////////////////////////////////////////////////////////////////////////////////// + // Don't change the declarations above or the generic RTApp implementation will break // + //////////////////////////////////////////////////////////////////////////////////////// + int range_mm; +} IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL; diff --git a/avnet_sensors_converge/avnet_tempHum13/main.c b/avnet_sensors_converge/avnet_tempHum13/main.c new file mode 100644 index 0000000..ab2da75 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/main.c @@ -0,0 +1,342 @@ +/* Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. + * + * This example is built on the Azure Sphere DevX library. + * 1. DevX is an Open Source community-maintained implementation of the Azure Sphere SDK samples. + * 2. DevX is a modular library that simplifies common development scenarios. + * - You can focus on your solution, not the plumbing. + * 3. DevX documentation is maintained at https://github.com/gloveboxes/AzureSphereDevX/wiki + * 4. The DevX library is not a substitute for understanding the Azure Sphere SDK Samples. + * - https://github.com/Azure/azure-sphere-samples + * + * DEVELOPER BOARD SELECTION + * + * The following developer boards are supported. + * + * 1. AVNET Azure Sphere Starter Kit. + * 2. AVNET Azure Sphere Starter Kit Revision 2. + * 3. Seeed Studio Azure Sphere MT3620 Development Kit aka Reference Design Board or rdb. + * 4. Seeed Studio Seeed Studio MT3620 Mini Dev Board. + * + * ENABLE YOUR DEVELOPER BOARD + * + * Each Azure Sphere developer board manufacturer maps pins differently. You need to select the + * configuration that matches your board. + * + * Follow these steps: + * + * 1. Open CMakeLists.txt. + * 2. Uncomment the set command that matches your developer board. + * 3. Click File, then Save to auto-generate the CMake Cache. + * + * How to use this sample + * + * Developers can use this sample as a starting point for their DevX based Azure Sphere + * application. It will connect to an Azure IoTHub, IOTCentral or Avnet's IoTConnect. + * + * There are sections marked with "TODO" that the developer can review for hints on where + * to add code, or to enable code that may be needed for general support, such as sending + * telemetry. + * + ************************************************************************************************/ +#include "main.h" + +static int closeRange = DEFAULT_CLOSE_RANGE; +static int mediumRange = DEFAULT_MEDIUM_RANGE; +static int farRange = DEFAULT_FAR_RANGE; + +static int lastRangeMeasurement = -1; + +/**************************************************************************************** + * Implementation + ****************************************************************************************/ +//static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms); + +static DX_DEVICE_TWIN_HANDLER(dt_red_led_set_limit, deviceTwinBinding) +{ + // validate data is sensible range before applying. + if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && + *(int *)deviceTwinBinding->propertyValue >= MIN_CLOSE_RANGE && + *(int *)deviceTwinBinding->propertyValue < mediumRange) { + + closeRange = *(int *)deviceTwinBinding->propertyValue; + + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_COMPLETED); + + } else { + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_ERROR); + } +} +DX_DEVICE_TWIN_HANDLER_END + +static DX_DEVICE_TWIN_HANDLER(dt_blue_led_set_limit, deviceTwinBinding) +{ + // validate data is sensible range before applying + if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && + *(int *)deviceTwinBinding->propertyValue >=closeRange && + *(int *)deviceTwinBinding->propertyValue < farRange) { + + mediumRange = *(int *)deviceTwinBinding->propertyValue; + + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_COMPLETED); + + } else { + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_ERROR); + } +} +DX_DEVICE_TWIN_HANDLER_END + +static DX_DEVICE_TWIN_HANDLER(dt_green_led_set_limit, deviceTwinBinding) +{ + // validate data is sensible range before applying + if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && + *(int *)deviceTwinBinding->propertyValue > mediumRange && + *(int *)deviceTwinBinding->propertyValue < FAR_RANGE_MAX) { + + farRange = *(int *)deviceTwinBinding->propertyValue; + + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_COMPLETED); + + } else { + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_ERROR); + } +} +DX_DEVICE_TWIN_HANDLER_END + +static DX_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms, deviceTwinBinding) +{ + + // validate data is sensible range before applying. + if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && + *(int *)deviceTwinBinding->propertyValue >= MIN_POLL_TIME_MS && + *(int *)deviceTwinBinding->propertyValue <= MAX_POLL_TIME_MS) { + + // Break the ms value int seconds and ms for the timespec struct + int seconds = (int)(*(int *)deviceTwinBinding->propertyValue/1000); + int ms = (long)(*(int *)deviceTwinBinding->propertyValue) - (seconds * 1000); + + dx_timerChange(&readSensorTimer, &(struct timespec){seconds, ms * ONE_MS}); + + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_COMPLETED); + + } else { + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_ERROR); + } +} +DX_DEVICE_TWIN_HANDLER_END + +static DX_DEVICE_TWIN_HANDLER(dt_set_telemetemetry_period_seconds, deviceTwinBinding) +{ + + // validate data is sensible range before applying. + if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && + *(int *)deviceTwinBinding->propertyValue >= MIN_TELEMETRY_TX_PERIOD && + *(int *)deviceTwinBinding->propertyValue <= MAX_TELEMETRY_TX_PERIOD) { + + dx_timerChange(&sendTelemetryTimer, &(struct timespec){ *(int *)deviceTwinBinding->propertyValue, 0}); + + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_COMPLETED); + + } else { + dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, + DX_DEVICE_TWIN_RESPONSE_ERROR); + } +} +DX_DEVICE_TWIN_HANDLER_END + + +// Using the rangeStatus value, turn on/off the range indication LEDs +static void setPwmStatusLed(RGB_Status rangeStatus, int range) +{ + static RGB_Status lastRangeStatus = RGB_INVALID; + static int lastRange = -1; + uint32_t dutyCycle = 100; + + // Nothing to see here folks, move along . . . + if((lastRangeStatus == rangeStatus) && (lastRange == range)){ + return; + } + + // Update the local static variables + lastRangeStatus = rangeStatus; + lastRange = range; + + // Turn off all the LED's then set the LED corresponding to the range status + // Turn off RGBLED - 100% duty cycle is off + dx_pwmSetDutyCycle(&pwm_red_led, 1000, 100); + dx_pwmSetDutyCycle(&pwm_green_led, 1000, 100); + dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 100); + + switch (rangeStatus) + { + case RGB_OUT_OF_RANGE: + break; // Leave the LEDs off + case RGB_CLOSE: // Red LED + dutyCycle = (uint32_t)((float)(range-0)/(float)(closeRange-0)*100); + dx_pwmSetDutyCycle(&pwm_red_led, 1000, dutyCycle); + break; + case RGB_MEDIUM: // Blue LED + dutyCycle = (uint32_t)(((float)(range-closeRange)/(float)(mediumRange - closeRange))*100); + dx_pwmSetDutyCycle(&pwm_blue_led, 1000, dutyCycle); + break; + case RGB_FAR: // Green LED + dutyCycle = (uint32_t)(((float)(range-mediumRange)/(float)(farRange - mediumRange))*100); + dx_pwmSetDutyCycle(&pwm_green_led, 1000, dutyCycle); + break; + case RGB_INVALID: + default: + break; + } +} + +/// +/// receive_msg_handler() +/// This handler is called when the high level application receives a raw data read response from the +/// Thermo CLICK real time application. +/// +static void receive_msg_handler(void *data_block, ssize_t message_length) +{ + + // Cast the data block so we can index into the data + IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL *messageData = (IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL*) data_block; + + switch (messageData->cmd) { + case IC_LIGHTRANGER5_CLICK_READ_SENSOR: + + if(messageData->range_mm == -1){ + setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->range_mm); + } + else{ + if(messageData->range_mm <= closeRange){ + setPwmStatusLed(RGB_CLOSE, messageData->range_mm); + } + else if (messageData->range_mm <= mediumRange){ + setPwmStatusLed(RGB_MEDIUM, messageData->range_mm); + } + else if (messageData->range_mm <= farRange){ + setPwmStatusLed(RGB_FAR, messageData->range_mm); + } + else{ + setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->range_mm); + } + } + + // Capture the last measurement in the global variable + lastRangeMeasurement = messageData->range_mm; + + break; + // Handle the other cases by doing nothing + case IC_LIGHTRANGER5_CLICK_HEARTBEAT: + case IC_LIGHTRANGER5_CLICK_READ_SENSOR_RESPOND_WITH_TELEMETRY: + case IC_LIGHTRANGER5_CLICK_SET_AUTO_TELEMETRY_RATE: + case IC_LIGHTRANGER5_CLICK_UNKNOWN: + default: + break; + } +} + +/// +/// Periodic timer to read the TMF8801 sensor +/// +static DX_TIMER_HANDLER(ReadSensorHandler) +{ + //Code to read the sensor data in your application + // reset inter-core block + memset(&ic_tx_block, 0x00, sizeof(IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT)); + + // Send read sensor message to realtime core app one + ic_tx_block.cmd = IC_LIGHTRANGER5_CLICK_READ_SENSOR; + dx_intercorePublish(&intercore_lightranger5_click_binding, &ic_tx_block, + sizeof(IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT)); +} +DX_TIMER_HANDLER_END + +/// +/// Periodic timer to read the TMF8801 sensor +/// +static DX_TIMER_HANDLER(SendTelemetryHandler) +{ + + snprintf(msgBuffer, sizeof(msgBuffer), "{\"rangeData\":%d}", lastRangeMeasurement); + Log_Debug("%s\n", msgBuffer); + + if(dx_isAzureConnected()){ + dx_azurePublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + } +} +DX_TIMER_HANDLER_END + +/// +/// Initialize peripherals, device twins, direct methods, timer_bindings. +/// +static void InitPeripheralsAndHandlers(void) +{ +#ifdef USE_AVNET_IOTCONNECT + dx_avnetConnect(&dx_config, NETWORK_INTERFACE); +#else + // TODO, to connect this application to Azure, remove the comment + // specifier below and update the app_manifest.json file with the details + // for your Azure resources and Azure Sphere tenant. + //dx_azureConnect(&dx_config, NETWORK_INTERFACE, IOT_PLUG_AND_PLAY_MODEL_ID); +#endif + + dx_gpioSetOpen(gpio_bindings, NELEMS(gpio_bindings)); + dx_timerSetStart(timer_bindings, NELEMS(timer_bindings)); + dx_deviceTwinSubscribe(device_twin_bindings, NELEMS(device_twin_bindings)); + dx_directMethodSubscribe(direct_method_bindings, NELEMS(direct_method_bindings)); + dx_intercoreConnect(&intercore_lightranger5_click_binding); + dx_pwmSetOpen(pwm_bindings, NELEMS(pwm_bindings)); + + // Turn off RGBLED - 100% duty cycle is off + dx_pwmSetDutyCycle(&pwm_red_led, 1000, 100); + dx_pwmSetDutyCycle(&pwm_green_led, 1000, 100); + dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 100); + + Log_Debug("Lightranger5 Demo Starting . . . \n"); +} + +/// +/// Close peripherals and handlers. +/// +static void ClosePeripheralsAndHandlers(void) +{ + dx_timerSetStop(timer_bindings, NELEMS(timer_bindings)); + dx_pwmSetClose(pwm_bindings, NELEMS(pwm_bindings)); + dx_deviceTwinUnsubscribe(); + dx_directMethodUnsubscribe(); + dx_gpioSetClose(gpio_bindings, NELEMS(gpio_bindings)); + dx_timerEventLoopStop(); +} + +int main(int argc, char *argv[]) +{ + dx_registerTerminationHandler(); + + if (!dx_configParseCmdLineArguments(argc, argv, &dx_config)) { + return dx_getTerminationExitCode(); + } + + InitPeripheralsAndHandlers(); + + // Main loop + while (!dx_isTerminationRequired()) { + int result = EventLoop_Run(dx_timerGetEventLoop(), -1, true); + // Continue if interrupted by signal, e.g. due to breakpoint being set. + if (result == -1 && errno != EINTR) { + dx_terminate(DX_ExitCode_Main_EventLoopFail); + } + } + + ClosePeripheralsAndHandlers(); + Log_Debug("Application exiting.\n"); + return dx_getTerminationExitCode(); +} \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/main.h b/avnet_sensors_converge/avnet_tempHum13/main.h new file mode 100644 index 0000000..2c375f4 --- /dev/null +++ b/avnet_sensors_converge/avnet_tempHum13/main.h @@ -0,0 +1,161 @@ + +#include "hw/sample_appliance.h" // Hardware definition +#include "app_exit_codes.h" +#include "dx_azure_iot.h" +#include "dx_config.h" +#include "dx_json_serializer.h" +#include "dx_terminate.h" +#include "dx_timer.h" +#include "dx_utilities.h" +#include "dx_direct_methods.h" +#include "dx_version.h" +#include "dx_config.h" +#include "dx_gpio.h" +#include "dx_pwm.h" +#include +#include +#include "dx_intercore.h" +#include "lightranger5_click.h" +#include "dx_uart.h" + +// Use main.h to define all your application definitions, message properties/contentProperties, +// bindings and binding sets. + +// https://docs.microsoft.com/en-us/azure/iot-pnp/overview-iot-plug-and-play +#define IOT_PLUG_AND_PLAY_MODEL_ID "dtmi:amsTmf8801Workshop:SphereTMF8801_5eg;1" + +// Details on how to connect your application using an ethernet adaptor +// https://docs.microsoft.com/en-us/azure-sphere/network/connect-ethernet +#define NETWORK_INTERFACE "wlan0" + +#define SAMPLE_VERSION_NUMBER "1.0" +#define ONE_MS 1000000 +#define ONE_HUNDRED_MS 100000000 + +#define DEFAULT_SENSOR_POLL_PERIOD_SECONDS 0 +#define DEFAULT_SENSOR_POLL_PERIOD_MS (ONE_MS * 50) + +#define DEFAULT_SEND_TELEMETRY_PERIOD_SECONDS 5 + +#define MIN_POLL_TIME_MS 20 +#define MAX_POLL_TIME_MS 60*1000 // 1 Minute + +#define MIN_TELEMETRY_TX_PERIOD 1 +#define MAX_TELEMETRY_TX_PERIOD (60*60) // 1 Hour + +#define DEFAULT_CLOSE_RANGE 100 +#define DEFAULT_MEDIUM_RANGE 200 +#define DEFAULT_FAR_RANGE 300 + +#define MIN_CLOSE_RANGE 30 +#define FAR_RANGE_MAX 500 + +DX_USER_CONFIG dx_config; + +/**************************************************************************************** + * Avnet IoTConnect Support + ****************************************************************************************/ +// TODO: If the application will connect to Avnet's IoTConnect platform enable the +// #define below +//#define USE_AVNET_IOTCONNECT + +/**************************************************************************************** + * Application defines + ****************************************************************************************/ +typedef enum { + RGB_INVALID = 0, + RGB_OUT_OF_RANGE, + RGB_CLOSE, + RGB_MEDIUM, + RGB_FAR +} RGB_Status; + +/**************************************************************************************** + * Forward declarations + ****************************************************************************************/ +static void receive_msg_handler(void *data_block, ssize_t message_length); +static DX_DECLARE_TIMER_HANDLER(ReadSensorHandler); +static DX_DECLARE_TIMER_HANDLER(SendTelemetryHandler); +static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_red_led_set_limit); +static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_blue_led_set_limit); +static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_green_led_set_limit); +static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms); +static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_telemetemetry_period_seconds); + +IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT ic_tx_block; +IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL ic_rx_block; + +/**************************************************************************************** + * Telemetry message buffer property sets + ****************************************************************************************/ + +// Number of bytes to allocate for the JSON telemetry message for IoT Hub/Central +#define JSON_MESSAGE_BYTES 32 +static char msgBuffer[JSON_MESSAGE_BYTES] = {0}; + +static DX_MESSAGE_PROPERTY *messageProperties[] = {&(DX_MESSAGE_PROPERTY){.key = "appid", .value = "TMF8801"}, + &(DX_MESSAGE_PROPERTY){.key = "type", .value = "telemetry"}, + &(DX_MESSAGE_PROPERTY){.key = "schema", .value = "1"}}; + +static DX_MESSAGE_CONTENT_PROPERTIES contentProperties = {.contentEncoding = "utf-8", .contentType = "application/json"}; + +/**************************************************************************************** + * Bindings + ****************************************************************************************/ +DX_INTERCORE_BINDING intercore_lightranger5_click_binding = { + .sockFd = -1, + .nonblocking_io = true, + .rtAppComponentId = "f6768b9a-e086-4f5a-8219-5ffe9684b001", + .interCoreCallback = receive_msg_handler, + .intercore_recv_block = &ic_rx_block, + .intercore_recv_block_length = sizeof(IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL)}; + +static DX_TIMER_BINDING readSensorTimer = { + .repeat = &(struct timespec){DEFAULT_SENSOR_POLL_PERIOD_SECONDS, DEFAULT_SENSOR_POLL_PERIOD_MS}, + .name = "readSensorTimer", .handler = ReadSensorHandler}; + +static DX_TIMER_BINDING sendTelemetryTimer = { + .repeat = &(struct timespec){DEFAULT_SEND_TELEMETRY_PERIOD_SECONDS, 0}, + .name = "sendTelemetryTimer", .handler = SendTelemetryHandler}; + +static DX_PWM_CONTROLLER pwm_led_controller = {.controllerId = SAMPLE_LED_PWM_CONTROLLER, + .name = "PWM Click Controller"}; + +static DX_PWM_BINDING pwm_red_led = { + .pwmController = &pwm_led_controller, .channelId = 0, .name = "red_led"}; +static DX_PWM_BINDING pwm_green_led = { + .pwmController = &pwm_led_controller, .channelId = 1, .name = "green led"}; +static DX_PWM_BINDING pwm_blue_led = { + .pwmController = &pwm_led_controller, .channelId = 2, .name = "blue led"}; + +static DX_DEVICE_TWIN_BINDING dt_red_limit = {.propertyName = "redLimit_mm", + .twinType = DX_DEVICE_TWIN_INT, + .handler = dt_red_led_set_limit}; + +static DX_DEVICE_TWIN_BINDING dt_green_limit = {.propertyName = "greenLimit_mm", + .twinType = DX_DEVICE_TWIN_INT, + .handler = dt_green_led_set_limit}; + +static DX_DEVICE_TWIN_BINDING dt_blue_limit = {.propertyName = "blueLimit_mm", + .twinType = DX_DEVICE_TWIN_INT, + .handler = dt_blue_led_set_limit}; + +static DX_DEVICE_TWIN_BINDING dt_desired_sample_rate_ms = {.propertyName = "sensorPollPeriod_ms", + .twinType = DX_DEVICE_TWIN_INT, + .handler = dt_set_sensor_polling_period_ms}; + +static DX_DEVICE_TWIN_BINDING dt_telemetry_tx_period_s = {.propertyName = "setTelemetrySendPeriod_seconds", + .twinType = DX_DEVICE_TWIN_INT, + .handler = dt_set_telemetemetry_period_seconds}; + + +/**************************************************************************************** + * Binding sets + ****************************************************************************************/ +DX_DEVICE_TWIN_BINDING *device_twin_bindings[] = {&dt_red_limit, &dt_green_limit, &dt_blue_limit, + &dt_desired_sample_rate_ms, + &dt_telemetry_tx_period_s}; +DX_DIRECT_METHOD_BINDING *direct_method_bindings[] = {}; +DX_GPIO_BINDING *gpio_bindings[] = {}; +DX_TIMER_BINDING *timer_bindings[] = {&readSensorTimer, &sendTelemetryTimer}; +static DX_PWM_BINDING *pwm_bindings[] = {&pwm_red_led, &pwm_green_led, &pwm_blue_led}; From ef561853e75d595579b8af29d33189ebfb4a17b8 Mon Sep 17 00:00:00 2001 From: Brian W Date: Thu, 31 Mar 2022 07:21:34 -0700 Subject: [PATCH 04/14] HTU21D App running and reading sensor data --- .../avnet_tempHum13/CMakeLists.txt | 2 +- .../{lightranger5_click.h => htu21d_rtapp.h} | 38 +++---- avnet_sensors_converge/avnet_tempHum13/main.c | 98 +++++++++---------- avnet_sensors_converge/avnet_tempHum13/main.h | 27 +++-- 4 files changed, 82 insertions(+), 83 deletions(-) rename avnet_sensors_converge/avnet_tempHum13/{lightranger5_click.h => htu21d_rtapp.h} (59%) diff --git a/avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt b/avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt index 9659192..2e9e76b 100644 --- a/avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt +++ b/avnet_sensors_converge/avnet_tempHum13/CMakeLists.txt @@ -3,7 +3,7 @@ cmake_minimum_required (VERSION 3.10) -project (avnet_lightranger5_TMF8801_HLApp-V1 C) +project (avnet_TEMPHUM_TMF8801_HLApp-V1 C) # Check if there is a global azsphere_board.cmake file get_filename_component(PARENT_DIR ${PROJECT_SOURCE_DIR} DIRECTORY) diff --git a/avnet_sensors_converge/avnet_tempHum13/lightranger5_click.h b/avnet_sensors_converge/avnet_tempHum13/htu21d_rtapp.h similarity index 59% rename from avnet_sensors_converge/avnet_tempHum13/lightranger5_click.h rename to avnet_sensors_converge/avnet_tempHum13/htu21d_rtapp.h index 03748d1..3412d00 100644 --- a/avnet_sensors_converge/avnet_tempHum13/lightranger5_click.h +++ b/avnet_sensors_converge/avnet_tempHum13/htu21d_rtapp.h @@ -1,39 +1,43 @@ -#pragma once - /* Copyright (c) Avnet Incorporated. All rights reserved. Licensed under the MIT License. */ - + +#pragma once + #define JSON_STRING_MAX_SIZE 100 // Define the different messages IDs we can send to real time applications // If this enum is changed, it also needs to be changed for the high level application -typedef enum +typedef enum __attribute__((packed)) { - IC_LIGHTRANGER5_CLICK_UNKNOWN, - IC_LIGHTRANGER5_CLICK_HEARTBEAT, - IC_LIGHTRANGER5_CLICK_READ_SENSOR_RESPOND_WITH_TELEMETRY, - IC_LIGHTRANGER5_CLICK_SET_AUTO_TELEMETRY_RATE, - IC_LIGHTRANGER5_CLICK_READ_SENSOR -} INTER_CORE_CMD_LIGHTRANGER5_CLICK; -typedef uint8_t cmdType; + IC_TEMPHUM_UNKNOWN, + IC_TEMPHUM_HEARTBEAT, + IC_TEMPHUM_READ_SENSOR_RESPOND_WITH_TELEMETRY, + IC_TEMPHUM_SET_TELEMETRY_SEND_RATE, + ///////////////////////////////////////////////////////////////////////////////// + // Don't change the enums above or the generic RTApp implementation will break // + ///////////////////////////////////////////////////////////////////////////////// + IC_TEMPHUM_READ_SENSOR + +} INTER_CORE_CMD_TEMPHUM; // Define the expected data structure. typedef struct __attribute__((packed)) { - uint8_t cmd; + INTER_CORE_CMD_TEMPHUM cmd; uint32_t telemtrySendRate; //////////////////////////////////////////////////////////////////////////////////////// // Don't change the declarations above or the generic RTApp implementation will break // //////////////////////////////////////////////////////////////////////////////////////// -} IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT; +} IC_COMMAND_BLOCK_TEMPHUM_HL_TO_RT; typedef struct __attribute__((packed)) { - uint8_t cmd; + INTER_CORE_CMD_TEMPHUM cmd; uint32_t telemtrySendRate; - char telemetryJSON[JSON_STRING_MAX_SIZE]; + char telemetryJSON[JSON_STRING_MAX_SIZE]; //////////////////////////////////////////////////////////////////////////////////////// // Don't change the declarations above or the generic RTApp implementation will break // //////////////////////////////////////////////////////////////////////////////////////// - int range_mm; -} IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL; + float temp; + float hum; +} IC_COMMAND_BLOCK_TEMPHUM_RT_TO_HL; \ No newline at end of file diff --git a/avnet_sensors_converge/avnet_tempHum13/main.c b/avnet_sensors_converge/avnet_tempHum13/main.c index ab2da75..498018e 100644 --- a/avnet_sensors_converge/avnet_tempHum13/main.c +++ b/avnet_sensors_converge/avnet_tempHum13/main.c @@ -41,11 +41,11 @@ ************************************************************************************************/ #include "main.h" -static int closeRange = DEFAULT_CLOSE_RANGE; -static int mediumRange = DEFAULT_MEDIUM_RANGE; -static int farRange = DEFAULT_FAR_RANGE; +static int coolRange = DEFAULT_COOL_TEMP; +static int warmRange = DEFAULT_WARM_TEMP; +static int hotRange = DEFAULT_HOT_TEMP; -static int lastRangeMeasurement = -1; +static float lastTempMeasurement = -100.0; /**************************************************************************************** * Implementation @@ -56,10 +56,9 @@ static DX_DEVICE_TWIN_HANDLER(dt_red_led_set_limit, deviceTwinBinding) { // validate data is sensible range before applying. if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && - *(int *)deviceTwinBinding->propertyValue >= MIN_CLOSE_RANGE && - *(int *)deviceTwinBinding->propertyValue < mediumRange) { + *(int *)deviceTwinBinding->propertyValue >= warmRange) { - closeRange = *(int *)deviceTwinBinding->propertyValue; + hotRange = *(int *)deviceTwinBinding->propertyValue; dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, DX_DEVICE_TWIN_RESPONSE_COMPLETED); @@ -75,10 +74,9 @@ static DX_DEVICE_TWIN_HANDLER(dt_blue_led_set_limit, deviceTwinBinding) { // validate data is sensible range before applying if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && - *(int *)deviceTwinBinding->propertyValue >=closeRange && - *(int *)deviceTwinBinding->propertyValue < farRange) { + *(int *)deviceTwinBinding->propertyValue < warmRange) { - mediumRange = *(int *)deviceTwinBinding->propertyValue; + coolRange = *(int *)deviceTwinBinding->propertyValue; dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, DX_DEVICE_TWIN_RESPONSE_COMPLETED); @@ -94,10 +92,10 @@ static DX_DEVICE_TWIN_HANDLER(dt_green_led_set_limit, deviceTwinBinding) { // validate data is sensible range before applying if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && - *(int *)deviceTwinBinding->propertyValue > mediumRange && - *(int *)deviceTwinBinding->propertyValue < FAR_RANGE_MAX) { + *(int *)deviceTwinBinding->propertyValue > coolRange && + *(int *)deviceTwinBinding->propertyValue < hotRange) { - farRange = *(int *)deviceTwinBinding->propertyValue; + warmRange = *(int *)deviceTwinBinding->propertyValue; dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, DX_DEVICE_TWIN_RESPONSE_COMPLETED); @@ -155,20 +153,20 @@ DX_DEVICE_TWIN_HANDLER_END // Using the rangeStatus value, turn on/off the range indication LEDs -static void setPwmStatusLed(RGB_Status rangeStatus, int range) +static void setPwmStatusLed(RGB_Status tempStatus, float temp) { - static RGB_Status lastRangeStatus = RGB_INVALID; - static int lastRange = -1; + static RGB_Status lastTempStatus = RGB_INVALID; + static float lastTemp = -100.0; uint32_t dutyCycle = 100; // Nothing to see here folks, move along . . . - if((lastRangeStatus == rangeStatus) && (lastRange == range)){ + if((lastTempStatus == tempStatus) && (lastTemp == temp)){ return; } // Update the local static variables - lastRangeStatus = rangeStatus; - lastRange = range; + lastTempStatus = tempStatus; + lastTemp = temp; // Turn off all the LED's then set the LED corresponding to the range status // Turn off RGBLED - 100% duty cycle is off @@ -176,22 +174,22 @@ static void setPwmStatusLed(RGB_Status rangeStatus, int range) dx_pwmSetDutyCycle(&pwm_green_led, 1000, 100); dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 100); - switch (rangeStatus) + switch (tempStatus) { case RGB_OUT_OF_RANGE: break; // Leave the LEDs off - case RGB_CLOSE: // Red LED - dutyCycle = (uint32_t)((float)(range-0)/(float)(closeRange-0)*100); - dx_pwmSetDutyCycle(&pwm_red_led, 1000, dutyCycle); - break; - case RGB_MEDIUM: // Blue LED - dutyCycle = (uint32_t)(((float)(range-closeRange)/(float)(mediumRange - closeRange))*100); + case RGB_COOL: // Blue LED + //dutyCycle = (uint32_t)((float)(range-0)/(float)(closeRange-0)*100); dx_pwmSetDutyCycle(&pwm_blue_led, 1000, dutyCycle); break; - case RGB_FAR: // Green LED - dutyCycle = (uint32_t)(((float)(range-mediumRange)/(float)(farRange - mediumRange))*100); + case RGB_WARM: // Green LED + //dutyCycle = (uint32_t)(((float)(range-closeRange)/(float)(mediumRange - closeRange))*100); dx_pwmSetDutyCycle(&pwm_green_led, 1000, dutyCycle); break; + case RGB_HOT: // Red LED + //dutyCycle = (uint32_t)(((float)(range-mediumRange)/(float)(farRange - mediumRange))*100); + dx_pwmSetDutyCycle(&pwm_red_led, 1000, dutyCycle); + break; case RGB_INVALID: default: break; @@ -207,38 +205,38 @@ static void receive_msg_handler(void *data_block, ssize_t message_length) { // Cast the data block so we can index into the data - IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL *messageData = (IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL*) data_block; + IC_COMMAND_BLOCK_TEMPHUM_RT_TO_HL *messageData = (IC_COMMAND_BLOCK_TEMPHUM_RT_TO_HL*) data_block; switch (messageData->cmd) { - case IC_LIGHTRANGER5_CLICK_READ_SENSOR: + case IC_TEMPHUM_READ_SENSOR: - if(messageData->range_mm == -1){ - setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->range_mm); + if(messageData->temp == -1){ + setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->temp); } else{ - if(messageData->range_mm <= closeRange){ - setPwmStatusLed(RGB_CLOSE, messageData->range_mm); + if(messageData->temp <= coolRange){ + setPwmStatusLed(RGB_COOL, messageData->temp); } - else if (messageData->range_mm <= mediumRange){ - setPwmStatusLed(RGB_MEDIUM, messageData->range_mm); + else if (messageData->temp <= warmRange){ + setPwmStatusLed(RGB_WARM, messageData->temp); } - else if (messageData->range_mm <= farRange){ - setPwmStatusLed(RGB_FAR, messageData->range_mm); + else if (messageData->temp <= hotRange){ + setPwmStatusLed(RGB_HOT, messageData->temp); } else{ - setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->range_mm); + setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->temp); } } // Capture the last measurement in the global variable - lastRangeMeasurement = messageData->range_mm; + lastTempMeasurement = messageData->temp; break; // Handle the other cases by doing nothing - case IC_LIGHTRANGER5_CLICK_HEARTBEAT: - case IC_LIGHTRANGER5_CLICK_READ_SENSOR_RESPOND_WITH_TELEMETRY: - case IC_LIGHTRANGER5_CLICK_SET_AUTO_TELEMETRY_RATE: - case IC_LIGHTRANGER5_CLICK_UNKNOWN: + case IC_TEMPHUM_HEARTBEAT: + case IC_TEMPHUM_READ_SENSOR_RESPOND_WITH_TELEMETRY: + case IC_TEMPHUM_SET_TELEMETRY_SEND_RATE: + case IC_TEMPHUM_UNKNOWN: default: break; } @@ -251,12 +249,12 @@ static DX_TIMER_HANDLER(ReadSensorHandler) { //Code to read the sensor data in your application // reset inter-core block - memset(&ic_tx_block, 0x00, sizeof(IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT)); + memset(&ic_tx_block, 0x00, sizeof(IC_COMMAND_BLOCK_TEMPHUM_HL_TO_RT)); // Send read sensor message to realtime core app one - ic_tx_block.cmd = IC_LIGHTRANGER5_CLICK_READ_SENSOR; - dx_intercorePublish(&intercore_lightranger5_click_binding, &ic_tx_block, - sizeof(IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT)); + ic_tx_block.cmd = IC_TEMPHUM_READ_SENSOR; + dx_intercorePublish(&intercore_tempHum13_click_binding, &ic_tx_block, + sizeof(IC_COMMAND_BLOCK_TEMPHUM_HL_TO_RT)); } DX_TIMER_HANDLER_END @@ -266,7 +264,7 @@ DX_TIMER_HANDLER_END static DX_TIMER_HANDLER(SendTelemetryHandler) { - snprintf(msgBuffer, sizeof(msgBuffer), "{\"rangeData\":%d}", lastRangeMeasurement); + snprintf(msgBuffer, sizeof(msgBuffer), "{\"rangeData\":%d}", lastTempMeasurement); Log_Debug("%s\n", msgBuffer); if(dx_isAzureConnected()){ @@ -293,7 +291,7 @@ static void InitPeripheralsAndHandlers(void) dx_timerSetStart(timer_bindings, NELEMS(timer_bindings)); dx_deviceTwinSubscribe(device_twin_bindings, NELEMS(device_twin_bindings)); dx_directMethodSubscribe(direct_method_bindings, NELEMS(direct_method_bindings)); - dx_intercoreConnect(&intercore_lightranger5_click_binding); + dx_intercoreConnect(&intercore_tempHum13_click_binding); dx_pwmSetOpen(pwm_bindings, NELEMS(pwm_bindings)); // Turn off RGBLED - 100% duty cycle is off diff --git a/avnet_sensors_converge/avnet_tempHum13/main.h b/avnet_sensors_converge/avnet_tempHum13/main.h index 2c375f4..0c360ff 100644 --- a/avnet_sensors_converge/avnet_tempHum13/main.h +++ b/avnet_sensors_converge/avnet_tempHum13/main.h @@ -15,14 +15,14 @@ #include #include #include "dx_intercore.h" -#include "lightranger5_click.h" +#include "htu21d_rtapp.h" #include "dx_uart.h" // Use main.h to define all your application definitions, message properties/contentProperties, // bindings and binding sets. // https://docs.microsoft.com/en-us/azure/iot-pnp/overview-iot-plug-and-play -#define IOT_PLUG_AND_PLAY_MODEL_ID "dtmi:amsTmf8801Workshop:SphereTMF8801_5eg;1" +#define IOT_PLUG_AND_PLAY_MODEL_ID "" // Details on how to connect your application using an ethernet adaptor // https://docs.microsoft.com/en-us/azure-sphere/network/connect-ethernet @@ -43,12 +43,9 @@ #define MIN_TELEMETRY_TX_PERIOD 1 #define MAX_TELEMETRY_TX_PERIOD (60*60) // 1 Hour -#define DEFAULT_CLOSE_RANGE 100 -#define DEFAULT_MEDIUM_RANGE 200 -#define DEFAULT_FAR_RANGE 300 - -#define MIN_CLOSE_RANGE 30 -#define FAR_RANGE_MAX 500 +#define DEFAULT_COOL_TEMP 26 +#define DEFAULT_WARM_TEMP 30 +#define DEFAULT_HOT_TEMP 32 DX_USER_CONFIG dx_config; @@ -65,9 +62,9 @@ DX_USER_CONFIG dx_config; typedef enum { RGB_INVALID = 0, RGB_OUT_OF_RANGE, - RGB_CLOSE, - RGB_MEDIUM, - RGB_FAR + RGB_COOL, + RGB_WARM, + RGB_HOT } RGB_Status; /**************************************************************************************** @@ -82,8 +79,8 @@ static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_green_led_set_limit); static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms); static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_telemetemetry_period_seconds); -IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_HL_TO_RT ic_tx_block; -IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL ic_rx_block; +IC_COMMAND_BLOCK_TEMPHUM_HL_TO_RT ic_tx_block; +IC_COMMAND_BLOCK_TEMPHUM_RT_TO_HL ic_rx_block; /**************************************************************************************** * Telemetry message buffer property sets @@ -102,13 +99,13 @@ static DX_MESSAGE_CONTENT_PROPERTIES contentProperties = {.contentEncoding = "ut /**************************************************************************************** * Bindings ****************************************************************************************/ -DX_INTERCORE_BINDING intercore_lightranger5_click_binding = { +DX_INTERCORE_BINDING intercore_tempHum13_click_binding = { .sockFd = -1, .nonblocking_io = true, .rtAppComponentId = "f6768b9a-e086-4f5a-8219-5ffe9684b001", .interCoreCallback = receive_msg_handler, .intercore_recv_block = &ic_rx_block, - .intercore_recv_block_length = sizeof(IC_COMMAND_BLOCK_LIGHTRANGER5_CLICK_RT_TO_HL)}; + .intercore_recv_block_length = sizeof(IC_COMMAND_BLOCK_TEMPHUM_RT_TO_HL)}; static DX_TIMER_BINDING readSensorTimer = { .repeat = &(struct timespec){DEFAULT_SENSOR_POLL_PERIOD_SECONDS, DEFAULT_SENSOR_POLL_PERIOD_MS}, From 0675baf80ee756f637dc27ec661d9e596876a7c6 Mon Sep 17 00:00:00 2001 From: Brian W Date: Thu, 31 Mar 2022 09:59:29 -0700 Subject: [PATCH 05/14] Demo with PWM working --- avnet_sensors_converge/avnet_tempHum13/main.c | 145 +++++++----------- avnet_sensors_converge/avnet_tempHum13/main.h | 40 ++--- 2 files changed, 65 insertions(+), 120 deletions(-) diff --git a/avnet_sensors_converge/avnet_tempHum13/main.c b/avnet_sensors_converge/avnet_tempHum13/main.c index 498018e..8f28196 100644 --- a/avnet_sensors_converge/avnet_tempHum13/main.c +++ b/avnet_sensors_converge/avnet_tempHum13/main.c @@ -41,75 +41,37 @@ ************************************************************************************************/ #include "main.h" -static int coolRange = DEFAULT_COOL_TEMP; -static int warmRange = DEFAULT_WARM_TEMP; -static int hotRange = DEFAULT_HOT_TEMP; - -static float lastTempMeasurement = -100.0; +static float lastTempMeasurement = -100.0F; +static float lastHumMeasurement = -100.0F; +static double calculatedRoomTemp = 0.0F; +static bool roomTempCalculated = false; /**************************************************************************************** * Implementation ****************************************************************************************/ -//static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms); - -static DX_DEVICE_TWIN_HANDLER(dt_red_led_set_limit, deviceTwinBinding) -{ - // validate data is sensible range before applying. - if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && - *(int *)deviceTwinBinding->propertyValue >= warmRange) { - - hotRange = *(int *)deviceTwinBinding->propertyValue; +static void updateHistoricalTempData(float tempData){ - dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, - DX_DEVICE_TWIN_RESPONSE_COMPLETED); + static float historicalTempData[HISTORICAL_DATA_ARRAY_SIZE]; + static int arrayIndex = 0; + double runningAverageSum = 0; - } else { - dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, - DX_DEVICE_TWIN_RESPONSE_ERROR); + if(!roomTempCalculated && ++arrayIndex >= HISTORICAL_DATA_ARRAY_SIZE){ + // Calculate room temperature based on the first HISTORICAL_DATA_ARRAY_SIZE + // temperature readings + for(int i = 0; i < HISTORICAL_DATA_ARRAY_SIZE; i++){ + runningAverageSum = runningAverageSum + tempData; + } + calculatedRoomTemp = runningAverageSum/(double)HISTORICAL_DATA_ARRAY_SIZE; + roomTempCalculated = true; + Log_Debug("Room temperature captured as %.2fC\n", calculatedRoomTemp); } -} -DX_DEVICE_TWIN_HANDLER_END - -static DX_DEVICE_TWIN_HANDLER(dt_blue_led_set_limit, deviceTwinBinding) -{ - // validate data is sensible range before applying - if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && - *(int *)deviceTwinBinding->propertyValue < warmRange) { - - coolRange = *(int *)deviceTwinBinding->propertyValue; - - dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, - DX_DEVICE_TWIN_RESPONSE_COMPLETED); - - } else { - dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, - DX_DEVICE_TWIN_RESPONSE_ERROR); + // We're still capturing data, update the next array location with the new temperature reading + else{ + historicalTempData[arrayIndex] = tempData; } } -DX_DEVICE_TWIN_HANDLER_END - -static DX_DEVICE_TWIN_HANDLER(dt_green_led_set_limit, deviceTwinBinding) -{ - // validate data is sensible range before applying - if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && - *(int *)deviceTwinBinding->propertyValue > coolRange && - *(int *)deviceTwinBinding->propertyValue < hotRange) { - - warmRange = *(int *)deviceTwinBinding->propertyValue; - - dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, - DX_DEVICE_TWIN_RESPONSE_COMPLETED); - - } else { - dx_deviceTwinAckDesiredValue(deviceTwinBinding, deviceTwinBinding->propertyValue, - DX_DEVICE_TWIN_RESPONSE_ERROR); - } -} -DX_DEVICE_TWIN_HANDLER_END - static DX_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms, deviceTwinBinding) { - // validate data is sensible range before applying. if (deviceTwinBinding->twinType == DX_DEVICE_TWIN_INT && *(int *)deviceTwinBinding->propertyValue >= MIN_POLL_TIME_MS && @@ -151,14 +113,24 @@ static DX_DEVICE_TWIN_HANDLER(dt_set_telemetemetry_period_seconds, deviceTwinBin } DX_DEVICE_TWIN_HANDLER_END - // Using the rangeStatus value, turn on/off the range indication LEDs -static void setPwmStatusLed(RGB_Status tempStatus, float temp) +static void setPwmStatusLed(float temp) { static RGB_Status lastTempStatus = RGB_INVALID; + RGB_Status tempStatus = RGB_INVALID; static float lastTemp = -100.0; uint32_t dutyCycle = 100; + // Detmine if we're under of over the calculated room temperature + if(roomTempCalculated){ + if(temp < calculatedRoomTemp){ + tempStatus = RGB_UNDER_ROOM_TEMP; + } + else if(temp > calculatedRoomTemp){ + tempStatus = RGB_OVER_ROOM_TEMP; + } + } + // Nothing to see here folks, move along . . . if((lastTempStatus == tempStatus) && (lastTemp == temp)){ return; @@ -176,18 +148,15 @@ static void setPwmStatusLed(RGB_Status tempStatus, float temp) switch (tempStatus) { - case RGB_OUT_OF_RANGE: - break; // Leave the LEDs off - case RGB_COOL: // Blue LED + case RGB_UNDER_ROOM_TEMP: // Blue LED + + //dutyCycle = (uint32_t)((float)(range-0)/(float)(closeRange-0)*100); + dutyCycle = (uint32_t)((float)(temp-(calculatedRoomTemp-OVER_UNDER_RANGE))/(float)(calculatedRoomTemp-(calculatedRoomTemp-OVER_UNDER_RANGE))*100); dx_pwmSetDutyCycle(&pwm_blue_led, 1000, dutyCycle); break; - case RGB_WARM: // Green LED - //dutyCycle = (uint32_t)(((float)(range-closeRange)/(float)(mediumRange - closeRange))*100); - dx_pwmSetDutyCycle(&pwm_green_led, 1000, dutyCycle); - break; - case RGB_HOT: // Red LED - //dutyCycle = (uint32_t)(((float)(range-mediumRange)/(float)(farRange - mediumRange))*100); + case RGB_OVER_ROOM_TEMP: // Red LED + dutyCycle = (uint32_t)((float)(temp-(calculatedRoomTemp+OVER_UNDER_RANGE))/(float)(calculatedRoomTemp-(calculatedRoomTemp+OVER_UNDER_RANGE))*100); dx_pwmSetDutyCycle(&pwm_red_led, 1000, dutyCycle); break; case RGB_INVALID: @@ -209,27 +178,15 @@ static void receive_msg_handler(void *data_block, ssize_t message_length) switch (messageData->cmd) { case IC_TEMPHUM_READ_SENSOR: - - if(messageData->temp == -1){ - setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->temp); + if(roomTempCalculated){ + setPwmStatusLed(messageData->temp); } else{ - if(messageData->temp <= coolRange){ - setPwmStatusLed(RGB_COOL, messageData->temp); - } - else if (messageData->temp <= warmRange){ - setPwmStatusLed(RGB_WARM, messageData->temp); - } - else if (messageData->temp <= hotRange){ - setPwmStatusLed(RGB_HOT, messageData->temp); - } - else{ - setPwmStatusLed(RGB_OUT_OF_RANGE, messageData->temp); - } + updateHistoricalTempData(messageData->temp); } - // Capture the last measurement in the global variable lastTempMeasurement = messageData->temp; + lastHumMeasurement = messageData->hum; break; // Handle the other cases by doing nothing @@ -264,7 +221,7 @@ DX_TIMER_HANDLER_END static DX_TIMER_HANDLER(SendTelemetryHandler) { - snprintf(msgBuffer, sizeof(msgBuffer), "{\"rangeData\":%d}", lastTempMeasurement); + snprintf(msgBuffer, sizeof(msgBuffer), "{\"temp\":%.2f, \"humidity\": %.2f}", lastTempMeasurement); Log_Debug("%s\n", msgBuffer); if(dx_isAzureConnected()){ @@ -294,12 +251,12 @@ static void InitPeripheralsAndHandlers(void) dx_intercoreConnect(&intercore_tempHum13_click_binding); dx_pwmSetOpen(pwm_bindings, NELEMS(pwm_bindings)); - // Turn off RGBLED - 100% duty cycle is off - dx_pwmSetDutyCycle(&pwm_red_led, 1000, 100); - dx_pwmSetDutyCycle(&pwm_green_led, 1000, 100); - dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 100); + // Turn on all RGBLEDs - 0% duty cycle is 100% on + dx_pwmSetDutyCycle(&pwm_red_led, 1000, 0); + dx_pwmSetDutyCycle(&pwm_green_led, 1000, 0); + dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 0); - Log_Debug("Lightranger5 Demo Starting . . . \n"); + Log_Debug("Temp&Hum13 Demo Starting . . . \n"); } /// @@ -307,6 +264,12 @@ static void InitPeripheralsAndHandlers(void) /// static void ClosePeripheralsAndHandlers(void) { + + // Turn off RGBLEDs - 100% duty cycle is off + dx_pwmSetDutyCycle(&pwm_red_led, 1000, 100); + dx_pwmSetDutyCycle(&pwm_green_led, 1000, 100); + dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 100); + dx_timerSetStop(timer_bindings, NELEMS(timer_bindings)); dx_pwmSetClose(pwm_bindings, NELEMS(pwm_bindings)); dx_deviceTwinUnsubscribe(); diff --git a/avnet_sensors_converge/avnet_tempHum13/main.h b/avnet_sensors_converge/avnet_tempHum13/main.h index 0c360ff..b06a484 100644 --- a/avnet_sensors_converge/avnet_tempHum13/main.h +++ b/avnet_sensors_converge/avnet_tempHum13/main.h @@ -18,9 +18,6 @@ #include "htu21d_rtapp.h" #include "dx_uart.h" -// Use main.h to define all your application definitions, message properties/contentProperties, -// bindings and binding sets. - // https://docs.microsoft.com/en-us/azure/iot-pnp/overview-iot-plug-and-play #define IOT_PLUG_AND_PLAY_MODEL_ID "" @@ -43,9 +40,9 @@ #define MIN_TELEMETRY_TX_PERIOD 1 #define MAX_TELEMETRY_TX_PERIOD (60*60) // 1 Hour -#define DEFAULT_COOL_TEMP 26 -#define DEFAULT_WARM_TEMP 30 -#define DEFAULT_HOT_TEMP 32 +#define HISTORICAL_DATA_ARRAY_SIZE 64 + +#define OVER_UNDER_RANGE 2 // Degrees C DX_USER_CONFIG dx_config; @@ -61,10 +58,8 @@ DX_USER_CONFIG dx_config; ****************************************************************************************/ typedef enum { RGB_INVALID = 0, - RGB_OUT_OF_RANGE, - RGB_COOL, - RGB_WARM, - RGB_HOT + RGB_UNDER_ROOM_TEMP, + RGB_OVER_ROOM_TEMP } RGB_Status; /**************************************************************************************** @@ -73,11 +68,9 @@ typedef enum { static void receive_msg_handler(void *data_block, ssize_t message_length); static DX_DECLARE_TIMER_HANDLER(ReadSensorHandler); static DX_DECLARE_TIMER_HANDLER(SendTelemetryHandler); -static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_red_led_set_limit); -static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_blue_led_set_limit); -static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_green_led_set_limit); static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms); static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_telemetemetry_period_seconds); +static void updateHistoricalTempData(float tempData); IC_COMMAND_BLOCK_TEMPHUM_HL_TO_RT ic_tx_block; IC_COMMAND_BLOCK_TEMPHUM_RT_TO_HL ic_rx_block; @@ -120,23 +113,13 @@ static DX_PWM_CONTROLLER pwm_led_controller = {.controllerId = SAMPLE_LED_PWM_CO static DX_PWM_BINDING pwm_red_led = { .pwmController = &pwm_led_controller, .channelId = 0, .name = "red_led"}; + static DX_PWM_BINDING pwm_green_led = { - .pwmController = &pwm_led_controller, .channelId = 1, .name = "green led"}; + .pwmController = &pwm_led_controller, .channelId = 1, .name = "green_led"}; + static DX_PWM_BINDING pwm_blue_led = { .pwmController = &pwm_led_controller, .channelId = 2, .name = "blue led"}; -static DX_DEVICE_TWIN_BINDING dt_red_limit = {.propertyName = "redLimit_mm", - .twinType = DX_DEVICE_TWIN_INT, - .handler = dt_red_led_set_limit}; - -static DX_DEVICE_TWIN_BINDING dt_green_limit = {.propertyName = "greenLimit_mm", - .twinType = DX_DEVICE_TWIN_INT, - .handler = dt_green_led_set_limit}; - -static DX_DEVICE_TWIN_BINDING dt_blue_limit = {.propertyName = "blueLimit_mm", - .twinType = DX_DEVICE_TWIN_INT, - .handler = dt_blue_led_set_limit}; - static DX_DEVICE_TWIN_BINDING dt_desired_sample_rate_ms = {.propertyName = "sensorPollPeriod_ms", .twinType = DX_DEVICE_TWIN_INT, .handler = dt_set_sensor_polling_period_ms}; @@ -149,10 +132,9 @@ static DX_DEVICE_TWIN_BINDING dt_telemetry_tx_period_s = {.propertyName = "setTe /**************************************************************************************** * Binding sets ****************************************************************************************/ -DX_DEVICE_TWIN_BINDING *device_twin_bindings[] = {&dt_red_limit, &dt_green_limit, &dt_blue_limit, - &dt_desired_sample_rate_ms, +DX_DEVICE_TWIN_BINDING *device_twin_bindings[] = {&dt_desired_sample_rate_ms, &dt_telemetry_tx_period_s}; DX_DIRECT_METHOD_BINDING *direct_method_bindings[] = {}; DX_GPIO_BINDING *gpio_bindings[] = {}; -DX_TIMER_BINDING *timer_bindings[] = {&readSensorTimer, &sendTelemetryTimer}; +DX_TIMER_BINDING *timer_bindings[] = {&readSensorTimer}; //, &sendTelemetryTimer}; static DX_PWM_BINDING *pwm_bindings[] = {&pwm_red_led, &pwm_green_led, &pwm_blue_led}; From 1e1dc548ccc730ce230bb9f7821ba5b59137df6e Mon Sep 17 00:00:00 2001 From: Brian W Date: Thu, 31 Mar 2022 13:22:07 -0700 Subject: [PATCH 06/14] Working demo --- .../avnet_tempHum13/app_manifest.json | 4 +- avnet_sensors_converge/avnet_tempHum13/main.c | 71 +++++++++++-------- avnet_sensors_converge/avnet_tempHum13/main.h | 53 +++++++------- 3 files changed, 71 insertions(+), 57 deletions(-) diff --git a/avnet_sensors_converge/avnet_tempHum13/app_manifest.json b/avnet_sensors_converge/avnet_tempHum13/app_manifest.json index c119d6b..db388da 100644 --- a/avnet_sensors_converge/avnet_tempHum13/app_manifest.json +++ b/avnet_sensors_converge/avnet_tempHum13/app_manifest.json @@ -1,11 +1,11 @@ { "SchemaVersion": 1, - "Name": "avnet_lightranger5_TMF8801_HLApp-V1", + "Name": "avnet_TEMPHUM_TMF8801_HLApp-V1", "ComponentId": "b8f5931e-173a-40f5-a4f8-3d98240f53ec", "EntryPoint": "/bin/app", "CmdArgs": [ "--ScopeID", "0ne00000000" ], "Capabilities": { - "Gpio": [], + "Gpio": ["$SAMPLE_BUTTON_1", "$SAMPLE_BUTTON_2"], "Pwm": [ "$SAMPLE_LED_PWM_CONTROLLER" ], "AllowedConnections": [ "global.azure-devices-provisioning.net", "YOUR_IOT_HUB-HOSTNAME.azure-devices.net"], diff --git a/avnet_sensors_converge/avnet_tempHum13/main.c b/avnet_sensors_converge/avnet_tempHum13/main.c index 8f28196..1f9ae0e 100644 --- a/avnet_sensors_converge/avnet_tempHum13/main.c +++ b/avnet_sensors_converge/avnet_tempHum13/main.c @@ -49,6 +49,29 @@ static bool roomTempCalculated = false; /**************************************************************************************** * Implementation ****************************************************************************************/ +/// +/// Handler to check for Button Presses +/// +static DX_TIMER_HANDLER(ButtonPressCheckHandler) +{ + static GPIO_Value_Type buttonAState; + static GPIO_Value_Type buttonBState; + + // Check to see if either button was pressed + if (dx_gpioStateGet(&buttonA, &buttonAState) || dx_gpioStateGet(&buttonB, &buttonBState) ) { + + // Turn the RBB LED on bright to indicate that we're sampling room temperature + dx_pwmSetDutyCycle(&pwm_red_led, 1000, 0); + dx_pwmSetDutyCycle(&pwm_green_led, 1000, 0); + dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 0); + + // Set the global flag to false so we calculate room temp again + roomTempCalculated = false; + calculatedRoomTemp = 0.0; + } +} +DX_TIMER_HANDLER_END + static void updateHistoricalTempData(float tempData){ static float historicalTempData[HISTORICAL_DATA_ARRAY_SIZE]; @@ -63,6 +86,7 @@ static void updateHistoricalTempData(float tempData){ } calculatedRoomTemp = runningAverageSum/(double)HISTORICAL_DATA_ARRAY_SIZE; roomTempCalculated = true; + arrayIndex = 0; // Reset the index in case we recalcualte during run time Log_Debug("Room temperature captured as %.2fC\n", calculatedRoomTemp); } // We're still capturing data, update the next array location with the new temperature reading @@ -116,28 +140,15 @@ DX_DEVICE_TWIN_HANDLER_END // Using the rangeStatus value, turn on/off the range indication LEDs static void setPwmStatusLed(float temp) { - static RGB_Status lastTempStatus = RGB_INVALID; - RGB_Status tempStatus = RGB_INVALID; static float lastTemp = -100.0; uint32_t dutyCycle = 100; - // Detmine if we're under of over the calculated room temperature - if(roomTempCalculated){ - if(temp < calculatedRoomTemp){ - tempStatus = RGB_UNDER_ROOM_TEMP; - } - else if(temp > calculatedRoomTemp){ - tempStatus = RGB_OVER_ROOM_TEMP; - } - } - // Nothing to see here folks, move along . . . - if((lastTempStatus == tempStatus) && (lastTemp == temp)){ + if(lastTemp == temp){ return; } - // Update the local static variables - lastTempStatus = tempStatus; + // Update the local static variable lastTemp = temp; // Turn off all the LED's then set the LED corresponding to the range status @@ -146,23 +157,21 @@ static void setPwmStatusLed(float temp) dx_pwmSetDutyCycle(&pwm_green_led, 1000, 100); dx_pwmSetDutyCycle(&pwm_blue_led, 1000, 100); - switch (tempStatus) - { - case RGB_UNDER_ROOM_TEMP: // Blue LED - - - //dutyCycle = (uint32_t)((float)(range-0)/(float)(closeRange-0)*100); - dutyCycle = (uint32_t)((float)(temp-(calculatedRoomTemp-OVER_UNDER_RANGE))/(float)(calculatedRoomTemp-(calculatedRoomTemp-OVER_UNDER_RANGE))*100); + // Detmine if we're under of over the calculated room temperature, then calculate the duty cycle + // 100% == LED Full Brightness + // 0% == LED Off + if(roomTempCalculated){ + if(temp < calculatedRoomTemp){ + dutyCycle = (uint32_t)((float)(temp-(calculatedRoomTemp-OVER_UNDER_RANGE))/ + (float)(calculatedRoomTemp-(calculatedRoomTemp-OVER_UNDER_RANGE))*100); dx_pwmSetDutyCycle(&pwm_blue_led, 1000, dutyCycle); - break; - case RGB_OVER_ROOM_TEMP: // Red LED - dutyCycle = (uint32_t)((float)(temp-(calculatedRoomTemp+OVER_UNDER_RANGE))/(float)(calculatedRoomTemp-(calculatedRoomTemp+OVER_UNDER_RANGE))*100); + } + else if(temp > calculatedRoomTemp){ + dutyCycle = (uint32_t)((float)(temp-(calculatedRoomTemp+OVER_UNDER_RANGE))/ + (float)(calculatedRoomTemp-(calculatedRoomTemp+OVER_UNDER_RANGE))*100); dx_pwmSetDutyCycle(&pwm_red_led, 1000, dutyCycle); - break; - case RGB_INVALID: - default: - break; - } + } + } } /// @@ -221,7 +230,7 @@ DX_TIMER_HANDLER_END static DX_TIMER_HANDLER(SendTelemetryHandler) { - snprintf(msgBuffer, sizeof(msgBuffer), "{\"temp\":%.2f, \"humidity\": %.2f}", lastTempMeasurement); + snprintf(msgBuffer, sizeof(msgBuffer), "{\"temp\":%.2f, \"humidity\": %.2f}", lastTempMeasurement, lastHumMeasurement); Log_Debug("%s\n", msgBuffer); if(dx_isAzureConnected()){ diff --git a/avnet_sensors_converge/avnet_tempHum13/main.h b/avnet_sensors_converge/avnet_tempHum13/main.h index b06a484..a94139b 100644 --- a/avnet_sensors_converge/avnet_tempHum13/main.h +++ b/avnet_sensors_converge/avnet_tempHum13/main.h @@ -26,11 +26,25 @@ #define NETWORK_INTERFACE "wlan0" #define SAMPLE_VERSION_NUMBER "1.0" + + +DX_USER_CONFIG dx_config; + +/**************************************************************************************** + * Avnet IoTConnect Support + ****************************************************************************************/ +// TODO: If the application will connect to Avnet's IoTConnect platform enable the +// #define below +//#define USE_AVNET_IOTCONNECT + +/**************************************************************************************** + * Application defines + ****************************************************************************************/ #define ONE_MS 1000000 #define ONE_HUNDRED_MS 100000000 #define DEFAULT_SENSOR_POLL_PERIOD_SECONDS 0 -#define DEFAULT_SENSOR_POLL_PERIOD_MS (ONE_MS * 50) +#define DEFAULT_SENSOR_POLL_PERIOD_MS (ONE_MS * 100) #define DEFAULT_SEND_TELEMETRY_PERIOD_SECONDS 5 @@ -40,34 +54,17 @@ #define MIN_TELEMETRY_TX_PERIOD 1 #define MAX_TELEMETRY_TX_PERIOD (60*60) // 1 Hour -#define HISTORICAL_DATA_ARRAY_SIZE 64 +#define HISTORICAL_DATA_ARRAY_SIZE 32 #define OVER_UNDER_RANGE 2 // Degrees C -DX_USER_CONFIG dx_config; - -/**************************************************************************************** - * Avnet IoTConnect Support - ****************************************************************************************/ -// TODO: If the application will connect to Avnet's IoTConnect platform enable the -// #define below -//#define USE_AVNET_IOTCONNECT - -/**************************************************************************************** - * Application defines - ****************************************************************************************/ -typedef enum { - RGB_INVALID = 0, - RGB_UNDER_ROOM_TEMP, - RGB_OVER_ROOM_TEMP -} RGB_Status; - /**************************************************************************************** * Forward declarations ****************************************************************************************/ static void receive_msg_handler(void *data_block, ssize_t message_length); static DX_DECLARE_TIMER_HANDLER(ReadSensorHandler); static DX_DECLARE_TIMER_HANDLER(SendTelemetryHandler); +static DX_DECLARE_TIMER_HANDLER(ButtonPressCheckHandler); static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_sensor_polling_period_ms); static DX_DECLARE_DEVICE_TWIN_HANDLER(dt_set_telemetemetry_period_seconds); static void updateHistoricalTempData(float tempData); @@ -127,14 +124,22 @@ static DX_DEVICE_TWIN_BINDING dt_desired_sample_rate_ms = {.propertyName = "sens static DX_DEVICE_TWIN_BINDING dt_telemetry_tx_period_s = {.propertyName = "setTelemetrySendPeriod_seconds", .twinType = DX_DEVICE_TWIN_INT, .handler = dt_set_telemetemetry_period_seconds}; - +static DX_TIMER_BINDING buttonPressCheckTimer = { + .period = {0, 1000000}, .name = "buttonPressCheckTimer", .handler = ButtonPressCheckHandler}; + +static DX_GPIO_BINDING buttonA = { + .pin = SAMPLE_BUTTON_1, .name = "buttonA", .direction = DX_INPUT, .detect = DX_GPIO_DETECT_LOW}; + +static DX_GPIO_BINDING buttonB = { + .pin = SAMPLE_BUTTON_2, .name = "buttonB", .direction = DX_INPUT, .detect = DX_GPIO_DETECT_LOW}; + /**************************************************************************************** * Binding sets ****************************************************************************************/ DX_DEVICE_TWIN_BINDING *device_twin_bindings[] = {&dt_desired_sample_rate_ms, &dt_telemetry_tx_period_s}; -DX_DIRECT_METHOD_BINDING *direct_method_bindings[] = {}; -DX_GPIO_BINDING *gpio_bindings[] = {}; -DX_TIMER_BINDING *timer_bindings[] = {&readSensorTimer}; //, &sendTelemetryTimer}; +static DX_DIRECT_METHOD_BINDING *direct_method_bindings[] = {}; +static DX_GPIO_BINDING *gpio_bindings[] = {&buttonA, &buttonB}; +static DX_TIMER_BINDING *timer_bindings[] = {&readSensorTimer, &sendTelemetryTimer, &buttonPressCheckTimer}; static DX_PWM_BINDING *pwm_bindings[] = {&pwm_red_led, &pwm_green_led, &pwm_blue_led}; From 5ac794cd9d428f78c234793cec6e128e4bb0e0c8 Mon Sep 17 00:00:00 2001 From: Brian W Date: Thu, 31 Mar 2022 13:30:10 -0700 Subject: [PATCH 07/14] signed binaries --- ...-Rev2-Click2-Workshop-V1-signed.imagepackage | Bin 0 -> 46072 bytes ...onverge_TMF8801_HLApp-V1-signed.imagepackage | Bin 0 -> 13068 bytes ...AvnetHTU21dRTApp-App1-V1-Signed.imagepackage | Bin 0 -> 45324 bytes .../avnet_TEMPHUM_HLApp-V1-signed.imagepackage | Bin 0 -> 13152 bytes 4 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 avnet_sensors_converge/avnet_lightranger5/DemoBinaries/AvnetLightRanger5Click-Rev2-Click2-Workshop-V1-signed.imagepackage create mode 100644 avnet_sensors_converge/avnet_lightranger5/DemoBinaries/avnet_sensors_converge_TMF8801_HLApp-V1-signed.imagepackage create mode 100644 avnet_sensors_converge/avnet_tempHum13/DemoBinaries/AvnetHTU21dRTApp-App1-V1-Signed.imagepackage create mode 100644 avnet_sensors_converge/avnet_tempHum13/DemoBinaries/avnet_TEMPHUM_HLApp-V1-signed.imagepackage diff --git a/avnet_sensors_converge/avnet_lightranger5/DemoBinaries/AvnetLightRanger5Click-Rev2-Click2-Workshop-V1-signed.imagepackage b/avnet_sensors_converge/avnet_lightranger5/DemoBinaries/AvnetLightRanger5Click-Rev2-Click2-Workshop-V1-signed.imagepackage new file mode 100644 index 0000000000000000000000000000000000000000..42ee95a35264b1b3ef39a60ec31bc07d6461ae1f GIT binary patch literal 46072 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 UNz&u%xx%(!=|q;R^o8tzd8p8MrT_o{ literal 0 HcmV?d00001 diff --git a/avnet_sensors_converge/avnet_lightranger5/DemoBinaries/avnet_sensors_converge_TMF8801_HLApp-V1-signed.imagepackage b/avnet_sensors_converge/avnet_lightranger5/DemoBinaries/avnet_sensors_converge_TMF8801_HLApp-V1-signed.imagepackage new file mode 100644 index 0000000000000000000000000000000000000000..ad471d567620bea1e6d82bf8ad4c3b7dc7d8f24e GIT binary patch literal 13068 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 aBGpVBhaaY@&158c4^rkL2JWGu8mEfD_F%FA literal 0 HcmV?d00001 diff --git a/avnet_sensors_converge/avnet_tempHum13/DemoBinaries/AvnetHTU21dRTApp-App1-V1-Signed.imagepackage b/avnet_sensors_converge/avnet_tempHum13/DemoBinaries/AvnetHTU21dRTApp-App1-V1-Signed.imagepackage new file mode 100644 index 0000000000000000000000000000000000000000..654b4059f3e0fa9fee4d6c22bc19d571d3b97d47 GIT binary patch literal 45324 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 G?%+9;oX8RY literal 0 HcmV?d00001 From 773bd428c32116613db98e9cb992c7cfef32913a Mon Sep 17 00:00:00 2001 From: Brian W Date: Wed, 13 Apr 2022 12:07:22 -0600 Subject: [PATCH 08/14] Avnet end to end updated to use the 2.1 API --- .../Avnet 2_1 DevX End to End_template.JSON | 85 +++++++++++++++++++ avnet_end_to_end/main.c | 7 +- avnet_end_to_end/main.h | 1 + 3 files changed, 90 insertions(+), 3 deletions(-) create mode 100644 avnet_end_to_end/IoTConnectDeviceTemplate/Avnet 2_1 DevX End to End_template.JSON diff --git a/avnet_end_to_end/IoTConnectDeviceTemplate/Avnet 2_1 DevX End to End_template.JSON b/avnet_end_to_end/IoTConnectDeviceTemplate/Avnet 2_1 DevX End to End_template.JSON new file mode 100644 index 0000000..a10ccfe --- /dev/null +++ b/avnet_end_to_end/IoTConnectDeviceTemplate/Avnet 2_1 DevX End to End_template.JSON @@ -0,0 +1,85 @@ +{ + "code": "AVTe2f", + "name": "AVT EndtoEnd21", + "authType": 2, + "description": "2.1 Device template for the DevX avnet_end_to_end example.", + "isIotEdgeEnable": false, + "attributes": [ + { + "name": "Temperature", + "type": "DECIMAL", + "description": null, + "unit": "Degrees C" + }, + { + "name": "Humidity", + "type": "DECIMAL", + "description": null, + "unit": "% moisture" + }, + { + "name": "Pressure", + "type": "DECIMAL", + "description": null, + "unit": null + }, + { + "name": "MsgId", + "type": "INTEGER" + } + ], + "settings": [ + { + "name": "Software Version", + "type": "STRING", + "localName": "SoftwareVersion", + "defaultValue": "\"\"", + "isReadOnly": true + }, + { + "name": "Timestamp of last startup", + "type": "STRING", + "localName": "DeviceStartUtc", + "defaultValue": "\" \"", + "isReadOnly": true + }, + { + "name": "Current UTC time for device twin update", + "type": "STRING", + "localName": "ReportedUTC", + "defaultValue": "\"\"", + "isReadOnly": true + }, + { + "name": "Timestamp of last connection", + "type": "STRING", + "localName": "DeviceConnectUtc", + "defaultValue": "\" \"", + "isReadOnly": true + }, + { + "name": "Reported Humidity", + "type": "DECIMAL", + "localName": "ReportedHumidity", + "defaultValue": "0", + "isReadOnly": true + }, + { + "name": "Desired Sample Rate", + "type": "INTEGER", + "localName": "DesiredSampleRate", + "defaultValue": "75", + "dataValidation": "0 to 120", + "isReadOnly": false + }, + { + "name": "Reported Temperature", + "type": "DECIMAL", + "localName": "ReportedTemperature", + "defaultValue": "0", + "isReadOnly": true + } + ], + "messageVersion": "2.1", + "dataFrequency": 60 +} \ No newline at end of file diff --git a/avnet_end_to_end/main.c b/avnet_end_to_end/main.c index b586b6f..0804437 100644 --- a/avnet_end_to_end/main.c +++ b/avnet_end_to_end/main.c @@ -44,7 +44,7 @@ static DX_TIMER_HANDLER(publish_message_handler) if (dx_isAvnetConnected()) { // Serialize telemetry as JSON - bool serialization_result = dx_avnetJsonSerialize(msgBuffer, sizeof(msgBuffer), NULL, 4, + bool serialization_result = dx_jsonSerialize(msgBuffer, sizeof(msgBuffer), 4, DX_JSON_INT, "MsgId", msgId++, DX_JSON_DOUBLE, "Temperature", temperature, DX_JSON_DOUBLE, "Humidity", humidity, @@ -54,7 +54,7 @@ static DX_TIMER_HANDLER(publish_message_handler) Log_Debug("%s\n", msgBuffer); - dx_azurePublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + dx_avnetPublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); } else { Log_Debug("JSON Serialization failed: Buffer too small\n"); @@ -69,7 +69,7 @@ static DX_TIMER_HANDLER(report_properties_handler) float temperature = 25.05f; double humidity = 60.25; - if (dx_isAzureConnected()) { + if (dx_isAvnetConnected()) { // Update twin with current UTC (Universal Time Coordinate) in ISO format dx_deviceTwinReportValue(&dt_reported_utc, dx_getCurrentUtc(msgBuffer, sizeof(msgBuffer))); @@ -152,6 +152,7 @@ static void NetworkConnectionState(bool connected) /// static void InitPeripheralsAndHandlers(void) { + dx_avnetSetDebugLevel(AVT_DEBUG_LEVEL_VERBOSE); // comment out to supress IoTConnect debug dx_avnetConnect(&dx_config, NETWORK_INTERFACE); dx_gpioSetOpen(gpio_bindings, NELEMS(gpio_bindings)); dx_timerSetStart(timer_bindings, NELEMS(timer_bindings)); diff --git a/avnet_end_to_end/main.h b/avnet_end_to_end/main.h index e8a6720..d791349 100644 --- a/avnet_end_to_end/main.h +++ b/avnet_end_to_end/main.h @@ -4,6 +4,7 @@ #include "app_exit_codes.h" #include "dx_azure_iot.h" +#include "dx_avnet_iot_connect.h" #include "dx_config.h" #include "dx_json_serializer.h" #include "dx_terminate.h" From a43f9fd4c8417d2016ddbb187fa0ed9b9da2fd46 Mon Sep 17 00:00:00 2001 From: Brian W Date: Wed, 13 Apr 2022 12:40:36 -0600 Subject: [PATCH 09/14] avnet_gw_send_message example updated to 2.1 --- .../devXGwDemo21_template.JSON | 30 ++++++++++++++++ .../devXGwDemo_template.JSON | 34 +++++++++++++++++++ avnet_gw_send_message/main.c | 5 +-- 3 files changed, 67 insertions(+), 2 deletions(-) create mode 100644 avnet_gw_send_message/iotConnect Templates/devXGwDemo21_template.JSON create mode 100644 avnet_gw_send_message/iotConnect Templates/devXGwDemo_template.JSON diff --git a/avnet_gw_send_message/iotConnect Templates/devXGwDemo21_template.JSON b/avnet_gw_send_message/iotConnect Templates/devXGwDemo21_template.JSON new file mode 100644 index 0000000..210c0d3 --- /dev/null +++ b/avnet_gw_send_message/iotConnect Templates/devXGwDemo21_template.JSON @@ -0,0 +1,30 @@ +{ + "code": "devXDemo21", + "name": "devXDemo21", + "tag": "spheregwdevice", + "authType": 2, + "isIotEdgeEnable": false, + "attributes": [ + { + "name": "temperature", + "type": "DECIMAL", + "tag": "temperaturechilddevice", + "unit": "C" + }, + { + "name": "humidity", + "type": "DECIMAL", + "tag": "humiditychilddevice", + "unit": "% moisture" + }, + { + "name": "pressure", + "type": "DECIMAL", + "tag": "pressurechilddevice", + "unit": "psi" + } + ], + "dataFrequency": 60, + "messageVersion": "2.1", + "msgCode": "138913Y" +} \ No newline at end of file diff --git a/avnet_gw_send_message/iotConnect Templates/devXGwDemo_template.JSON b/avnet_gw_send_message/iotConnect Templates/devXGwDemo_template.JSON new file mode 100644 index 0000000..3dfc70d --- /dev/null +++ b/avnet_gw_send_message/iotConnect Templates/devXGwDemo_template.JSON @@ -0,0 +1,34 @@ +{ + "code": "devXDemo", + "name": "devXDemo", + "tag": "spheregwdevice", + "authType": 2, + "description": null, + "isIotEdgeEnable": false, + "attributes": [ + { + "name": "temperature", + "type": "NUMBER", + "tag": "temperaturechilddevice", + "description": null, + "unit": "C" + }, + { + "name": "humidity", + "type": "NUMBER", + "tag": "humiditychilddevice", + "description": null, + "unit": "% moisture" + }, + { + "name": "pressure", + "type": "NUMBER", + "tag": "pressurechilddevice", + "description": null, + "unit": "psi" + } + ], + "dataFrequency": 60, + "messageVersion": "1.0", + "msgCode": "1389TEE" +} \ No newline at end of file diff --git a/avnet_gw_send_message/main.c b/avnet_gw_send_message/main.c index 3cfdeeb..e8e6357 100644 --- a/avnet_gw_send_message/main.c +++ b/avnet_gw_send_message/main.c @@ -136,6 +136,7 @@ DX_TIMER_HANDLER_END /// static void InitPeripheralsAndHandlers(void) { + dx_avnetSetDebugLevel(AVT_DEBUG_LEVEL_INFO); // Comment out to supress IoTConnect debug dx_avnetConnect(&dx_config, NETWORK_INTERFACE); dx_timerSetStart(timers, NELEMS(timers)); dx_deviceTwinSubscribe(device_twin_bindings, NELEMS(device_twin_bindings)); @@ -181,13 +182,13 @@ void sendChildDeviceTelemetry(const char* id, const char* key, float value){ // Create serialized telemetry as JSON bool serialization_result = - dx_avnetJsonSerialize(msgBuffer, sizeof(msgBuffer), dx_avnetFindChild(id), 1, + dx_jsonSerialize(msgBuffer, sizeof(msgBuffer), 1, DX_JSON_DOUBLE, key, value); if (serialization_result) { Log_Debug("%s\n", msgBuffer); - dx_azurePublish(msgBuffer, strlen(msgBuffer), NULL, 0, NULL); + dx_avnetPublish(msgBuffer, strlen(msgBuffer), NULL, 0, NULL, dx_avnetFindChild(id)); } else { Log_Debug("JSON Serialization failed: Buffer too small\n"); From 0a942a1a0f804a6c9bce93af9ef2296fd4b6ae7b Mon Sep 17 00:00:00 2001 From: Brian W Date: Wed, 13 Apr 2022 13:06:34 -0600 Subject: [PATCH 10/14] Update avnet_rsl10-2devices to 2.1 API --- .gitmodules | 6 ++++ avnet_rsl10_2devices/AzureSphereDevX | 2 +- avnet_rsl10_2devices/main.c | 1 + avnet_rsl10_2devices/rsl10.c | 41 ++++++++++++---------------- 4 files changed, 26 insertions(+), 24 deletions(-) diff --git a/.gitmodules b/.gitmodules index 688c5ea..7ebbd44 100644 --- a/.gitmodules +++ b/.gitmodules @@ -172,3 +172,9 @@ [submodule "avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions"] path = avnet_sensors_converge/avnet_tempHum13/HardwareDefinitions url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git +[submodule "avnet_rsl10_2devices/AzureSphereDevX"] + path = avnet_rsl10_2devices/AzureSphereDevX + url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.git +[submodule "avnet_rsl10_2devices/HardwareDefinitions"] + path = avnet_rsl10_2devices/HardwareDefinitions + url = https://github.com/Azure-Sphere-DevX/AzureSphereDevX.HardwareDefinitions.git diff --git a/avnet_rsl10_2devices/AzureSphereDevX b/avnet_rsl10_2devices/AzureSphereDevX index 08e01b4..e3c6c22 160000 --- a/avnet_rsl10_2devices/AzureSphereDevX +++ b/avnet_rsl10_2devices/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 08e01b406c2bcb8c4874f65aa9317c025657dcc4 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_rsl10_2devices/main.c b/avnet_rsl10_2devices/main.c index 5cb2ea7..8c51bc3 100644 --- a/avnet_rsl10_2devices/main.c +++ b/avnet_rsl10_2devices/main.c @@ -350,6 +350,7 @@ static void InitPeripheralsAndHandlers(void) #endif // USE_WEB_PROXY #ifdef USE_IOT_CONNECT + dx_avnetSetDebugLevel(AVT_DEBUG_LEVEL_INFO); // Comment out to supress IoTConnect Debug dx_avnetConnect(&dx_config, NETWORK_INTERFACE); #else dx_azureConnect(&dx_config, NETWORK_INTERFACE, IOT_PLUG_AND_PLAY_MODEL_ID); diff --git a/avnet_rsl10_2devices/rsl10.c b/avnet_rsl10_2devices/rsl10.c index e04bc68..fe7366b 100644 --- a/avnet_rsl10_2devices/rsl10.c +++ b/avnet_rsl10_2devices/rsl10.c @@ -36,10 +36,6 @@ SOFTWARE. // Static buffer for telemetry data static char telemetryBuffer[JSON_BUFFER_SIZE] = {0}; -#ifdef USE_IOT_CONNECT -static char avtMsgBuffer[JSON_BUFFER_SIZE + DX_AVNET_IOT_CONNECT_METADATA] = {0}; -#endif //USE_IOT_CONNECT - static DX_MESSAGE_PROPERTY *messageProperties[] = {&(DX_MESSAGE_PROPERTY){.key = "appid", .value = "Avnet RSL10 Demo"}, &(DX_MESSAGE_PROPERTY){.key = "type", .value = "telemetry"}, &(DX_MESSAGE_PROPERTY){.key = "schema", .value = "1"}}; @@ -503,12 +499,12 @@ void rsl10SendTelemetry(void) { Rsl10DeviceList[currentDevice].lastOrientation_z, Rsl10DeviceList[currentDevice].lastOrientation_w); + Log_Debug("Send telemetry: %s\n", telemetryBuffer); + #ifdef USE_IOT_CONNECT - // Add the IoTConnect metadata to the seralized telemetry - dx_avnetJsonSerializePayload(telemetryBuffer, avtMsgBuffer, sizeof(avtMsgBuffer), NULL); - Log_Debug("%s\n", avtMsgBuffer); - dx_azurePublish(avtMsgBuffer, strlen(avtMsgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + // Send the telemetry message + dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties,NULL); #else // !USE_IOT_CONNECT @@ -516,7 +512,6 @@ void rsl10SendTelemetry(void) { dx_azurePublish(telemetryBuffer, strnlen(telemetryBuffer, JSON_BUFFER_SIZE), messageProperties, NELEMS(messageProperties), &contentProperties); - Log_Debug("Send telemetry: %s\n", telemetryBuffer); #endif // Clear the flag so we don't send this data again Rsl10DeviceList[currentDevice].movementDataRefreshed = false; @@ -541,21 +536,21 @@ void rsl10SendTelemetry(void) { Rsl10DeviceList[currentDevice].lastHumidity, Rsl10DeviceList[currentDevice].telemetryKey, Rsl10DeviceList[currentDevice].lastPressure); + Log_Debug("Send telemetry: %s\n", telemetryBuffer); + #ifdef USE_IOT_CONNECT - // Add the IoTConnect metadata to the seralized telemetry - dx_avnetJsonSerializePayload(telemetryBuffer, avtMsgBuffer, sizeof(avtMsgBuffer), NULL); - Log_Debug("%s\n", avtMsgBuffer); - dx_azurePublish(avtMsgBuffer, strlen(avtMsgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + // Send the telemetry message + dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties,NULL); #else // !USE_IOT_CONNECT // Send the telemetry message dx_azurePublish(telemetryBuffer, strnlen(telemetryBuffer, JSON_BUFFER_SIZE), messageProperties, NELEMS(messageProperties), - &contentProperties); - Log_Debug("Send telemetry: %s\n", telemetryBuffer); -#endif + &contentProperties); +#endif + // Clear the flag so we don't send this data again Rsl10DeviceList[currentDevice].movementDataRefreshed = false; @@ -578,21 +573,21 @@ void rsl10SendTelemetry(void) { Rsl10DeviceList[currentDevice].lastRssi, Rsl10DeviceList[currentDevice].telemetryKey, Rsl10DeviceList[currentDevice].lastBattery); + Log_Debug("Send telemetry: %s\n", telemetryBuffer); + #ifdef USE_IOT_CONNECT - // Add the IoTConnect metadata to the seralized telemetry - dx_avnetJsonSerializePayload(telemetryBuffer, avtMsgBuffer, sizeof(avtMsgBuffer), NULL); - Log_Debug("%s\n", avtMsgBuffer); - dx_azurePublish(avtMsgBuffer, strlen(avtMsgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + // Send the telemetry message + dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties,NULL); #else // !USE_IOT_CONNECT // Send the telemetry message dx_azurePublish(telemetryBuffer, strnlen(telemetryBuffer, JSON_BUFFER_SIZE), messageProperties, NELEMS(messageProperties), - &contentProperties); - Log_Debug("Send telemetry: %s\n", telemetryBuffer); -#endif + &contentProperties); +#endif + // Clear the flag so we don't send this data again Rsl10DeviceList[currentDevice].batteryDataRefreshed = false; From 95dad7cd78f1ba76c6c39e1497c2eadb9bbf7588 Mon Sep 17 00:00:00 2001 From: Brian W Date: Wed, 13 Apr 2022 13:12:14 -0600 Subject: [PATCH 11/14] Update avnet_send_message to 2.1 API --- avnet_send_message/main.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/avnet_send_message/main.c b/avnet_send_message/main.c index 4e18cb0..2339447 100644 --- a/avnet_send_message/main.c +++ b/avnet_send_message/main.c @@ -49,17 +49,16 @@ static void publish_message_handler(EventLoopTimer *eventLoopTimer) // Serialize telemetry as JSON bool serialization_result = - dx_avnetJsonSerialize(msgBuffer, sizeof(msgBuffer), NULL, 4, DX_JSON_INT, "MsgId", msgId++, + dx_jsonSerialize(msgBuffer, sizeof(msgBuffer), 4, DX_JSON_INT, "MsgId", msgId++, DX_JSON_DOUBLE, "Temperature", temperature, DX_JSON_DOUBLE, "Humidity", humidity, DX_JSON_DOUBLE, "Pressure", pressure); - if (serialization_result) { Log_Debug("%s\n", msgBuffer); - dx_azurePublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + dx_avnetPublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); } else { Log_Debug("JSON Serialization failed: Buffer too small\n"); @@ -100,6 +99,7 @@ static void dt_desired_temperature_handler(DX_DEVICE_TWIN_BINDING *deviceTwinBin /// static void InitPeripheralsAndHandlers(void) { + dx_avnetSetDebugLevel(AVT_DEBUG_LEVEL_INFO); // Comment out to suppress IoTConnect Debug dx_avnetConnect(&dx_config, NETWORK_INTERFACE); dx_timerSetStart(timers, NELEMS(timers)); dx_deviceTwinSubscribe(device_twin_bindings, NELEMS(device_twin_bindings)); From 1c9c06a3f2d28df7292b96ae7c52fff4b8c1ee6b Mon Sep 17 00:00:00 2001 From: Brian W Date: Wed, 13 Apr 2022 13:23:14 -0600 Subject: [PATCH 12/14] monitor_memory_usage updated to 2.1 api --- monitor_memory_usage/main.c | 14 ++++++++------ monitor_memory_usage/main.h | 3 ++- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/monitor_memory_usage/main.c b/monitor_memory_usage/main.c index 269d10d..7dc0154 100644 --- a/monitor_memory_usage/main.c +++ b/monitor_memory_usage/main.c @@ -101,17 +101,18 @@ static DX_TIMER_HANDLER(monitor_memory_handler) Log_Debug("New Memory High Water Mark: %d Kb\n", newMemoryHighWaterMark); // Serialize telemetry as JSON -#ifdef USE_AVNET_IOTCONNECT - bool serialization_result = dx_avnetJsonSerialize(msgBuffer, sizeof(msgBuffer), NULL, 1, - DX_JSON_INT, "MemoryHighWaterMark", newMemoryHighWaterMark); -#else bool serialization_result = dx_jsonSerialize(msgBuffer, sizeof(msgBuffer), 1, DX_JSON_INT, "MemoryHighWaterMark", newMemoryHighWaterMark); -#endif if (serialization_result) { Log_Debug("%s\n", msgBuffer); - dx_azurePublish(msgBuffer, strlen(msgBuffer), memoryMessageProperties, NELEMS(memoryMessageProperties), &contentProperties); +#ifdef USE_AVNET_IOTCONNECT + + dx_avnetPublish(msgBuffer, strlen(msgBuffer), memoryMessageProperties, NELEMS(memoryMessageProperties), &contentProperties, NULL); +#else + dx_azurePublish(msgBuffer, strlen(msgBuffer), memoryMessageProperties, NELEMS(memoryMessageProperties), &contentProperties); + +#endif } else { Log_Debug("JSON Serialization failed: Buffer too small\n"); } @@ -126,6 +127,7 @@ DX_TIMER_HANDLER_END static void InitPeripheralsAndHandlers(void) { #ifdef USE_AVNET_IOTCONNECT + dx_avnetSetDebugLevel(AVT_DEBUG_LEVEL_INFO); dx_avnetConnect(&dx_config, NETWORK_INTERFACE); #else dx_azureConnect(&dx_config, NETWORK_INTERFACE, IOT_PLUG_AND_PLAY_MODEL_ID); diff --git a/monitor_memory_usage/main.h b/monitor_memory_usage/main.h index 4541528..d3a8b2a 100644 --- a/monitor_memory_usage/main.h +++ b/monitor_memory_usage/main.h @@ -8,6 +8,7 @@ #include "dx_timer.h" #include "dx_utilities.h" #include "dx_version.h" +#include "dx_avnet_iot_connect.h" #include #include @@ -27,7 +28,7 @@ DX_USER_CONFIG dx_config; ****************************************************************************************/ // TODO: If the application will connect to Avnet's IoTConnect platform enable the // #define below -// #define USE_AVNET_IOTCONNECT +//#define USE_AVNET_IOTCONNECT /**************************************************************************************** * Application defines From 00268ff5d01219b1c46a60b0600637cd4961e413 Mon Sep 17 00:00:00 2001 From: Brian W Date: Wed, 13 Apr 2022 13:24:25 -0600 Subject: [PATCH 13/14] Update all submodules --- avnet_RTAppLab_app/AzureSphereDevX | 2 +- avnet_RTAppLab_app/HardwareDefinitions | 2 +- avnet_bbq_monitor/AzureSphereDevX | 2 +- avnet_bbq_monitor/HardwareDefinitions | 2 +- avnet_end_to_end/AzureSphereDevX | 2 +- avnet_end_to_end/app_manifest.json | 8 ++++---- avnet_gw_send_message/AzureSphereDevX | 2 +- avnet_gw_send_message/app_manifest.json | 13 +++++++------ avnet_rsl10_2devices/app_manifest.json | 16 +++++++++------- avnet_send_message/AzureSphereDevX | 2 +- .../avnet_lightranger5/AzureSphereDevX | 2 +- .../avnet_tempHum13/AzureSphereDevX | 2 +- avnet_sk_demo/AzureSphereDevX | 2 +- azure_end_to_end/AzureSphereDevX | 2 +- azure_send_message/AzureSphereDevX | 2 +- deferred_update/AzureSphereDevX | 2 +- device_twins/AzureSphereDevX | 2 +- device_twins_json_object/AzureSphereDevX | 2 +- direct_methods/AzureSphereDevX | 2 +- error_reporting/AzureSphereDevX | 2 +- gpio_example/AzureSphereDevX | 2 +- intercore_example/HighLevelApp/AzureSphereDevX | 2 +- intercore_generic_example/AzureSphereDevX | 2 +- little_fs_on_mutable_storage/AzureSphereDevX | 2 +- little_fs_on_mutable_storage/littlefs | 2 +- monitor_memory_usage/AzureSphereDevX | 2 +- pwm_click_buzz/AzureSphereDevX | 2 +- pwm_example/AzureSphereDevX | 2 +- starter_project/AzureSphereDevX | 2 +- timer_example/AzureSphereDevX | 2 +- uart_example/AzureSphereDevX | 2 +- 31 files changed, 48 insertions(+), 45 deletions(-) diff --git a/avnet_RTAppLab_app/AzureSphereDevX b/avnet_RTAppLab_app/AzureSphereDevX index 08e01b4..e3c6c22 160000 --- a/avnet_RTAppLab_app/AzureSphereDevX +++ b/avnet_RTAppLab_app/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 08e01b406c2bcb8c4874f65aa9317c025657dcc4 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_RTAppLab_app/HardwareDefinitions b/avnet_RTAppLab_app/HardwareDefinitions index ad2cefa..871149b 160000 --- a/avnet_RTAppLab_app/HardwareDefinitions +++ b/avnet_RTAppLab_app/HardwareDefinitions @@ -1 +1 @@ -Subproject commit ad2cefa8cf6e52ae6ee21e343da2b08a988c15a4 +Subproject commit 871149bd855184ac1d42ee6e61def5da18e9dc8f diff --git a/avnet_bbq_monitor/AzureSphereDevX b/avnet_bbq_monitor/AzureSphereDevX index de68952..e3c6c22 160000 --- a/avnet_bbq_monitor/AzureSphereDevX +++ b/avnet_bbq_monitor/AzureSphereDevX @@ -1 +1 @@ -Subproject commit de68952b0a1c48cac1017cca83000bba08990e00 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_bbq_monitor/HardwareDefinitions b/avnet_bbq_monitor/HardwareDefinitions index 1b76a0e..871149b 160000 --- a/avnet_bbq_monitor/HardwareDefinitions +++ b/avnet_bbq_monitor/HardwareDefinitions @@ -1 +1 @@ -Subproject commit 1b76a0e3b0b19ec6a5447eee6fa6dcbc70e52d32 +Subproject commit 871149bd855184ac1d42ee6e61def5da18e9dc8f diff --git a/avnet_end_to_end/AzureSphereDevX b/avnet_end_to_end/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/avnet_end_to_end/AzureSphereDevX +++ b/avnet_end_to_end/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_end_to_end/app_manifest.json b/avnet_end_to_end/app_manifest.json index 5a5a2be..15f760f 100644 --- a/avnet_end_to_end/app_manifest.json +++ b/avnet_end_to_end/app_manifest.json @@ -3,14 +3,14 @@ "Name": "avnet_end_to_end", "ComponentId": "b217fd65-ac8d-4d7c-b62c-0d07b5df6357", "EntryPoint": "/bin/app", - "CmdArgs": [ "--ScopeID", "REPLACE_WITH_YOUR_ID_SCOPE" ], + "CmdArgs": [ "--ScopeID", "0ne001DB429" ], "Capabilities": { "Gpio": [ "$NETWORK_CONNECTED_LED", "$LED2" ], "AllowedConnections": [ "global.azure-devices-provisioning.net", - "REPLACE_WITH_YOUR_IOT_HUB_ENDPOINT_URL" + "poc-iotc-sphere-iothub-eu.azure-devices.net" ], - "DeviceAuthentication": "REPLACE_WITH_YOUR_AZURE_SPHERE_TENANT_ID" + "DeviceAuthentication": "8d34f65c-532e-4dcf-a1d6-3e811c1e5c68" }, "ApplicationType": "Default" -} +} \ No newline at end of file diff --git a/avnet_gw_send_message/AzureSphereDevX b/avnet_gw_send_message/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/avnet_gw_send_message/AzureSphereDevX +++ b/avnet_gw_send_message/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_gw_send_message/app_manifest.json b/avnet_gw_send_message/app_manifest.json index 84fb196..15f760f 100644 --- a/avnet_gw_send_message/app_manifest.json +++ b/avnet_gw_send_message/app_manifest.json @@ -1,15 +1,16 @@ { "SchemaVersion": 1, - "Name": "avnet_gateway_example", - "ComponentId": "353d8b5e-d3ab-43f7-b65a-10f14b766d21", + "Name": "avnet_end_to_end", + "ComponentId": "b217fd65-ac8d-4d7c-b62c-0d07b5df6357", "EntryPoint": "/bin/app", - "CmdArgs": ["--ScopeID", "REPLACE_WITH_YOUR_ID_SCOPE"], + "CmdArgs": [ "--ScopeID", "0ne001DB429" ], "Capabilities": { + "Gpio": [ "$NETWORK_CONNECTED_LED", "$LED2" ], "AllowedConnections": [ "global.azure-devices-provisioning.net", - "REPLACE_WITH_YOUR_IOT_HUB_ENDPOINT_URL" + "poc-iotc-sphere-iothub-eu.azure-devices.net" ], - "DeviceAuthentication": "REPLACE_WITH_YOUR_AZURE_SPHERE_TENANT_ID" + "DeviceAuthentication": "8d34f65c-532e-4dcf-a1d6-3e811c1e5c68" }, "ApplicationType": "Default" -} +} \ No newline at end of file diff --git a/avnet_rsl10_2devices/app_manifest.json b/avnet_rsl10_2devices/app_manifest.json index f285c3e..18b7b46 100644 --- a/avnet_rsl10_2devices/app_manifest.json +++ b/avnet_rsl10_2devices/app_manifest.json @@ -1,19 +1,21 @@ { "SchemaVersion": 1, - "Name": "AvnetRSL10Example", + "Name": "avnet_end_to_end", "ComponentId": "b217fd65-ac8d-4d7c-b62c-0d07b5df6357", "EntryPoint": "/bin/app", - "CmdArgs": [ "--ScopeID", "" ], + "CmdArgs": [ "--ScopeID", "0ne001DB429" ], "Capabilities": { "Gpio": [ "$SAMPLE_RGBLED_RED", "$SAMPLE_RGBLED_GREEN", "$SAMPLE_RGBLED_BLUE"], "Uart": ["$SAMPLE_PMOD_UART"], - "AllowedConnections": ["global.azure-devices-provisioning.net", - "ENTER.IOT.HUB.HOSTNAME.net"], - "DeviceAuthentication": "00000000-0000-0000-0000-000000000000", - "NetworkConfig": true + "NetworkConfig": true, + "AllowedConnections": [ + "global.azure-devices-provisioning.net", + "poc-iotc-sphere-iothub-eu.azure-devices.net" + ], + "DeviceAuthentication": "8d34f65c-532e-4dcf-a1d6-3e811c1e5c68" }, "ApplicationType": "Default" -} +} \ No newline at end of file diff --git a/avnet_send_message/AzureSphereDevX b/avnet_send_message/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/avnet_send_message/AzureSphereDevX +++ b/avnet_send_message/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX b/avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX +++ b/avnet_sensors_converge/avnet_lightranger5/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX b/avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX +++ b/avnet_sensors_converge/avnet_tempHum13/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/avnet_sk_demo/AzureSphereDevX b/avnet_sk_demo/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/avnet_sk_demo/AzureSphereDevX +++ b/avnet_sk_demo/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/azure_end_to_end/AzureSphereDevX b/azure_end_to_end/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/azure_end_to_end/AzureSphereDevX +++ b/azure_end_to_end/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/azure_send_message/AzureSphereDevX b/azure_send_message/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/azure_send_message/AzureSphereDevX +++ b/azure_send_message/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/deferred_update/AzureSphereDevX b/deferred_update/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/deferred_update/AzureSphereDevX +++ b/deferred_update/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/device_twins/AzureSphereDevX b/device_twins/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/device_twins/AzureSphereDevX +++ b/device_twins/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/device_twins_json_object/AzureSphereDevX b/device_twins_json_object/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/device_twins_json_object/AzureSphereDevX +++ b/device_twins_json_object/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/direct_methods/AzureSphereDevX b/direct_methods/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/direct_methods/AzureSphereDevX +++ b/direct_methods/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/error_reporting/AzureSphereDevX b/error_reporting/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/error_reporting/AzureSphereDevX +++ b/error_reporting/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/gpio_example/AzureSphereDevX b/gpio_example/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/gpio_example/AzureSphereDevX +++ b/gpio_example/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/intercore_example/HighLevelApp/AzureSphereDevX b/intercore_example/HighLevelApp/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/intercore_example/HighLevelApp/AzureSphereDevX +++ b/intercore_example/HighLevelApp/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/intercore_generic_example/AzureSphereDevX b/intercore_generic_example/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/intercore_generic_example/AzureSphereDevX +++ b/intercore_generic_example/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/little_fs_on_mutable_storage/AzureSphereDevX b/little_fs_on_mutable_storage/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/little_fs_on_mutable_storage/AzureSphereDevX +++ b/little_fs_on_mutable_storage/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/little_fs_on_mutable_storage/littlefs b/little_fs_on_mutable_storage/littlefs index ead5080..9c7e232 160000 --- a/little_fs_on_mutable_storage/littlefs +++ b/little_fs_on_mutable_storage/littlefs @@ -1 +1 @@ -Subproject commit ead50807f1ca3fdf2da00b77a0ce02651ded2d13 +Subproject commit 9c7e232086f865cff0bb96fe753deb66431d91fd diff --git a/monitor_memory_usage/AzureSphereDevX b/monitor_memory_usage/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/monitor_memory_usage/AzureSphereDevX +++ b/monitor_memory_usage/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/pwm_click_buzz/AzureSphereDevX b/pwm_click_buzz/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/pwm_click_buzz/AzureSphereDevX +++ b/pwm_click_buzz/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/pwm_example/AzureSphereDevX b/pwm_example/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/pwm_example/AzureSphereDevX +++ b/pwm_example/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/starter_project/AzureSphereDevX b/starter_project/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/starter_project/AzureSphereDevX +++ b/starter_project/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/timer_example/AzureSphereDevX b/timer_example/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/timer_example/AzureSphereDevX +++ b/timer_example/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 diff --git a/uart_example/AzureSphereDevX b/uart_example/AzureSphereDevX index 32fb212..e3c6c22 160000 --- a/uart_example/AzureSphereDevX +++ b/uart_example/AzureSphereDevX @@ -1 +1 @@ -Subproject commit 32fb212aa73d764f2602e2e2624929972af6c003 +Subproject commit e3c6c2232621fd13059f4fd91791bfcb0f526b75 From 22570fc8e73ed1f8a6893c0980925d19c879e219 Mon Sep 17 00:00:00 2001 From: Brian Willess Date: Wed, 1 Jun 2022 04:29:32 -0700 Subject: [PATCH 14/14] Updates to use new IoTConnect calls --- avnet_rsl10_2devices/rsl10.c | 24 +++++++-------- avnet_sk_demo/build_options.h | 1 - avnet_sk_demo/main.c | 58 ++++++++++++++++------------------- avnet_sk_demo/main.h | 3 -- 4 files changed, 38 insertions(+), 48 deletions(-) diff --git a/avnet_rsl10_2devices/rsl10.c b/avnet_rsl10_2devices/rsl10.c index fe7366b..ce84fff 100644 --- a/avnet_rsl10_2devices/rsl10.c +++ b/avnet_rsl10_2devices/rsl10.c @@ -500,11 +500,9 @@ void rsl10SendTelemetry(void) { Rsl10DeviceList[currentDevice].lastOrientation_w); Log_Debug("Send telemetry: %s\n", telemetryBuffer); - #ifdef USE_IOT_CONNECT - // Send the telemetry message - dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties,NULL); + dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); #else // !USE_IOT_CONNECT @@ -536,21 +534,21 @@ void rsl10SendTelemetry(void) { Rsl10DeviceList[currentDevice].lastHumidity, Rsl10DeviceList[currentDevice].telemetryKey, Rsl10DeviceList[currentDevice].lastPressure); + Log_Debug("Send telemetry: %s\n", telemetryBuffer); #ifdef USE_IOT_CONNECT - // Send the telemetry message - dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties,NULL); + dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); #else // !USE_IOT_CONNECT // Send the telemetry message dx_azurePublish(telemetryBuffer, strnlen(telemetryBuffer, JSON_BUFFER_SIZE), messageProperties, NELEMS(messageProperties), - &contentProperties); -#endif - + &contentProperties); + +#endif // Clear the flag so we don't send this data again Rsl10DeviceList[currentDevice].movementDataRefreshed = false; @@ -573,21 +571,21 @@ void rsl10SendTelemetry(void) { Rsl10DeviceList[currentDevice].lastRssi, Rsl10DeviceList[currentDevice].telemetryKey, Rsl10DeviceList[currentDevice].lastBattery); + Log_Debug("Send telemetry: %s\n", telemetryBuffer); #ifdef USE_IOT_CONNECT - // Send the telemetry message - dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties,NULL); + dx_avnetPublish(telemetryBuffer, strlen(telemetryBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); #else // !USE_IOT_CONNECT // Send the telemetry message dx_azurePublish(telemetryBuffer, strnlen(telemetryBuffer, JSON_BUFFER_SIZE), messageProperties, NELEMS(messageProperties), - &contentProperties); -#endif - + &contentProperties); + +#endif // Clear the flag so we don't send this data again Rsl10DeviceList[currentDevice].batteryDataRefreshed = false; diff --git a/avnet_sk_demo/build_options.h b/avnet_sk_demo/build_options.h index 4630d19..4253dda 100644 --- a/avnet_sk_demo/build_options.h +++ b/avnet_sk_demo/build_options.h @@ -22,7 +22,6 @@ // If this is a IoT Conect build, make sure to enable the IOT Hub application code #ifdef USE_IOT_CONNECT #define IOT_HUB_APPLICATION -#define IOT_CONNECT_API_VERSION 1 #undef USE_PNP // Disable PNP device twins responses #endif diff --git a/avnet_sk_demo/main.c b/avnet_sk_demo/main.c index 5afc05d..49ff985 100644 --- a/avnet_sk_demo/main.c +++ b/avnet_sk_demo/main.c @@ -112,8 +112,7 @@ static void publish_message_handler(void) #ifdef USE_DEVX_SERIALIZATION // Serialize telemetry as JSON -#ifdef USE_IOT_CONNECT - bool serialization_result = dx_avnetJsonSerialize(avtMsgBuffer, sizeof(avtMsgBuffer), NULL, 11, + bool serialization_result = dx_jsonSerialize(msgBuffer, sizeof(msgBuffer), 11, DX_JSON_DOUBLE, "gX", acceleration_g.x, DX_JSON_DOUBLE, "gY", acceleration_g.y, DX_JSON_DOUBLE, "gZ", acceleration_g.z, @@ -128,27 +127,14 @@ static void publish_message_handler(void) if (serialization_result) { - Log_Debug("%s\n", avtMsgBuffer); - dx_azurePublish(avtMsgBuffer, strlen(avtMsgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + Log_Debug("%s\n", msgBuffer); -#else // ! IoT Connect +#ifdef USE_IOT_CONNECT - bool serialization_result = dx_jsonSerialize(msgBuffer, sizeof(msgBuffer), 11, - DX_JSON_DOUBLE, "gX", acceleration_g.x, - DX_JSON_DOUBLE, "gY", acceleration_g.y, - DX_JSON_DOUBLE, "gZ", acceleration_g.z, - DX_JSON_DOUBLE, "aX", angular_rate_dps.x, - DX_JSON_DOUBLE, "aY", angular_rate_dps.y, - DX_JSON_DOUBLE, "aZ", angular_rate_dps.z, - DX_JSON_DOUBLE, "pressure", pressure_hPa, - DX_JSON_DOUBLE, "light_intensity", light_sensor, - DX_JSON_DOUBLE, "altitude", altitude, - DX_JSON_DOUBLE, "temp", lsm6dso_temperature, - DX_JSON_INT, "rssi", network_data.rssi); + dx_avnetPublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); - if (serialization_result) { +#else // ! IoT Connect - Log_Debug("%s\n", msgBuffer); dx_azurePublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); #endif // USE_IOT_CONNECT @@ -166,16 +152,16 @@ static void publish_message_handler(void) angular_rate_dps.y, angular_rate_dps.z, pressure_hPa, light_sensor, altitude, lsm6dso_temperature, network_data.rssi); + Log_Debug("%s\n", msgBuffer); + #ifdef USE_IOT_CONNECT - // Add the IoTConnect metadata to the seralized telemetry - dx_avnetJsonSerializePayload(msgBuffer, avtMsgBuffer, sizeof(avtMsgBuffer), NULL); - Log_Debug("%s\n", avtMsgBuffer); - dx_azurePublish(avtMsgBuffer, strlen(avtMsgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + dx_avnetPublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); #else // !USE_IOT_CONNECt - Log_Debug("%s\n", msgBuffer); + dx_azurePublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + #endif // USE_IOT_CONNECT #endif // // !USE_DEVX_SERIALIZATION } @@ -525,8 +511,17 @@ static void SendButtonTelemetry(const char* telemetry_key, GPIO_Value_Type butto if (serialization_result) { Log_Debug("%s\n", msgBuffer); + +#ifdef USE_IOT_CONNECT + + dx_avnetPublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); + +#else // !USE_IOT_CONNECT + dx_azurePublish(msgBuffer, strlen(msgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); +#endif // USE_IOT_CONNECT + } else { Log_Debug("JSON Serialization failed\n"); } @@ -569,18 +564,18 @@ switch (messageData->cmd) { break; case IC_READ_SENSOR_RESPOND_WITH_TELEMETRY: Log_Debug("IC_READ_SENSOR_RESPOND_WITH_TELEMETRY\n"); -// Log_Debug("%s\n", messageData->telemetryJSON); + Log_Debug("%s\n", messageData->telemetryJSON); #ifdef IOT_HUB_APPLICATION #ifdef USE_IOT_CONNECT - // Add the IoTConnect metadata to the seralized telemetry - dx_avnetJsonSerializePayload(messageData->telemetryJSON, avtMsgBuffer, sizeof(avtMsgBuffer), NULL); - Log_Debug("%s\n", avtMsgBuffer); - dx_azurePublish(avtMsgBuffer, strlen(avtMsgBuffer), messageProperties, NELEMS(messageProperties), &contentProperties); + + dx_avnetPublish(messageData->telemetryJSON, strlen(messageData->telemetryJSON), messageProperties, NELEMS(messageProperties), &contentProperties, NULL); #else // !USE_IOT_CONNECT - Log_Debug("%s\n", messageData->telemetryJSON); - dx_azurePublish(messageData->telemetryJSON, strlen(messageData->telemetryJSON), messageProperties, NELEMS(messageProperties), &contentProperties); + + Log_Debug("%s\n", messageData->telemetryJSON); + dx_azurePublish(messageData->telemetryJSON, strlen(messageData->telemetryJSON), messageProperties, NELEMS(messageProperties), &contentProperties); + #endif // USE_IOT_CONNECT #endif // IOT_HUB_APPLICATION @@ -609,6 +604,7 @@ static void InitPeripheralsAndHandlers(void) #ifdef IOT_HUB_APPLICATION #ifdef USE_IOT_CONNECT + //dx_avnetSetDebugLevel(AVT_DEBUG_LEVEL_VERBOSE); dx_avnetConnect(&dx_config, NETWORK_INTERFACE); #else // not Avnet IoTConnect dx_azureConnect(&dx_config, NETWORK_INTERFACE, IOT_PLUG_AND_PLAY_MODEL_ID); diff --git a/avnet_sk_demo/main.h b/avnet_sk_demo/main.h index 7e8860e..7ca6f72 100644 --- a/avnet_sk_demo/main.h +++ b/avnet_sk_demo/main.h @@ -76,9 +76,6 @@ DX_USER_CONFIG dx_config; #ifdef IOT_HUB_APPLICATION static char msgBuffer[JSON_MESSAGE_BYTES] = {0}; #endif // IOT_HUB_APPLICATION -#ifdef USE_IOT_CONNECT -static char avtMsgBuffer[JSON_MESSAGE_BYTES + DX_AVNET_IOT_CONNECT_METADATA] = {0}; -#endif //USE_IOT_CONNECT #ifdef IOT_HUB_APPLICATION static DX_MESSAGE_PROPERTY *messageProperties[] = {&(DX_MESSAGE_PROPERTY){.key = "appid", .value = "SK-Demo"},