bool emberAfPreZDOMessageReceivedCallback(EmberNodeId sender, EmberApsFrame* apsFrame, uint8_t* message, uint16_t length) { if (!enabled) { return false; } if (apsFrame->clusterId == END_DEVICE_ANNOUNCE) { EmberEUI64 tempEui64; MEMMOVE(tempEui64, &(message[DEVICE_ANNOUNCE_EUI64_OFFSET]), EUI64_SIZE); // If the device already exists, this call won't overwrite it and will // leave its status alone. Maybe it rejoined and we already know about, // in which case we won't bother re-interrogating it. const EmberAfDeviceInfo* device = emberAfPluginDeviceDatabaseAdd(tempEui64, message[DEVICE_ANNOUNCE_CAPABILITIES_OFFSET]); if (device == NULL) { emberAfCorePrint("Error: %p failed to add device to database: ", PLUGIN_NAME); emberAfPrintLittleEndianEui64(tempEui64); emberAfCorePrintln(""); } else { if (device->status == EMBER_AF_DEVICE_DISCOVERY_STATUS_NEW) { emberAfCorePrint("%p added device to database: ", PLUGIN_NAME); emberAfPrintLittleEndianEui64(tempEui64); emberAfCorePrintln(", capabilities: 0x%X", device->capabilities); scheduleEvent(WITH_DELAY); } } return true; } return false; }
bool emberAfPluginDeviceDatabaseSetEndpoints(const EmberEUI64 eui64, const uint8_t* endpointList, uint8_t endpointCount) { EmberAfDeviceInfo* device = findDeviceByEui64(eui64); if (device == NULL) { emberAfCorePrint("Error: %p cannot add endpoints. No such device in database: "); emberAfPrintLittleEndianEui64(eui64); emberAfCorePrintln(""); return false; } // Clear all existing endpoints so there is no leftover clusters or endpoints. MEMSET(device->endpoints, 0xFF, sizeof(EmberAfEndpointInfoStruct) * EMBER_AF_MAX_ENDPOINTS_PER_DEVICE); device->endpointCount = (endpointCount < EMBER_AF_MAX_ENDPOINTS_PER_DEVICE ? endpointCount : EMBER_AF_MAX_ENDPOINTS_PER_DEVICE); uint8_t i; for (i = 0; i < device->endpointCount; i++) { device->endpoints[i].endpoint = *endpointList; device->endpoints[i].clusterCount = 0; endpointList++; } return true; }
/*! Callback for IEEE address Request */ static void ProcessEUI64Discovery(const EmberAfServiceDiscoveryResult *result) { if (emberAfHaveDiscoveryResponseStatus(result->status)) { MatchDescriptorReq_t *in_dev = GetTopInDeviceDescriptor(); assert(in_dev != NULL); SetInConnEUI64Address((const uint8_t *)result->responseData); emberAfDebugPrint("DEBUG: EUI64 "); emberAfPrintLittleEndianEui64(in_dev->source_eui64); emberAfDebugPrintln(""); SetNextEvent(SC_EZEV_BIND); } emberEventControlSetActive(StateMachineEvent); }
const EmberAfDeviceInfo* emberAfPluginDeviceDatabaseAddDeviceWithAllInfo(const EmberAfDeviceInfo* newDevice) { if (NULL != findDeviceByEui64(newDevice->eui64)) { emberAfCorePrint("Error: %p cannot add device that already exists: ", PLUGIN_NAME); emberAfPrintLittleEndianEui64(newDevice->eui64); emberAfCorePrintln(""); return NULL; } EmberEUI64 nullEui64; MEMSET(nullEui64, 0xFF, EUI64_SIZE); EmberAfDeviceInfo* device = findDeviceByEui64(nullEui64); if (device != NULL) { MEMMOVE(device, newDevice, sizeof(EmberAfDeviceInfo)); emberAfPluginDeviceDatabaseDiscoveryCompleteCallback(device); } return device; }
void emberAfPluginDeviceQueryServiceMyEventHandler(void) { emberEventControlSetInactive(emberAfPluginDeviceQueryServiceMyEventControl); debugPrintln("%p event", PLUGIN_NAME); const EmberAfDeviceInfo* device; if (emberAfMemoryByteCompare(currentEui64, EUI64_SIZE, 0xFF)) { debugPrintln("%p no current device being queried, looking in database for one.", PLUGIN_NAME); device = emberAfPluginDeviceDatabaseFindDeviceByStatus(EMBER_AF_DEVICE_DISCOVERY_STATUS_NEW | EMBER_AF_DEVICE_DISCOVERY_STATUS_FIND_ENDPOINTS | EMBER_AF_DEVICE_DISCOVERY_STATUS_FIND_CLUSTERS); if (device != NULL) { debugPrintln("%p found device with status (0x%X): %p", PLUGIN_NAME, device->status, emberAfPluginDeviceDatabaseGetStatusString(device->status)); if ((device->capabilities & RECEIVER_ON_WHEN_IDLE) == 0) { emberAfPluginDeviceDatabaseSetStatus(device->eui64, EMBER_AF_DEVICE_DISCOVERY_STATUS_DONE); debugPrintln("%p ignoring sleepy device."); scheduleEvent(RIGHT_NOW); return; } else { MEMMOVE(currentEui64, device->eui64, EUI64_SIZE); } } } else { device = emberAfPluginDeviceDatabaseFindDeviceByEui64(currentEui64); if (device == NULL) { emberAfCorePrint("Error: %p the current EUI64 does not correspond to any known device: ", PLUGIN_NAME); emberAfPrintLittleEndianEui64(currentEui64); emberAfCorePrintln(""); clearCurrentDevice(); scheduleEvent(WITH_DELAY); return; } } if (device == NULL) { clearCurrentDevice(); if (emberAfPluginDeviceDatabaseClearAllFailedDiscoveryStatus(EMBER_AF_PLUGIN_DEVICE_QUERY_SERVICE_MAX_FAILURES)) { emberAfCorePrintln("%p Retrying failed discoveries.", PLUGIN_NAME); scheduleEvent(WITH_DELAY); } else { emberAfCorePrintln("%p All known devices discovered.", PLUGIN_NAME); } return; } // Although we could consult our local tables for addresses, we perform a broadcast // lookup here to insure that we have a current source route back to the destination. // The target of the discovery will unicast the result, along with a route record. if (currentNodeId == EMBER_NULL_NODE_ID) { debugPrint("%p initiating node ID discovery for: ", PLUGIN_NAME); debugPrintEui64(currentEui64); debugPrintln(""); EmberStatus status = emberAfFindNodeId(currentEui64, serviceDiscoveryCallback); if (status != EMBER_SUCCESS) { emberAfCorePrintln("%p failed to initiate node ID discovery.", PLUGIN_NAME); noteFailedDiscovery(device); scheduleEvent(WITH_DELAY); } // Else // Don't schedule event, since service discovery callback returns the results. return; } switch (device->status) { case EMBER_AF_DEVICE_DISCOVERY_STATUS_NEW: case EMBER_AF_DEVICE_DISCOVERY_STATUS_FIND_ENDPOINTS: sendActiveEndpointRequest(device); break; case EMBER_AF_DEVICE_DISCOVERY_STATUS_FIND_CLUSTERS: sendSimpleDescriptorRequest(device); break; default: break; } }
static void serviceDiscoveryCallback(const EmberAfServiceDiscoveryResult* result) { debugPrintln("%p serviceDiscoveryCallback()", PLUGIN_NAME); emberEventControlSetInactive(emberAfPluginDeviceQueryServiceMyEventControl); if (!enabled) { return; } const EmberAfDeviceInfo* device = emberAfPluginDeviceDatabaseFindDeviceByEui64(currentEui64); if (device == NULL) { emberAfCorePrint("Error: %p could not find device in database with EUI64: ", PLUGIN_NAME); emberAfPrintLittleEndianEui64(currentEui64); emberAfCorePrintln(""); clearCurrentDevice(); scheduleEvent(WITH_DELAY); return; } if (!emberAfHaveDiscoveryResponseStatus(result->status)) { emberAfCorePrintln("Error: %p service discovery returned no results.", PLUGIN_NAME); noteFailedDiscovery(device); scheduleEvent(WITH_DELAY); return; } else if (result->zdoRequestClusterId == NETWORK_ADDRESS_REQUEST) { currentNodeId = result->matchAddress; emberAfPluginDeviceDatabaseSetStatus(device->eui64, EMBER_AF_DEVICE_DISCOVERY_STATUS_FIND_ENDPOINTS); scheduleEvent(RIGHT_NOW); } else if (result->zdoRequestClusterId == ACTIVE_ENDPOINTS_REQUEST) { const EmberAfEndpointList* listStruct = (const EmberAfEndpointList*)(result->responseData); debugPrintln("%p found %d active endpoints.", PLUGIN_NAME, listStruct->count); if (!emberAfPluginDeviceDatabaseSetEndpoints(device->eui64, listStruct->list, listStruct->count)) { emberAfCorePrint("Error: %p failed to set endpoints in device database for:", PLUGIN_NAME); emberAfPrintLittleEndianEui64(device->eui64); emberAfCorePrintln(""); noteFailedDiscovery(device); scheduleEvent(WITH_DELAY); } else { currentEndpointIndex = 0; emberAfPluginDeviceDatabaseSetStatus(device->eui64, EMBER_AF_DEVICE_DISCOVERY_STATUS_FIND_CLUSTERS); scheduleEvent(RIGHT_NOW); } } else if (result->zdoRequestClusterId == SIMPLE_DESCRIPTOR_REQUEST) { const EmberAfClusterList* clusterInfo = (const EmberAfClusterList*)result->responseData; debugPrintln("%p found %d server clusters and %d client clusters on EP %d", PLUGIN_NAME, clusterInfo->inClusterCount, clusterInfo->outClusterCount, clusterInfo->endpoint); if (!emberAfPluginDeviceDatabaseSetClustersForEndpoint(device->eui64, clusterInfo)) { emberAfCorePrintln("Error: %p failed to set clusters for device.", PLUGIN_NAME); noteFailedDiscovery(device); scheduleEvent(WITH_DELAY); } else { currentEndpointIndex++; scheduleEvent(RIGHT_NOW); } } }