Logo
Developing with ZBOSS for Zigbee
In-home Display

Macros

#define ZB_SE_DEVICE_VER_IN_HOME_DISPLAY   0
 In-Home Display device version.
 
#define ZB_SE_DECLARE_IN_HOME_DISPLAY_CLUSTER_LIST(cluster_list_name, basic_attr_list, kec_attr_list, drlc_attr_list)
 Declare cluster list for In-Home Display device. More...
 
#define ZB_SE_DECLARE_IN_HOME_DISPLAY_EP(ep_name, ep_id, cluster_list)
 Declare endpoint for In-Home Display device. More...
 
#define ZB_SE_DECLARE_IN_HOME_DISPLAY_CTX(device_ctx_name, ep_name)   ZBOSS_DECLARE_DEVICE_CTX_1_EP(device_ctx_name, ep_name)
 Declares In-Home Display device context. More...
 

Detailed Description

The In-Home Display device will relay energy consumption data to the user by way of a graphical or text display. The display may or may not be an interactive device. At a minimum at least one of the following should be displayed: current energy usage, a history over selectable periods, pricing information, or text messages. As an interactive device, it can be used for returning simple messages for interpretation by the recipient (e.g. “Button A was pressed). The display may also show critical pricing information to advise the customer when peaks are due to occur so that they can take appropriate action.

Supported clusters
In-home Display Device has X clusters (see SE spec 1.4 subclauses 6.1, 6.3.3.1):
Server roles Client roles
ZCL Basic cluster SE Key Establishment Cluster
SE Key Establishment Cluster ZCL Metering Cluster (optional)
ZCL Keep Alive Cluster (optional)
SE Calendar cluster (optional)
ZCL Price cluster (optional)
ZCL Demand Response and Load Control (DRLC) cluster (optional)
SE Events cluster (optional)
ZCL Messaging cluster (optional)
SE Energy Management cluster (optional)
SE MDU Pairing cluster (optional)
SE Prepayment cluster (optional)
Example

Declare clusters
/**
* Declaring attributes for each cluster
*/
/* Basic cluster attributes */
ZB_ZCL_DECLARE_BASIC_ATTR_LIST(basic_attr_list, g_dev_ctx.basic_attrs);
/* Key Establishment cluster attributes */
ZB_ZCL_DECLARE_KEC_ATTR_LIST(kec_attr_list, g_dev_ctx.kec_attrs);
/* DRLC cluster attributes */
ZB_ZCL_DECLARE_DRLC_ATTR_LIST(drlc_attr_list, g_dev_ctx.drlc_attrs);
/* Declare cluster list for the device */
basic_attr_list,
kec_attr_list,
drlc_attr_list);
/* Declare endpoint */
ZB_SE_DECLARE_IN_HOME_DISPLAY_EP(ihd_dev_ep, IHD_DEV_ENDPOINT, ihd_dev_clusters);
/* Declare SE application's device context for single-endpoint device */
ZB_SE_DECLARE_IN_HOME_DISPLAY_CTX(ihd_dev_zcl_ctx, ihd_dev_ep);

Register device context
/* Register device ZCL context */
ZB_AF_REGISTER_DEVICE_CTX(&ihd_dev_zcl_ctx);
/* Register cluster commands handler for a specific endpoint */
ZB_AF_SET_ENDPOINT_HANDLER(IHD_DEV_ENDPOINT, ihd_dev_zcl_cmd_handler);

Command handler example
zb_uint8_t ihd_dev_zcl_cmd_handler(zb_uint8_t param)
{
zb_uint8_t cmd_processed = ZB_FALSE;
TRACE_MSG(TRACE_APP1, "> ihd_dev_zcl_cmd_handler param %hd", (FMT__H, param));
TRACE_MSG(TRACE_APP2, "f type %hd cluster_id 0x%x cmd_id %hd",
(FMT__H_D_H, cmd_info->is_common_command, cmd_info->cluster_id, cmd_info->cmd_id));
if (cmd_info->cluster_id == ZB_ZCL_CLUSTER_ID_METERING)
{
if (cmd_info->is_common_command &&
{
ihd_dev_read_metering_attrs(param, cmd_info);
zb_buf_free(param);
cmd_processed = ZB_TRUE;
}
else if (cmd_info->is_common_command &&
{
ihd_dev_disc_attr_resp_handler(param, cmd_info);
zb_buf_free(param);
cmd_processed = ZB_TRUE;
}
}
TRACE_MSG(TRACE_APP1, "< ihd_dev_zcl_cmd_handler %hd", (FMT__H, cmd_processed));
return cmd_processed;
}

Signal handler example
/** [SIGNAL_HANDLER_GET_SIGNAL] */
/* Application signal handler. Used for informing application about important ZBOSS
* events/states (device started first time/rebooted, key establishment completed etc).
* Application may ignore signals in which it is not interested. */
{
TRACE_MSG(TRACE_APP1, ">> zboss_signal_handler: param %hd signal %hd status %hd",
(FMT__H_H_H, param, sig, ZB_GET_APP_SIGNAL_STATUS(param)));
if (ZB_GET_APP_SIGNAL_STATUS(param) == 0)
{
switch (sig)
{
if (zb_buf_len(param) > sizeof(zb_zdo_app_signal_hdr_t))
{
se_app_production_config_t *prod_cfg =
ZB_ZDO_SIGNAL_GET_PARAMS(sg_p, se_app_production_config_t);
TRACE_MSG(TRACE_APP1, "Loading application production config", (FMT__0));
if (prod_cfg->version == SE_APP_PROD_CFG_CURRENT_VERSION)
{
zb_set_node_descriptor_manufacturer_code_req(prod_cfg->manuf_code, NULL);
}
}
break;
/** [SIGNAL_HANDLER_GET_SIGNAL] */
zboss_start_continue();
break;
/* wait button click to start commissioning */
#ifdef ZB_USE_BUTTONS
zb_button_register_handler(BUTTON_LEFT, 0, ihd_dev_left_button_handler);
zb_button_register_handler(BUTTON_RIGHT, 16, ihd_dev_right_button_handler);
#else
ihd_dev_left_button_handler(0);
#endif
break;
zb_se_indicate_commissioning_started();
break;
case ZB_SIGNAL_DEVICE_FIRST_START:
case ZB_SIGNAL_DEVICE_REBOOT:
TRACE_MSG(TRACE_APP1, "Device STARTED OK: first_start %hd",
(FMT__H, sig == ZB_SIGNAL_DEVICE_FIRST_START));
{
TRACE_MSG(TRACE_APP1, "unique TCLK: " TRACE_FORMAT_128, (FMT__B, TRACE_ARG_128(key)));
TRACE_MSG(TRACE_APP1, "NWK key: " TRACE_FORMAT_128, (FMT__B, TRACE_ARG_128(key)));
TRACE_MSG(TRACE_APP1, "TCLK by installcode: " TRACE_FORMAT_128, (FMT__B, TRACE_ARG_128(key)));
}
zb_se_indicate_default_start();
break;
/** [SIGNAL_HANDLER_CBKE_OK] */
TRACE_MSG(TRACE_APP1, "Key Establishment with Trust Center (CBKE) OK", (FMT__0));
#ifdef DEBUG_EXPOSE_KEYS
{
zb_uint16_t r_a_s = 0;
if (zb_se_debug_get_link_key(r_a_s, key) == RET_OK)
{
TRACE_MSG(TRACE_APP1, "CBKE OK TCLK key " TRACE_FORMAT_128,
(FMT__B, TRACE_ARG_128(key)));
/** [SIGNAL_HANDLER_TC_SIGNAL_CHILD_JOIN] */
/* Note: that code broadcasts your TCLK! Use it only for debug purposes! Never keep it in production mode! */
zb_debug_bcast_key(NULL, key);
}
{
TRACE_MSG(TRACE_APP1, "Current NWK key " TRACE_FORMAT_128,
(FMT__B, TRACE_ARG_128(key)));
/* Note: that code broadcasts your NWK key! Use it only for debug purposes! Never keep it in production mode! */
zb_debug_bcast_key(NULL, key);
}
}
#endif
break;
/** [SIGNAL_HANDLER_CBKE_OK] */
/** [SIGNAL_HANDLER_START_DISCOVERY] */
#if defined ZB_USE_BUTTONS
if (dev_sd_start_enabled == ZB_FALSE) {
break;
}
#endif
TRACE_MSG(TRACE_APP1, "Start Service Discovery", (FMT__0));
zb_se_service_discovery_start(IHD_DEV_ENDPOINT);
zb_se_indicate_service_discovery_started();
break;
/** [SIGNAL_HANDLER_START_DISCOVERY] */
/** [SIGNAL_HANDLER_DO_BIND] */
{
TRACE_MSG(TRACE_APP1, "can bind cluster 0x%x commodity_type %d remote_dev " TRACE_FORMAT_64,
(FMT__D_D_A, bind_params->cluster_id, bind_params->commodity_type,
TRACE_ARG_64(bind_params->device_addr)));
/** [SIGNAL_HANDLER_DO_BIND] */
/** [SIGNAL_HANDLER_BIND_DEV] */
{
#ifdef IHD_DEV_SUPPORT_MULTIPLE_COMMODITY
#endif
{
i = ihd_dev_add_to_list(bind_params->device_addr,
bind_params->cluster_id,
bind_params->endpoint);
if (i != 0xFF)
{
#ifdef IHD_DEV_SUPPORT_MULTIPLE_COMMODITY
g_dev_ctx.dev.lst[i].u.metering.device_type = bind_params->commodity_type;
#endif
if(g_dev_ctx.dev.lst[i].pending_cmd == IHD_DEV_NO_CMD)
{
g_dev_ctx.dev.lst[i].pending_cmd = IHD_DEV_METERING_DISCOVER_ATTRS;
ZB_SCHEDULE_APP_CALLBACK(ihd_dev_send_pending_cmd, i);
}
zb_se_service_discovery_bind_req(param, bind_params->device_addr, bind_params->endpoint);
param = 0;
}
}
}
else if (bind_params->cluster_id == ZB_ZCL_CLUSTER_ID_PRICE)
{
#ifdef IHD_DEV_SUPPORT_MULTIPLE_COMMODITY
#endif
{
i = ihd_dev_add_to_list(bind_params->device_addr,
bind_params->cluster_id,
bind_params->endpoint);
if (i != 0xFF)
{
#ifdef IHD_DEV_SUPPORT_MULTIPLE_COMMODITY
g_dev_ctx.dev.lst[i].u.price.commodity_type = bind_params->commodity_type;
#endif
if(g_dev_ctx.dev.lst[i].pending_cmd == IHD_DEV_NO_CMD)
{
g_dev_ctx.dev.lst[i].pending_cmd = IHD_DEV_PRICE_GET_CURRENT_PRICE;
ZB_SCHEDULE_APP_CALLBACK(ihd_dev_send_pending_cmd, i);
}
zb_se_service_discovery_bind_req(param, bind_params->device_addr, bind_params->endpoint);
param = 0;
}
}
}
else if (bind_params->cluster_id == ZB_ZCL_CLUSTER_ID_DRLC)
{
i = ihd_dev_add_to_list(bind_params->device_addr,
bind_params->cluster_id,
bind_params->endpoint);
if (i != 0xFF)
{
if(g_dev_ctx.dev.lst[i].pending_cmd == IHD_DEV_NO_CMD)
{
g_dev_ctx.dev.lst[i].pending_cmd = IHD_DEV_DRLC_GET_SCHEDULED_EVENTS;
ZB_SCHEDULE_APP_CALLBACK(ihd_dev_send_pending_cmd, i);
}
zb_se_service_discovery_bind_req(param, bind_params->device_addr, bind_params->endpoint);
param = 0;
}
}
else if (bind_params->cluster_id == ZB_ZCL_CLUSTER_ID_MESSAGING)
{
i = ihd_dev_add_to_list(bind_params->device_addr,
bind_params->cluster_id,
bind_params->endpoint);
if (i != 0xFF)
{
if(g_dev_ctx.dev.lst[i].pending_cmd == IHD_DEV_NO_CMD)
{
g_dev_ctx.dev.lst[i].pending_cmd = IHD_DEV_MESSAGING_GET_LAST_MESSAGE;
ZB_SCHEDULE_APP_CALLBACK(ihd_dev_send_pending_cmd, i);
}
zb_se_service_discovery_bind_req(param, bind_params->device_addr, bind_params->endpoint);
param = 0;
}
}
#if IHD_ENABLE_GET_CALENDAR
else if (bind_params->cluster_id == ZB_ZCL_CLUSTER_ID_CALENDAR)
{
TRACE_MSG(TRACE_APP1, "Send bind request to Calendar Server", (FMT__0));
i = ihd_dev_add_to_list(bind_params->device_addr,
bind_params->cluster_id,
bind_params->endpoint);
if (i != 0xFF)
{
if(g_dev_ctx.dev.lst[i].pending_cmd == IHD_DEV_NO_CMD)
{
g_dev_ctx.dev.lst[i].pending_cmd = IHD_DEV_CALENDAR_GET_CALENDAR;
ZB_SCHEDULE_APP_CALLBACK(ihd_dev_send_pending_cmd, i);
}
zb_se_service_discovery_bind_req(param, bind_params->device_addr, bind_params->endpoint);
param = 0;
}
}
#endif
{
i = ihd_dev_add_to_list(bind_params->device_addr,
bind_params->cluster_id,
bind_params->endpoint);
if (i != 0xFF)
{
TRACE_MSG(TRACE_APP1, "Send bind request to Energy Management cluster", (FMT__0));
if(g_dev_ctx.dev.lst[i].pending_cmd == IHD_DEV_NO_CMD)
{
g_dev_ctx.dev.lst[i].pending_cmd = IHD_DEV_ENERGY_MANAGEMENT_SEND_MANAGE_EVENT;
ZB_SCHEDULE_APP_CALLBACK(ihd_dev_send_pending_cmd, i);
}
zb_se_service_discovery_bind_req(param, bind_params->device_addr, bind_params->endpoint);
param = 0;
}
}
}
break;
/** [SIGNAL_HANDLER_BIND_DEV] */
/** [SIGNAL_HANDLER_BIND_OK] */
{
TRACE_MSG(TRACE_APP1, "Bind dev 0x%x OK", (FMT__D, *addr));
break;
}
/** [SIGNAL_HANDLER_BIND_OK] */
/** [SIGNAL_HANDLER_DISCOVERY_OK] */
TRACE_MSG(TRACE_APP1, "Service Discovery OK", (FMT__0));
zb_se_indicate_commissioning_stopped();
break;
/** [SIGNAL_HANDLER_DISCOVERY_OK] */
/** [SIGNAL_HANDLER_DISCOVERY_FAILED] */
TRACE_MSG(TRACE_APP1, "Service Discovery failed", (FMT__0));
zb_se_indicate_commissioning_fail(0, /* erase nvram */
0); /* reboot */
break;
/** [SIGNAL_HANDLER_DISCOVERY_FAILED] */
/**[SIGNAL_APS_KEY_READY] */
/* NOTE: Place here Energy Management cluster call, because during handling
* SIGNAL_HANDLER_DO_BIND for Energy Management cluster IHD don't
* receive Transport key between itself and Energy Management cluster
*/
{
TRACE_MSG(TRACE_APP1, "Partner link key established, remote device addr: " TRACE_FORMAT_64,
(FMT__A, TRACE_ARG_64(*remote_device_addr)));
/**[SIGNAL_APS_KEY_READY] */
/**[SIGNAL_APS_KEY_READY_DEV] */
ihd_dev_aps_key_established(*remote_device_addr);
}
break;
/**[SIGNAL_APS_KEY_READY_DEV] */
default:
break;
}
}
{
TRACE_MSG(TRACE_APP1, "Production config is not present or invalid", (FMT__0));
}
else
{
TRACE_MSG(TRACE_ERROR, "Device started FAILED status %d", (FMT__D, ZB_GET_APP_SIGNAL_STATUS(param)));
/* if (ZB_GET_APP_SIGNAL_STATUS(param) == (zb_uint16_t)RET_CONNECTION_LOST) */
/* TODO: Debug commissioning after error. Anyway, now let's reboot */
zb_se_indicate_commissioning_fail(0, /* erase nvram */
1); /* reboot */
}
SE_APP_AUX_SIGNAL_HANDLER(param);
if (param)
{
zb_buf_free(param);
}
TRACE_MSG(TRACE_APP1, "<< zboss_signal_handler", (FMT__0));
}

Macro Definition Documentation

§ ZB_SE_DECLARE_IN_HOME_DISPLAY_CLUSTER_LIST

#define ZB_SE_DECLARE_IN_HOME_DISPLAY_CLUSTER_LIST (   cluster_list_name,
  basic_attr_list,
  kec_attr_list,
  drlc_attr_list 
)

Declare cluster list for In-Home Display device.

Parameters
cluster_list_name- cluster list variable name
basic_attr_list- attribute list for Basic cluster
kec_attr_list- attribute list for Key Establishment cluster
drlc_attr_list- attribute list for DRLC cluster

§ ZB_SE_DECLARE_IN_HOME_DISPLAY_CTX

#define ZB_SE_DECLARE_IN_HOME_DISPLAY_CTX (   device_ctx_name,
  ep_name 
)    ZBOSS_DECLARE_DEVICE_CTX_1_EP(device_ctx_name, ep_name)

Declares In-Home Display device context.

Parameters
device_ctx_name- device context variable name.
ep_name- endpoint variable name.

§ ZB_SE_DECLARE_IN_HOME_DISPLAY_EP

#define ZB_SE_DECLARE_IN_HOME_DISPLAY_EP (   ep_name,
  ep_id,
  cluster_list 
)
Value:
ZB_ZCL_DECLARE_IN_HOME_DISPLAY_SIMPLE_DESC(ep_name, \
ep_id, \
ZB_SE_IN_HOME_DISPLAY_IN_CLUSTER_NUM, \
ZB_SE_IN_HOME_DISPLAY_OUT_CLUSTER_NUM); \
ZB_AF_DECLARE_ENDPOINT_DESC(ep_name, \
ep_id, \
0, \
NULL, \
ZB_ZCL_ARRAY_SIZE(cluster_list, zb_zcl_cluster_desc_t), \
cluster_list, \
(zb_af_simple_desc_1_1_t*)&simple_desc_##ep_name, \
ZB_SE_IN_HOME_DISPLAY_REPORT_ATTR_COUNT, NULL, \
0, NULL)
ZCL cluster description.
Definition: zb_zcl_common.h:129
#define ZB_AF_SE_PROFILE_ID
Definition: zboss_api_af.h:297

Declare endpoint for In-Home Display device.

Parameters
ep_name- endpoint variable name
ep_id- endpoint ID
cluster_list- endpoint cluster list