Revision as of 08:08, 16 December 2021 by Registered User

1. Introduction

Link Keys are used to encrypt/decrypt the communication between each two devices. The network security depends on the robustness of the link keys. Default global preconfigured link key ZigBee 09 is generally used in home automation applications. The problem is that the same link key is used for all the nodes, and this is a security leak. For maximizing security, ZigBee 3.0 provides Install Code process to create preconfigured link keys that are unique between the trust center and each end device node.

2. Install Code Format

Install code is made up of 6,8, 12 or 16 bytes hexadecimal number with 2 bytes CRC. The CRC should be appended to the installation code in little endian format. ZigBee 3.0 Base Device Behavior Specification requires the use of 16-byte Install Code.

3. Trust center behavior

The trust center should decide whether a joining node shall use the default link key or an Install Code Link Key depending on the value of bdbJoinUsesInstallCodeKey.
If bdbJoinUsesInstallCodeKey is FALSE, the Trust Center permits a node to join its network without having a corresponding install code link key. If bdbJoinUsesInstallCodeKey is TRUE, the Trust Center only permits a node to join its network if a corresponding install code link key associated with the node has been preinstalled before the node joins. The Trust Center shall add an entry into its Link Key Table based on ZED EUI64 address.

4. Trust Center (ZC) Install code process

Form ZigBee network using whatever Link key:

/* Attempt to join a ZigBee network */
ZbStartupConfigGetProDefaults(&config);

/* Set the centralized network */
APP_DBG("Network config : APP_STARTUP_CENTRALIZED_COORDINATOR");
config.startupControl = ZbStartTypeForm;

/* Using the default HA preconfigured Link Key */
memcpy(config.security.preconfiguredLinkKey, sec_key_ha, ZB_SEC_KEYSIZE);

config.channelList.count = 1;
config.channelList.list[0].page = 0;
config.channelList.list[0].channelMask = 1 << CHANNEL; /*Channel in use */

/* Using ZbStartupWait (blocking) */
status = ZbStartupWait(zigbee_app_info.zb, &config);

Enable Install Code:

uint32_t tcPolicy = 0;
ZbApsGet(zigbee_app_info.zb, ZB_APS_IB_ID_TRUST_CENTER_POLICY, &tcPolicy, sizeof(tcPolicy));
tcPolicy |= (ZB_APSME_POLICY_IC_SUPPORTED | ZB_APSME_POLICY_TCLK_UPDATE_REQUIRED);
ZbApsSet(zigbee_app_info.zb, ZB_APS_IB_ID_TRUST_CENTER_POLICY, &tcPolicy, sizeof(tcPolicy));

Add dedicated preconfigured Link Key for ZED with EUI64 address ieeeAddr:

struct ZbApsmeAddKeyReqT addKeyReq;
struct ZbApsmeAddKeyConfT addKeyConf;
memset(&addKeyReq, 0, sizeof(addKeyReq));

addKeyReq.keyType = ZB_SEC_KEYTYPE_TC_LINK;
addKeyReq.keySeqNumber = 0;
addKeyReq.partnerAddr = ieeeAddr;

memcpy(addKeyReq.key, ZED_LinkKey, ZB_SEC_KEYSIZE);
ZbApsmeAddKeyReq(cli_p->zb, &addKeyReq, &addKeyConf);

5. End Device (ZED) Install code process

Configure End Device with same preconfigured Link Key:

/* Attempt to join a zigbee network */
ZbStartupConfigGetProDefaults(&config);

/* Set the centralized network */
APP_DBG("Network config : APP_STARTUP_CENTRALIZED_ROUTER");
config.startupControl = ZbStartTypeJoin;

/* Using the same preconfigured Link Key as the one configured on Trust Center */
memcpy(config.security.preconfiguredLinkKey, ZED_LinkKey, ZB_SEC_KEYSIZE);
config.channelList.count = 1;
config.channelList.list[0].page = 0;
config.channelList.list[0].channelMask = 1 << CHANNEL; /*Channel in use */

/* Using ZbStartupWait (blocking) */
status = ZbStartupWait(zigbee_app_info.zb, &config);
Node Install Code Steps