diff --git a/CHANGELOG.md b/CHANGELOG.md index ea63c55d..cd51fc43 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,9 +4,16 @@ All notable changes to this project will be documented in this file. Dates are d Generated by [`auto-changelog`](https://github.com/CookPete/auto-changelog). - +#### [1.1.7](https://github.com/rdkcentral/control/compare/1.1.6...1.1.7) + +> 4 December 2025 + +- RDKEMW-11159: new_certselector_type [`#157`](https://github.com/rdkcentral/control/pull/157) +- RDKEMW-10425: Automation Logging [`#144`](https://github.com/rdkcentral/control/pull/144) +- RDKEMW-9600: FIRST_PACKET_TIMEOUTs [`#135`](https://github.com/rdkcentral/control/pull/135) + #### [1.1.6](https://github.com/rdkcentral/control/compare/1.1.5...1.1.6) > 19 November 2025 diff --git a/src/auth/ctrlm_auth_certificate.cpp b/src/auth/ctrlm_auth_certificate.cpp index 63ff900c..63ae514e 100644 --- a/src/auth/ctrlm_auth_certificate.cpp +++ b/src/auth/ctrlm_auth_certificate.cpp @@ -42,7 +42,7 @@ ctrlm_auth_certificate_t::ctrlm_auth_certificate_t() { char *cert_path = NULL; char *cert_password = NULL; - rdkcertselector_h cert_selector = rdkcertselector_new( NULL, NULL, "MTLS" ); + rdkcertselector_h cert_selector = rdkcertselector_new( NULL, NULL, "FBK_MTLS" ); if(cert_selector == NULL){ XLOGD_TELEMETRY("cert selector init failed"); diff --git a/src/ble/ctrlm_ble_controller.cpp b/src/ble/ctrlm_ble_controller.cpp index d8886150..d86650db 100644 --- a/src/ble/ctrlm_ble_controller.cpp +++ b/src/ble/ctrlm_ble_controller.cpp @@ -615,13 +615,13 @@ void ctrlm_obj_controller_ble_t::print_status() { XLOGD_INFO("Model : %s", model_->to_string().c_str()); XLOGD_INFO("MAC Address : %s", ieee_address_->to_string().c_str()); XLOGD_INFO("Device Minor ID : %d", device_minor_id_); - XLOGD_INFO("Battery Level : %u%%", get_battery_percent()); + XLOGD_AUTOMATION_INFO("Battery Level : %u%%", get_battery_percent()); XLOGD_INFO("HW Revision : %s", hw_revision_->to_string().c_str()); XLOGD_INFO("FW Revision : %s", fw_revision_->to_string().c_str()); - XLOGD_INFO("SW Revision : %s", sw_revision_->to_string().c_str()); + XLOGD_AUTOMATION_INFO("SW Revision : %s", sw_revision_->to_string().c_str()); XLOGD_INFO("Serial Number : %s", serial_number_->to_string().c_str()); XLOGD_INFO(""); - XLOGD_INFO("Connected : %s", (connected_==true) ? "true" : "false"); + XLOGD_AUTOMATION_INFO("Connected : %s", (connected_==true) ? "true" : "false"); XLOGD_INFO("Last Activity Time : %s", ctrlm_utils_time_as_string(this->last_activity_time_get()).c_str()); XLOGD_INFO("Bound Time : %s", ctrlm_utils_time_as_string(this->time_binding_get()).c_str()); XLOGD_INFO(""); diff --git a/src/ble/ctrlm_ble_network.cpp b/src/ble/ctrlm_ble_network.cpp index dca4c78f..8965b71a 100644 --- a/src/ble/ctrlm_ble_network.cpp +++ b/src/ble/ctrlm_ble_network.cpp @@ -525,7 +525,6 @@ void ctrlm_obj_network_ble_t::req_process_voice_session_begin(void *data, int si // only support ADPCM from ble-rcu component ctrlm_hal_ble_VoiceEncoding_t encoding = CTRLM_HAL_BLE_ENCODING_ADPCM; - ctrlm_hal_ble_VoiceStreamEnd_t streamEnd = CTRLM_HAL_BLE_VOICE_STREAM_END_ON_KEY_UP; ctrlm_voice_format_t voice_format = { .type = CTRLM_VOICE_FORMAT_INVALID }; @@ -543,18 +542,21 @@ void ctrlm_obj_network_ble_t::req_process_voice_session_begin(void *data, int si audio_format.getHeaderInfoAdpcm(adpcm_frame->offset_step_size_index, adpcm_frame->offset_predicted_sample_lsb, adpcm_frame->offset_predicted_sample_msb, adpcm_frame->offset_sequence_value, adpcm_frame->shift_sequence_value, adpcm_frame->sequence_value_min, adpcm_frame->sequence_value_max); pressAndHoldSupport = audio_format.getPressAndHoldSupport(); - if(!pressAndHoldSupport) { - streamEnd = CTRLM_HAL_BLE_VOICE_STREAM_END_ON_AUDIO_DURATION; - } controllers_[controller_id]->setPressAndHoldSupport(pressAndHoldSupport); } } + ctrlm_voice_start_audio_params_t audio_start_params; + audio_start_params.m_controller_id = controller_id; + audio_start_params.m_fd = -1; + audio_start_params.m_started = false; + auto audio_start_cb = std::bind(&ctrlm_obj_network_ble_t::start_controller_audio_streaming, this, std::placeholders::_1); + voice_status = ctrlm_get_voice_obj()->voice_session_req(network_id_get(), controller_id, device, voice_format, NULL, controllers_[controller_id]->get_model().c_str(), controllers_[controller_id]->get_sw_revision().to_string().c_str(), controllers_[controller_id]->get_hw_revision().to_string().c_str(), 0.0, - false, NULL, NULL, NULL, true, pressAndHoldSupport); + false, NULL, NULL, NULL, true, pressAndHoldSupport, audio_start_cb, &audio_start_params); if (!controllers_[controller_id]->get_capabilities().has_capability(ctrlm_controller_capabilities_t::capability::PAR) && (VOICE_SESSION_RESPONSE_AVAILABLE_PAR_VOICE == voice_status)) { XLOGD_WARN("PAR voice is enabled but not supported by BLE controller treating as normal voice session"); voice_status = VOICE_SESSION_RESPONSE_AVAILABLE; @@ -562,24 +564,21 @@ void ctrlm_obj_network_ble_t::req_process_voice_session_begin(void *data, int si if (VOICE_SESSION_RESPONSE_AVAILABLE != voice_status) { XLOGD_TELEMETRY("Failed opening voice session in ctrlm_voice_t, error = <%d>", voice_status); } else { + int fd = -1; bool success = false; - if (ble_rcu_interface_) { - int fd = -1; - - if (!ble_rcu_interface_->startAudioStreaming(ieee_address, encoding, streamEnd, fd)) { - XLOGD_ERROR("failed to start audio streaming on remote"); - } else { + if (!audio_start_params.m_started) { // voice session req did not need to start audio + start_controller_audio_streaming(&audio_start_params); + } + fd = audio_start_params.m_fd; - if (fd < 0) { - XLOGD_ERROR("Voice streaming pipe invalid (fd = <%d>), aborting voice session", fd); - success = false; - } else { - XLOGD_INFO("Acquired voice streaming pipe fd = <%d>, sending to voice engine", fd); - //Send the fd acquired from bluez to the voice engine - success = ctrlm_get_voice_obj()->voice_session_data(network_id_get(), controller_id, fd); - } - } + if (fd < 0) { + XLOGD_ERROR("Voice streaming pipe invalid (fd = <%d>), aborting voice session", fd); + success = false; + } else { + XLOGD_AUTOMATION_INFO("Acquired voice streaming pipe fd = <%d>, sending to voice engine", fd); + //Send the fd acquired from bluez to the voice engine + success = ctrlm_get_voice_obj()->voice_session_data(network_id_get(), controller_id, fd); } if (false == success) { @@ -1826,7 +1825,7 @@ void ctrlm_obj_network_ble_t::ind_process_rcu_status(void *data, int size) { print_status = false; break; case CTRLM_HAL_BLE_PROPERTY_IS_UPGRADING: - XLOGD_INFO("Controller <%s> firmware upgrading = %s", controller->ieee_address_get().to_string().c_str(), dqm->rcu_data.is_upgrading ? "TRUE" : "FALSE"); + XLOGD_AUTOMATION_INFO("Controller <%s> firmware upgrading = %s", controller->ieee_address_get().to_string().c_str(), dqm->rcu_data.is_upgrading ? "TRUE" : "FALSE"); upgrade_in_progress_ = dqm->rcu_data.is_upgrading; if (!dqm->rcu_data.is_upgrading) { // If we get FALSE here, make sure the controller upgrade progress flag is cleared. But we don't want to set the controller progress @@ -1837,7 +1836,7 @@ void ctrlm_obj_network_ble_t::ind_process_rcu_status(void *data, int size) { print_status = false; break; case CTRLM_HAL_BLE_PROPERTY_UPGRADE_PROGRESS: - XLOGD_INFO("Controller <%s> firmware upgrade %d%% complete...", controller->ieee_address_get().to_string().c_str(), dqm->rcu_data.upgrade_progress); + XLOGD_AUTOMATION_INFO("Controller <%s> firmware upgrade %d%% complete...", controller->ieee_address_get().to_string().c_str(), dqm->rcu_data.upgrade_progress); // From a controller perspective, we cannot use the CTRLM_HAL_BLE_PROPERTY_IS_UPGRADING flag above to determine if its actively upgrading. // Instead, its more accurate to use the progress percentage to determine if the remote is actively receiving firmware packets. controller->setUpgradeInProgress(dqm->rcu_data.upgrade_progress > 0 && dqm->rcu_data.upgrade_progress < 100); @@ -1850,7 +1849,7 @@ void ctrlm_obj_network_ble_t::ind_process_rcu_status(void *data, int size) { print_status = false; break; case CTRLM_HAL_BLE_PROPERTY_UPGRADE_ERROR: - XLOGD_ERROR("Controller <%s> firmware upgrade FAILED with error <%s>.", controller->ieee_address_get().to_string().c_str(), dqm->rcu_data.upgrade_error); + XLOGD_AUTOMATION_ERROR("Controller <%s> firmware upgrade FAILED with error <%s>.", controller->ieee_address_get().to_string().c_str(), dqm->rcu_data.upgrade_error); report_status = false; print_status = false; controller->set_upgrade_error(dqm->rcu_data.upgrade_error); @@ -1883,7 +1882,7 @@ void ctrlm_obj_network_ble_t::ind_process_rcu_status(void *data, int size) { controller->ota_failure_cnt_incr(); break; case CTRLM_HAL_BLE_PROPERTY_UNPAIR_REASON: - XLOGD_INFO("Controller <%s> notified reason for unpairing = <%s>", controller->ieee_address_get().to_string().c_str(), ctrlm_ble_unpair_reason_str(dqm->rcu_data.unpair_reason)); + XLOGD_AUTOMATION_INFO("Controller <%s> notified reason for unpairing = <%s>", controller->ieee_address_get().to_string().c_str(), ctrlm_ble_unpair_reason_str(dqm->rcu_data.unpair_reason)); last_rcu_unpair_metrics_.write_rcu_unpair_event(controller->ieee_address_get().get_value(), string(ctrlm_ble_unpair_reason_str(dqm->rcu_data.unpair_reason))); report_status = false; print_status = false; @@ -1898,7 +1897,7 @@ void ctrlm_obj_network_ble_t::ind_process_rcu_status(void *data, int size) { } break; case CTRLM_HAL_BLE_PROPERTY_REBOOT_REASON: - XLOGD_TELEMETRY("Controller <%s> notified reason for rebooting = <%s%s%s%s>", + XLOGD_AUTOMATION_TELEMETRY("Controller <%s> notified reason for rebooting = <%s%s%s%s>", controller->ieee_address_get().to_string().c_str(), ctrlm_ble_reboot_reason_str(dqm->rcu_data.reboot_reason), dqm->rcu_data.reboot_reason == CTRLM_BLE_RCU_REBOOT_REASON_ASSERT ? " - \"" : "", @@ -2206,7 +2205,7 @@ void ctrlm_obj_network_ble_t::ind_process_keypress(void *data, int size) { controller->setVoiceStartTime(keyDownTime); XLOGD_INFO("------------------------------------------------------------------------"); - XLOGD_INFO("CODE_VOICE_KEY button PRESSED event for device: %s", controller->ieee_address_get().to_string().c_str()); + XLOGD_AUTOMATION_INFO("CODE_VOICE_KEY button PRESSED event for device: %s", controller->ieee_address_get().to_string().c_str()); XLOGD_INFO("------------------------------------------------------------------------"); ctrlm_voice_iarm_call_voice_session_t v_params; @@ -2256,7 +2255,7 @@ void ctrlm_obj_network_ble_t::ind_process_keypress(void *data, int size) { if (controller->isVoiceKey(dqm->event.code)) { if(!controller->getPressAndHoldSupport()) { // if the voice session is "Press and Release" then don't end session on voice key up event XLOGD_INFO("------------------------------------------------------------------------"); - XLOGD_INFO("CODE_VOICE_KEY button RELEASED event for device: %s (ignored for PAR session)", controller->ieee_address_get().to_string().c_str()); + XLOGD_AUTOMATION_INFO("CODE_VOICE_KEY button RELEASED event for device: %s (ignored for PAR session)", controller->ieee_address_get().to_string().c_str()); XLOGD_INFO("------------------------------------------------------------------------"); } else { rdkx_timestamp_t keyUpTime, keyUpTimeLocal, voiceStartTimeLocal, firstAudioDataTime; @@ -2291,11 +2290,11 @@ void ctrlm_obj_network_ble_t::ind_process_keypress(void *data, int size) { } XLOGD_INFO("------------------------------------------------------------------------"); - XLOGD_INFO("CODE_VOICE_KEY button RELEASED event for device: %s duration <%lld ms> start lag <%lld ms>", controller->ieee_address_get().to_string().c_str(), audioDurationKeys, startAudioLag); + XLOGD_AUTOMATION_INFO("CODE_VOICE_KEY button RELEASED event for device: %s duration <%lld ms> start lag <%lld ms>", controller->ieee_address_get().to_string().c_str(), audioDurationKeys, startAudioLag); XLOGD_INFO("------------------------------------------------------------------------"); } else { XLOGD_INFO("------------------------------------------------------------------------"); - XLOGD_INFO("CODE_VOICE_KEY button RELEASED event for device: %s duration <%lld ms>", controller->ieee_address_get().to_string().c_str(), audioDurationKeys); + XLOGD_AUTOMATION_INFO("CODE_VOICE_KEY button RELEASED event for device: %s duration <%lld ms>", controller->ieee_address_get().to_string().c_str(), audioDurationKeys); XLOGD_INFO("------------------------------------------------------------------------"); } @@ -2498,7 +2497,7 @@ void ctrlm_obj_network_ble_t::printStatus() { it->second->print_status(); } XLOGD_INFO("BLE Network Status: <%s>", ctrlm_rf_pair_state_str(state_)); - XLOGD_TELEMETRY("IR Programming Status: <%s>", ctrlm_ir_state_str(ir_state_)); + XLOGD_AUTOMATION_TELEMETRY("IR Programming Status: <%s>", ctrlm_ir_state_str(ir_state_)); XLOGD_WARN("<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<"); } @@ -2616,3 +2615,43 @@ ctrlm_controller_id_t ctrlm_obj_network_ble_t::find_controller_from_upgrade_sess } return id; } + +void ctrlm_obj_network_ble_t::start_controller_audio_streaming(ctrlm_voice_start_audio_params_t *params) { + THREAD_ID_VALIDATE(); + int fd = -1; + ctrlm_controller_id_t id = params->m_controller_id; + params->m_fd = fd; + params->m_started = false; + + if (!ready_) { + XLOGD_FATAL("Network is not ready!"); + return; + } + + if(!controller_exists(id)) { + XLOGD_WARN("Controller %u doesn't exist.", id); + return; + } + + if (!ble_rcu_interface_) { + XLOGD_WARN("ble rcu interface not ready"); + return; + } + + ctrlm_hal_ble_VoiceEncoding_t encoding = CTRLM_HAL_BLE_ENCODING_ADPCM; + ctrlm_hal_ble_VoiceStreamEnd_t streamEnd = CTRLM_HAL_BLE_VOICE_STREAM_END_ON_KEY_UP; + auto rcu = controllers_.at(id); + + if (rcu->getPressAndHoldSupport()) { + streamEnd = CTRLM_HAL_BLE_VOICE_STREAM_END_ON_AUDIO_DURATION; + } + + uint64_t ieee_address = rcu->ieee_address_get().get_value(); + if (!ble_rcu_interface_->startAudioStreaming(ieee_address, encoding, streamEnd, fd)) { + XLOGD_ERROR("failed to start audio streaming on remote"); + return; + } + + params->m_fd = fd; + params->m_started = true; +} diff --git a/src/ble/ctrlm_ble_network.h b/src/ble/ctrlm_ble_network.h index 92868ca1..787bb8b8 100644 --- a/src/ble/ctrlm_ble_network.h +++ b/src/ble/ctrlm_ble_network.h @@ -192,6 +192,8 @@ class ctrlm_obj_network_ble_t : public ctrlm_obj_network_t { std::shared_ptr getConfigSettings(); + virtual void start_controller_audio_streaming(ctrlm_voice_start_audio_params_t *params); + private: ctrlm_obj_network_ble_t(); diff --git a/src/ble/hal/blercu/blercupairingstatemachine.cpp b/src/ble/hal/blercu/blercupairingstatemachine.cpp index 0a5572c5..b55613ed 100644 --- a/src/ble/hal/blercu/blercupairingstatemachine.cpp +++ b/src/ble/hal/blercu/blercupairingstatemachine.cpp @@ -517,19 +517,19 @@ void BleRcuPairingStateMachine::onStateTransition(int oldState, int newState) { if (newState == FinishedState) { if (oldState == UnpairingState) { - XLOGD_WARN("timed-out in un-pairing phase (failed rcu may be left paired)"); + XLOGD_AUTOMATION_WARN("timed-out in un-pairing phase (failed rcu may be left paired)"); } else if (oldState == StartingDiscoveryState) { - XLOGD_ERROR("timed-out waiting for discovery started signal"); + XLOGD_AUTOMATION_ERROR("timed-out waiting for discovery started signal"); } else if (oldState == DiscoveringState) { - XLOGD_ERROR("timed-out in discovery phase (didn't find target rcu device to pair to)"); + XLOGD_AUTOMATION_ERROR("timed-out in discovery phase (didn't find target rcu device to pair to)"); } else if (oldState == StoppingDiscoveryState) { - XLOGD_ERROR("timed-out waiting for discovery to stop (suggesting something has gone wrong inside bluez)"); + XLOGD_AUTOMATION_ERROR("timed-out waiting for discovery to stop (suggesting something has gone wrong inside bluez)"); } } else if (newState == UnpairingState) { if (oldState == EnablePairableState || oldState == PairingState) { - XLOGD_WARN("timed-out in pairing phase (rcu device didn't pair within %dms)", m_pairingTimeout); + XLOGD_AUTOMATION_WARN("timed-out in pairing phase (rcu device didn't pair within %dms)", m_pairingTimeout); } else if (oldState == SetupState) { - XLOGD_WARN("timed-out in setup phase (rcu didn't response to all requests within %dms)", m_setupTimeout); + XLOGD_AUTOMATION_WARN("timed-out in setup phase (rcu didn't response to all requests within %dms)", m_setupTimeout); } } } diff --git a/src/ble/hal/blercu/bluez/blercuadapter.cpp b/src/ble/hal/blercu/bluez/blercuadapter.cpp index f8e0bcbd..c7d5834e 100644 --- a/src/ble/hal/blercu/bluez/blercuadapter.cpp +++ b/src/ble/hal/blercu/bluez/blercuadapter.cpp @@ -1721,7 +1721,7 @@ void BleRcuAdapterBluez::onDevicePairedChanged(const BleAddress &address, void BleRcuAdapterBluez::onDeviceReadyChanged(const BleAddress &address, bool ready) { - XLOGD_INFO("device with address %s is %sREADY", address.toString().c_str(), ready ? "" : "NOT "); + XLOGD_AUTOMATION_INFO("device with address %s is %sREADY", address.toString().c_str(), ready ? "" : "NOT "); map>::const_iterator it = m_devices.find(address); @@ -1768,7 +1768,7 @@ bool BleRcuAdapterBluez::setConnectionParams(BleAddress address, double minInter if (address == deviceInfo.address) { - XLOGD_INFO("HCI connection handle: %u, device: %s requesting an update of connection parameters to " + XLOGD_AUTOMATION_INFO("HCI connection handle: %u, device: %s requesting an update of connection parameters to " "minInterval=%f, maxInterval=%f, latency=%d, supervisionTimeout=%d", deviceInfo.handle, deviceInfo.address.toString().c_str(), minInterval, maxInterval, latency, supervisionTimeout); diff --git a/src/ble/hal/blercu/bluez/blercudevice.cpp b/src/ble/hal/blercu/bluez/blercudevice.cpp index 8212a3a1..08aa0287 100644 --- a/src/ble/hal/blercu/bluez/blercudevice.cpp +++ b/src/ble/hal/blercu/bluez/blercudevice.cpp @@ -668,7 +668,7 @@ void BleRcuDeviceBluez::onEnteredRecoveryDisconnectingState() m_recoveryAttempts++; // log the attempt - XLOGD_ERROR("entered recovery state after device %s failed to resolve services (attempt #%d)", + XLOGD_AUTOMATION_ERROR("entered recovery state after device %s failed to resolve services (attempt #%d)", m_address.toString().c_str(), m_recoveryAttempts); diff --git a/src/ctrlm_controller.cpp b/src/ctrlm_controller.cpp index 0088b414..aaae3b40 100644 --- a/src/ctrlm_controller.cpp +++ b/src/ctrlm_controller.cpp @@ -172,11 +172,11 @@ void ctrlm_obj_controller_t::process_event_key(ctrlm_key_status_t key_status, ui last_key_code_->set_value((uint64_t)key_code); last_key_time_update(); - XLOGD_TELEMETRY("ind_process_keypress: %s - MAC Address <%s>, code = <%d> (%s key), status = <%s>", controller_type_str_get().c_str(), - ieee_address_get().to_string().c_str(), - mask ? -1 : key_code, - ctrlm_linux_key_code_str(key_code, mask), - ctrlm_key_status_str(key_status)); + XLOGD_AUTOMATION_TELEMETRY("ind_process_keypress: %s - MAC Address <%s>, code = <%d> (%s key), status = <%s>", controller_type_str_get().c_str(), + ieee_address_get().to_string().c_str(), + mask ? -1 : key_code, + ctrlm_linux_key_code_str(key_code, mask), + ctrlm_key_status_str(key_status)); } ctrlm_controller_capabilities_t ctrlm_obj_controller_t::get_capabilities() const { diff --git a/src/ctrlm_ir_controller.cpp b/src/ctrlm_ir_controller.cpp index db978c7c..17db165b 100644 --- a/src/ctrlm_ir_controller.cpp +++ b/src/ctrlm_ir_controller.cpp @@ -489,7 +489,7 @@ void* ctrlm_ir_key_monitor_thread(void *data) { case 2: { key_status = CTRLM_KEY_STATUS_REPEAT; break; } default: break; } - XLOGD_TELEMETRY("%s - code = <%d> (%s key), status = <%s>", ir_controller->name_get().c_str(), + XLOGD_AUTOMATION_TELEMETRY("%s - code = <%d> (%s key), status = <%s>", ir_controller->name_get().c_str(), ir_controller->mask_key_codes_get() ? -1 : event.code, ctrlm_linux_key_code_str(event.code, ir_controller->mask_key_codes_get()), ctrlm_key_status_str(key_status)); diff --git a/src/ctrlm_main.cpp b/src/ctrlm_main.cpp index 272d254e..1bffc6df 100644 --- a/src/ctrlm_main.cpp +++ b/src/ctrlm_main.cpp @@ -806,7 +806,7 @@ int main(int argc, char *argv[]) { ctrlm_trigger_startup_actions(); - XLOGD_INFO("Enter main loop"); + XLOGD_AUTOMATION_INFO("Enter main loop"); g_main_loop_run(g_ctrlm.main_loop); //Save the shutdown time if it is valid @@ -988,7 +988,7 @@ gboolean ctrlm_thread_monitor(gpointer user_data) { XLOGD_DEBUG("Checking %s", it->name); if(it->response != CTRLM_THREAD_MONITOR_RESPONSE_ALIVE) { - XLOGD_TELEMETRY("Thread %s is unresponsive", it->name); + XLOGD_AUTOMATION_TELEMETRY("Thread %s is unresponsive", it->name); #ifdef BREAKPAD_SUPPORT if(g_ctrlm.thread_monitor_minidump) { XLOGD_FATAL("Thread Monitor Minidump is enabled"); @@ -2329,7 +2329,7 @@ gpointer ctrlm_main_thread(gpointer param) { // Unblock the caller that launched this thread sem_post(&g_ctrlm.semaphore); - XLOGD_INFO("Enter main loop"); + XLOGD_AUTOMATION_INFO("Enter main loop"); do { gpointer msg = g_async_queue_pop(g_ctrlm.queue); @@ -2675,7 +2675,7 @@ gpointer ctrlm_main_thread(gpointer param) { //If execution reaches here, then change power state and inform VSDK of on or deep sleep states g_ctrlm.power_state = dqm->new_state; - XLOGD_INFO("Enter power state <%s>", ctrlm_power_state_str(g_ctrlm.power_state)); + XLOGD_AUTOMATION_INFO("Enter power state <%s>", ctrlm_power_state_str(g_ctrlm.power_state)); if(g_ctrlm.networked_standby_supported && (g_ctrlm.power_state == CTRLM_POWER_STATE_DEEP_SLEEP)) { XLOGD_INFO("NSM is <%s>", (ctrlm_main_get_networked_standby_mode())?"ENABLED":"DISABLED"); } diff --git a/src/ctrlm_main_iarm.cpp b/src/ctrlm_main_iarm.cpp index 8012b334..db124af4 100644 --- a/src/ctrlm_main_iarm.cpp +++ b/src/ctrlm_main_iarm.cpp @@ -753,7 +753,7 @@ IARM_Result_t ctrlm_main_iarm_call_start_pair_with_code(void *arg) { return(IARM_RESULT_INVALID_PARAM); } - XLOGD_INFO("params->network_id = <%d>, params->pair_code = 0x%X", params->network_id, params->pair_code); + XLOGD_AUTOMATION_INFO("params->network_id = <%d>, params->pair_code = 0x%X", params->network_id, params->pair_code); // Signal completion of the operation sem_t semaphore; diff --git a/src/ctrlm_network.cpp b/src/ctrlm_network.cpp index 74ff4129..69fa462b 100644 --- a/src/ctrlm_network.cpp +++ b/src/ctrlm_network.cpp @@ -1074,3 +1074,8 @@ void ctrlm_obj_network_t::iarm_event_rcu_firmware_status(const ctrlm_obj_control } #endif } + +void ctrlm_obj_network_t::start_controller_audio_streaming(ctrlm_voice_start_audio_params_t *params) { + XLOGD_WARN("not implemented for %s network", name_get()); + return; +} diff --git a/src/ctrlm_network.h b/src/ctrlm_network.h index ab22b51b..c39f3285 100644 --- a/src/ctrlm_network.h +++ b/src/ctrlm_network.h @@ -289,6 +289,8 @@ class ctrlm_obj_network_t virtual void iarm_event_rcu_validation_status(void); virtual void iarm_event_rcu_firmware_status(const ctrlm_obj_controller_t &rcu); + virtual void start_controller_audio_streaming(ctrlm_voice_start_audio_params_t *params); + // Internal methods std::string version_; diff --git a/src/ipc/ctrlm_ipc_iarm_powermanager.cpp b/src/ipc/ctrlm_ipc_iarm_powermanager.cpp index 0bef46ce..24897391 100755 --- a/src/ipc/ctrlm_ipc_iarm_powermanager.cpp +++ b/src/ipc/ctrlm_ipc_iarm_powermanager.cpp @@ -80,7 +80,7 @@ bool ctrlm_ipc_iarm_powermanager_t::get_wakeup_reason_voice() { return false; } - XLOGD_INFO("wakeup_reason <%s>", ctrlm_wakeup_reason_str(wakeup_reason)); + XLOGD_AUTOMATION_INFO("wakeup_reason <%s>", ctrlm_wakeup_reason_str(wakeup_reason)); wakeup_reason_voice = (wakeup_reason == DEEPSLEEP_WAKEUPREASON_VOICE) ? true: false; diff --git a/src/rf4ce/ctrlm_rf4ce_network.cpp b/src/rf4ce/ctrlm_rf4ce_network.cpp index de5a22ff..5fea2cd3 100644 --- a/src/rf4ce/ctrlm_rf4ce_network.cpp +++ b/src/rf4ce/ctrlm_rf4ce_network.cpp @@ -3751,94 +3751,35 @@ void ctrlm_obj_network_rf4ce_t::ind_process_voice_session_request(void *data, in XLOGD_INFO("processing session request - type <%s> voice format <%s>", ctrlm_voice_device_str(device_type), ctrlm_voice_format_str(voice_format)); } - std::string controller_name = controllers_[dqm->controller_id]->product_name_get(); - ctrlm_hal_rf4ce_cfm_data_t cb_confirm_rf4ce = NULL; - void * cb_confirm_param = NULL; + std::string controller_name = controllers_[dqm->controller_id]->product_name_get(); + void * cb_confirm_param = NULL; ctrlm_voice_session_rsp_confirm_t cb_confirm_voice_obj = NULL; + ctrlm_voice_start_audio_params_t start_audio_params; + start_audio_params.m_controller_id = dqm->controller_id; + start_audio_params.m_use_stream_params = use_stream_params; + start_audio_params.m_offset = offset; + start_audio_params.m_started = false; + start_audio_params.m_timestamp = dqm->timestamp; + start_audio_params.m_device_type = device_type; + auto audio_start_cb = std::bind(&ctrlm_obj_network_rf4ce_t::start_controller_audio_streaming, this, std::placeholders::_1); + session = ctrlm_get_voice_obj()->voice_session_req(network_id_get(), dqm->controller_id, device_type, voice_format, use_stream_params ? &stream_params : NULL, controller_name.c_str(), sw_version.to_string().c_str(), hw_version.to_string().c_str(), (((double)battery_status.get_voltage_loaded()) * 4.0 / 255), command_status, - &dqm->timestamp, &cb_confirm_voice_obj, &cb_confirm_param); - if(session == VOICE_SESSION_RESPONSE_AVAILABLE_PAR_VOICE) { - if(controllers_[dqm->controller_id]->get_capabilities().has_capability(ctrlm_controller_capabilities_t::capability::PAR)) { - session = VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE; - } else { - session = VOICE_SESSION_RESPONSE_AVAILABLE; - } - } - if(session == VOICE_SESSION_RESPONSE_AVAILABLE) { - session = VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK; - } - - XLOGD_INFO("Voice Session Response Status <%#x>", session); - - // Send the response back to the HAL device - guchar response[5]; - guchar response_len = 2; - - response[0] = MSO_VOICE_CMD_ID_VOICE_SESSION_RESPONSE; - response[1] = session; - if(use_stream_params && session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK) { // Add stream params in the response - response[1] |= 0x80; - response[2] = (guchar) stream_begin_; - response[3] = (offset & 0xFF); - response[4] = (offset >> 8); - response_len = 5; - } - - if(session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE) { - voice_params_par_t params; - ctrlm_get_voice_obj()->voice_params_par_get(¶ms); + &dqm->timestamp, &cb_confirm_voice_obj, &cb_confirm_param, + false, false, audio_start_cb, &start_audio_params); - XLOGD_INFO("PAR Voice EOS data bytes timeout <%d> method <%d>", params.par_voice_eos_timeout, params.par_voice_eos_method); - response[2] = params.par_voice_eos_method; - response[3] = (params.par_voice_eos_timeout & 0xFF); - response[4] = (params.par_voice_eos_timeout >> 8); - response_len = 5; + if(!start_audio_params.m_started) { + start_audio_params.m_cb_confirm_voice_obj = cb_confirm_voice_obj; + start_audio_params.m_cb_confirm_param = cb_confirm_param; + start_audio_params.m_status = session; + start_controller_audio_streaming(&start_audio_params); } - ctrlm_timestamp_t hal_timestamp = dqm->timestamp; - - // Determine when to send the response (50 ms after receipt) - if(controller_type_get(dqm->controller_id) == RF4CE_CONTROLLER_TYPE_XR19) { - ctrlm_timestamp_add_ms(&dqm->timestamp, response_idle_time_ff_); - } else { - ctrlm_timestamp_add_ms(&dqm->timestamp, CTRLM_RF4CE_CONST_RESPONSE_IDLE_TIME); - } - - - if(cb_confirm_voice_obj != NULL && (session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK || - session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE)) { // Only confirm response for accepted session so there is only ever one response stored - voice_session_rsp_confirm_ = cb_confirm_voice_obj; - voice_session_rsp_confirm_param_ = cb_confirm_param; - - timestamp_voice_session_request_ = hal_timestamp; - timestamp_voice_first_packet_ = hal_timestamp; - - cb_confirm_rf4ce = ctrlm_network_rf4ce_cfm_voice_session_rsp; - cb_confirm_param = voice_session_rsp_params_.network_id; - - // Store controller id, packet and timestamp for retransmission in case of send error - voice_session_rsp_params_.controller_id = dqm->controller_id; - voice_session_rsp_params_.response_len = response_len; - voice_session_rsp_params_.timestamp_hal = hal_timestamp; - voice_session_rsp_params_.timestamp_begin = dqm->timestamp; - voice_session_rsp_params_.timestamp_end = dqm->timestamp; - voice_session_rsp_params_.retries = 0; - ctrlm_timestamp_add_ms(&voice_session_rsp_params_.timestamp_end, CTRLM_RF4CE_CONST_RESPONSE_WAIT_TIME); - errno_t safec_rc = memcpy_s(&voice_session_rsp_params_.response, sizeof(voice_session_rsp_params_.response),response, response_len); - ERR_CHK(safec_rc); - ctrlm_timestamp_get(&voice_session_rsp_params_.timestamp_rsp_req); - } - - req_data(CTRLM_RF4CE_PROFILE_ID_VOICE, dqm->controller_id, dqm->timestamp, response_len, response, NULL, NULL, false, single_channel_rsp_, cb_confirm_rf4ce, cb_confirm_param); - - XLOGD_INFO("session response delivered"); - if(session != VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK && session != VOICE_SESSION_RESPONSE_AVAILABLE && session != VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE && session != VOICE_SESSION_RESPONSE_AVAILABLE_PAR_VOICE) { voice_session_active_count_--; @@ -3847,26 +3788,10 @@ void ctrlm_obj_network_rf4ce_t::ind_process_voice_session_request(void *data, in property.state = CTRLM_HAL_FREQUENCY_AGILITY_ENABLE; ctrlm_network_property_set(network_id_get(), CTRLM_HAL_NETWORK_PROPERTY_FREQUENCY_AGILITY, (void *)&property, sizeof(property)); } - - if(device_type == CTRLM_VOICE_DEVICE_PTT) { - // Send voice key up event since the session was not accepted - process_event_key(dqm->controller_id, CTRLM_KEY_STATUS_UP, CTRLM_KEY_CODE_PUSH_TO_TALK); - } } if(dqm->status != VOICE_SESSION_RESPONSE_AVAILABLE && dqm->status != VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK) { // Session was aborted XLOGD_INFO("voice session abort"); - - // // Broadcast the event over the iarm bus - // ctrlm_voice_iarm_event_session_abort_t event; - // event.api_revision = CTRLM_VOICE_IARM_BUS_API_REVISION; - // event.network_id = dqm->header.network_id; - // event.network_type = ctrlm_network_type_get(dqm->header.network_id); - // event.controller_id = dqm->controller_id; - // event.session_id = ctrlm_voice_session_id_get_next(); - // event.reason = dqm->reason; - - // ctrlm_voice_iarm_event_session_abort(&event); } } @@ -3901,7 +3826,6 @@ void ctrlm_obj_network_rf4ce_t::cfm_voice_session_rsp(void *data, int size) { } ctrlm_timestamp_t now; ctrlm_timestamp_get(&now); - double loadavg[3] = { -1, -1, -1 }; getloadavg(loadavg, 3); struct sysinfo s_info; @@ -5093,3 +5017,117 @@ void ctrlm_obj_network_rf4ce_t::controller_init_uinput(ctrlm_controller_id_t con return; } } + +void ctrlm_obj_network_rf4ce_t::start_controller_audio_streaming(ctrlm_voice_start_audio_params_t *params) { + THREAD_ID_VALIDATE(); + params->m_started = false; + ctrlm_controller_id_t controller_id = params->m_controller_id; + ctrlm_voice_device_t device_type = params->m_device_type; + + if(!ready_) { + XLOGD_FATAL("Network is not ready!"); + return; + } + + if(!controller_exists(controller_id)) { + XLOGD_WARN("Controller %u doesn't exist.", controller_id); + return; + } + + ctrlm_voice_session_response_status_t session = params->m_status; + + if(session == VOICE_SESSION_RESPONSE_AVAILABLE_PAR_VOICE) { + if(controllers_[controller_id]->get_capabilities().has_capability(ctrlm_controller_capabilities_t::capability::PAR)) { + session = VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE; + } else { + session = VOICE_SESSION_RESPONSE_AVAILABLE; + } + } + if(session == VOICE_SESSION_RESPONSE_AVAILABLE) { + session = VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK; + } + + XLOGD_INFO("Voice Session Response Status <%#x>", session); + + // Send the response back to the HAL device + guchar response[5]; + guchar response_len = 2; + gint16 offset = params->m_offset; + + response[0] = MSO_VOICE_CMD_ID_VOICE_SESSION_RESPONSE; + response[1] = session; + if(params->m_use_stream_params && session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK) { // Add stream params in the response + response[1] |= 0x80; + response[2] = (guchar) stream_begin_; + response[3] = (offset & 0xFF); + response[4] = (offset >> 8); + response_len = 5; + } + + if(session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE) { + voice_params_par_t voice_params; + ctrlm_get_voice_obj()->voice_params_par_get(&voice_params); + + XLOGD_INFO("PAR Voice EOS data bytes timeout <%d> method <%d>", voice_params.par_voice_eos_timeout, voice_params.par_voice_eos_method); + response[2] = voice_params.par_voice_eos_method; + response[3] = (voice_params.par_voice_eos_timeout & 0xFF); + response[4] = (voice_params.par_voice_eos_timeout >> 8); + response_len = 5; + } + + ctrlm_timestamp_t hal_timestamp = params->m_timestamp; + + // Determine when to send the response (50 ms after receipt) + if(controller_type_get(controller_id) == RF4CE_CONTROLLER_TYPE_XR19) { + ctrlm_timestamp_add_ms(¶ms->m_timestamp, response_idle_time_ff_); + } else { + ctrlm_timestamp_add_ms(¶ms->m_timestamp, CTRLM_RF4CE_CONST_RESPONSE_IDLE_TIME); + } + + ctrlm_hal_rf4ce_cfm_data_t cb_confirm_rf4ce = NULL; + + if(params->m_cb_confirm_voice_obj != NULL && (session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK || + session == VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE)) { // Only confirm response for accepted session so there is only ever one response stored + voice_session_rsp_confirm_ = params->m_cb_confirm_voice_obj; + voice_session_rsp_confirm_param_ = params->m_cb_confirm_param; + + timestamp_voice_session_request_ = hal_timestamp; + timestamp_voice_first_packet_ = hal_timestamp; + + cb_confirm_rf4ce = ctrlm_network_rf4ce_cfm_voice_session_rsp; + params->m_cb_confirm_param = voice_session_rsp_params_.network_id; + + // Store controller id, packet and timestamp for retransmission in case of send error + voice_session_rsp_params_.controller_id = controller_id; + voice_session_rsp_params_.response_len = response_len; + voice_session_rsp_params_.timestamp_hal = hal_timestamp; + voice_session_rsp_params_.timestamp_begin = params->m_timestamp; + voice_session_rsp_params_.timestamp_end = params->m_timestamp; + voice_session_rsp_params_.retries = 0; + ctrlm_timestamp_add_ms(&voice_session_rsp_params_.timestamp_end, CTRLM_RF4CE_CONST_RESPONSE_WAIT_TIME); + errno_t safec_rc = memcpy_s(&voice_session_rsp_params_.response, sizeof(voice_session_rsp_params_.response),response, response_len); + ERR_CHK(safec_rc); + ctrlm_timestamp_get(&voice_session_rsp_params_.timestamp_rsp_req); + } + + req_data(CTRLM_RF4CE_PROFILE_ID_VOICE, controller_id, params->m_timestamp, response_len, response, NULL, NULL, false, single_channel_rsp_, cb_confirm_rf4ce, params->m_cb_confirm_param); + + XLOGD_INFO("session response delivered"); + + if(session != VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK && session != VOICE_SESSION_RESPONSE_AVAILABLE && + session != VOICE_SESSION_RESPONSE_AVAILABLE_SKIP_CHAN_CHECK_PAR_VOICE && session != VOICE_SESSION_RESPONSE_AVAILABLE_PAR_VOICE) { + voice_session_active_count_--; + if(voice_session_active_count_ == 0) { // Re-enable frequency agility if the no other active RF4CE voice sessions + ctrlm_hal_network_property_frequency_agility_t property; + property.state = CTRLM_HAL_FREQUENCY_AGILITY_ENABLE; + ctrlm_network_property_set(network_id_get(), CTRLM_HAL_NETWORK_PROPERTY_FREQUENCY_AGILITY, (void *)&property, sizeof(property)); + } + + if(device_type == CTRLM_VOICE_DEVICE_PTT) { + // Send voice key up event since the session was not accepted + process_event_key(controller_id, CTRLM_KEY_STATUS_UP, CTRLM_KEY_CODE_PUSH_TO_TALK); + } + } + + params->m_started = true; +} diff --git a/src/rf4ce/ctrlm_rf4ce_network.h b/src/rf4ce/ctrlm_rf4ce_network.h index 1e4ce251..07298971 100644 --- a/src/rf4ce/ctrlm_rf4ce_network.h +++ b/src/rf4ce/ctrlm_rf4ce_network.h @@ -462,6 +462,8 @@ class ctrlm_obj_network_rf4ce_t : public ctrlm_obj_network_t virtual std::vector get_controller_obj_list() const; void rcu_timeout_key_release(void *data, int data_size); + virtual void start_controller_audio_streaming(ctrlm_voice_start_audio_params_t *params); + protected: virtual gboolean key_event_hook(ctrlm_network_id_t network_id, ctrlm_controller_id_t controller_id, ctrlm_key_status_t key_status, ctrlm_key_code_t key_code); diff --git a/src/voice/ctrlm_voice_obj.cpp b/src/voice/ctrlm_voice_obj.cpp index 93c12ac2..d114aeea 100644 --- a/src/voice/ctrlm_voice_obj.cpp +++ b/src/voice/ctrlm_voice_obj.cpp @@ -1344,7 +1344,7 @@ ctrlm_voice_session_response_status_t ctrlm_voice_t::voice_session_req(ctrlm_net ctrlm_voice_device_t device_type, ctrlm_voice_format_t format, voice_session_req_stream_params *stream_params, const char *controller_name, const char *sw_version, const char *hw_version, double voltage, bool command_status, - ctrlm_timestamp_t *timestamp, ctrlm_voice_session_rsp_confirm_t *cb_confirm, void **cb_confirm_param, bool use_external_data_pipe, bool press_and_hold, const char *l_transcription_in, const char *audio_file_in, const uuid_t *uuid, bool low_latency, bool low_cpu_util, int audio_fd) { + ctrlm_timestamp_t *timestamp, ctrlm_voice_session_rsp_confirm_t *cb_confirm, void **cb_confirm_param, bool use_external_data_pipe, bool press_and_hold, std::function cb_start_audio, ctrlm_voice_start_audio_params_t *cb_audio_start_params, const char *l_transcription_in, const char *audio_file_in, const uuid_t *uuid, bool low_latency, bool low_cpu_util, int audio_fd) { ctrlm_voice_session_t *session = &this->voice_session[voice_device_to_session_group(device_type)]; @@ -1376,6 +1376,7 @@ ctrlm_voice_session_response_status_t ctrlm_voice_t::voice_session_req(ctrlm_net // Cancel current speech router session XLOGD_INFO("Waiting on the results from previous session, aborting this and continuing.."); + pre_session_terminate(cb_start_audio, cb_audio_start_params, cb_confirm, cb_confirm_param); xrsr_session_terminate(voice_device_to_xrsr(session->voice_device)); // Synchronous - this will take a bit of time. Might need to revisit this down the road. } bool request_new_session = true; @@ -1387,6 +1388,7 @@ ctrlm_voice_session_response_status_t ctrlm_voice_t::voice_session_req(ctrlm_net request_new_session = false; } else { // Cancel current speech router session XLOGD_WARN("Session in progress with same controller - src <%s> dst <%s>, aborting this and continuing..", ctrlm_voice_state_src_str(session->state_src), ctrlm_voice_state_dst_str(session->state_dst)); + pre_session_terminate(cb_start_audio, cb_audio_start_params, cb_confirm, cb_confirm_param); xrsr_session_terminate(voice_device_to_xrsr(session->voice_device)); // Synchronous - this will take a bit of time. Might need to revisit this down the road. } } else { // session in progress with different controller @@ -1770,16 +1772,16 @@ void ctrlm_voice_t::voice_session_data_post_processing(int bytes_sent, const cha float rx_rate = (elapsed == 0) ? 0 : (session->audio_sent_samples * 2 * 8) / elapsed; session->timeout_packet_tag = g_timeout_add(timeout, ctrlm_voice_packet_timeout, NULL); - XLOGD_DEBUG("Audio %s bytes <%lu> samples <%lu> rate <%6.2f kbps> timeout <%lu ms>", action, session->audio_sent_bytes, session->audio_sent_samples, rx_rate, timeout); + XLOGD_AUTOMATION_DEBUG("Audio %s bytes <%lu> samples <%lu> rate <%6.2f kbps> timeout <%lu ms>", action, session->audio_sent_bytes, session->audio_sent_samples, rx_rate, timeout); } else { #ifdef VOICE_BUFFER_STATS if(voice_buffer_warning_triggered) { - XLOGD_DEBUG("Audio %s bytes <%lu> samples <%lu> pkt cnt <%3u> elapsed <%8llu ms> lag <%8lld ms> (%4.2f packets)", action, session->audio_sent_bytes, session->audio_sent_samples, packets_total, session_time / 1000, session_delta / 1000, (((float)session_delta) / this->voice_packet_interval)); + XLOGD_AUTOMATION_DEBUG("Audio %s bytes <%lu> samples <%lu> pkt cnt <%3u> elapsed <%8llu ms> lag <%8lld ms> (%4.2f packets)", action, session->audio_sent_bytes, session->audio_sent_samples, packets_total, session_time / 1000, session_delta / 1000, (((float)session_delta) / this->voice_packet_interval)); } else { - XLOGD_DEBUG("Audio %s bytes <%lu> samples <%lu>", action, session->audio_sent_bytes, session->audio_sent_samples); + XLOGD_AUTOMATION_DEBUG("Audio %s bytes <%lu> samples <%lu>", action, session->audio_sent_bytes, session->audio_sent_samples); } #else - XLOGD_DEBUG("Audio %s bytes <%lu> samples <%lu>", action, session->audio_sent_bytes, session->audio_sent_samples); + XLOGD_AUTOMATION_DEBUG("Audio %s bytes <%lu> samples <%lu>", action, session->audio_sent_bytes, session->audio_sent_samples); #endif } } @@ -2059,10 +2061,10 @@ void ctrlm_voice_t::voice_session_timeout() { signed long long elapsed = rdkx_timestamp_subtract_ms(session->session_timing.ctrl_audio_rxd_first, timestamp); float rx_rate = (elapsed == 0) ? 0 : (session->audio_sent_samples * 2 * 8) / elapsed; - XLOGD_INFO("elapsed time <%llu> ms rx samples <%u> rate <%6.1f> kbps", elapsed, session->audio_sent_samples, rx_rate); + XLOGD_AUTOMATION_INFO("elapsed time <%llu> ms rx samples <%u> rate <%6.1f> kbps", elapsed, session->audio_sent_samples, rx_rate); reason = CTRLM_VOICE_SESSION_END_REASON_MINIMUM_QOS; } - XLOGD_INFO("%s", ctrlm_voice_session_end_reason_str(reason)); + XLOGD_AUTOMATION_INFO("%s", ctrlm_voice_session_end_reason_str(reason)); this->voice_session_end(session, reason); } @@ -2979,7 +2981,7 @@ void ctrlm_voice_t::voice_stream_end_callback(ctrlm_voice_stream_end_cb_t *strea stream_duration = (session->packets_processed * frame_duration_us) / 1000; samples_per_packet = (session->format.value.adpcm_frame.size_packet - session->format.value.adpcm_frame.size_header) * 2; // 2 samples per byte for ADPCM } - XLOGD_TELEMETRY("src <%s> Packets Lost/Total <%u/%u> %.02f%% duration <%u> ms", ctrlm_voice_device_str(session->voice_device), session->packets_lost, session->packets_lost + session->packets_processed, 100.0 * ((double)session->packets_lost / (double)(session->packets_lost + session->packets_processed)), stream_duration); + XLOGD_AUTOMATION_TELEMETRY("src <%s> Packets Lost/Total <%u/%u> %.02f%% duration <%u> ms", ctrlm_voice_device_str(session->voice_device), session->packets_lost, session->packets_lost + session->packets_processed, 100.0 * ((double)session->packets_lost / (double)(session->packets_lost + session->packets_processed)), stream_duration); #ifdef TELEMETRY_SUPPORT if(this->prefs.telemetry_session_stats) { uint32_t packets_total = session->packets_lost + session->packets_processed; @@ -4244,3 +4246,14 @@ void ctrlm_voice_t::url_hostname_patterns(const std::vector &obj_se this->url_hostname_pattern_add(itr.c_str()); } } + +void ctrlm_voice_t::pre_session_terminate(std::function cb_start_audio, ctrlm_voice_start_audio_params_t *cb_audio_start_params, ctrlm_voice_session_rsp_confirm_t *cb_confirm, void **cb_confirm_param) { + if (cb_start_audio != nullptr && cb_audio_start_params != nullptr) { + if(cb_confirm != NULL && cb_confirm_param != NULL) { + cb_audio_start_params->m_cb_confirm_voice_obj = ctrlm_voice_session_response_confirm; + cb_audio_start_params->m_cb_confirm_param = NULL; + cb_audio_start_params->m_status = (this->prefs.par_voice_enabled) ? VOICE_SESSION_RESPONSE_AVAILABLE_PAR_VOICE : VOICE_SESSION_RESPONSE_AVAILABLE; + } + cb_start_audio(cb_audio_start_params); + } +} diff --git a/src/voice/ctrlm_voice_obj.h b/src/voice/ctrlm_voice_obj.h index bd8de16c..3976a62c 100644 --- a/src/voice/ctrlm_voice_obj.h +++ b/src/voice/ctrlm_voice_obj.h @@ -389,6 +389,29 @@ typedef struct { typedef void (*ctrlm_voice_session_rsp_confirm_t)(bool result, signed long long rsp_time, unsigned int rsp_window, const std::string &err_str, ctrlm_timestamp_t *timestamp, void *user_data); +class ctrlm_voice_start_audio_params_t +{ +public: + // Generic + ctrlm_voice_start_audio_params_t() = default; + virtual ~ctrlm_voice_start_audio_params_t() = default; + + ctrlm_controller_id_t m_controller_id = -1; + bool m_started = false; + + // BLE + int m_fd = -1; + + // RF4CE + bool m_use_stream_params = false; + int16_t m_offset = 0; + ctrlm_timestamp_t m_timestamp; + ctrlm_voice_session_rsp_confirm_t m_cb_confirm_voice_obj; + void * m_cb_confirm_param; + ctrlm_voice_session_response_status_t m_status; + ctrlm_voice_device_t m_device_type; +}; + typedef struct { ctrlm_network_id_t network_id; ctrlm_network_type_t network_type; @@ -471,7 +494,7 @@ class ctrlm_voice_t { ctrlm_voice_t(); virtual ~ctrlm_voice_t(); - ctrlm_voice_session_response_status_t voice_session_req(ctrlm_network_id_t network_id, ctrlm_controller_id_t controller_id, ctrlm_voice_device_t device_type, ctrlm_voice_format_t format, voice_session_req_stream_params *stream_params, const char *controller_name, const char *sw_version, const char *hw_version, double voltage, bool command_status=false, ctrlm_timestamp_t *timestamp=NULL, ctrlm_voice_session_rsp_confirm_t *cb_confirm=NULL, void **cb_confirm_param=NULL, bool use_external_data_pipe=false, bool press_and_hold=true, const char *transcription_in=NULL, const char *audio_file_in=NULL, const uuid_t *uuid = NULL, bool low_latency=false, bool low_cpu_util=false, int audio_fd = -1); + ctrlm_voice_session_response_status_t voice_session_req(ctrlm_network_id_t network_id, ctrlm_controller_id_t controller_id, ctrlm_voice_device_t device_type, ctrlm_voice_format_t format, voice_session_req_stream_params *stream_params, const char *controller_name, const char *sw_version, const char *hw_version, double voltage, bool command_status=false, ctrlm_timestamp_t *timestamp=NULL, ctrlm_voice_session_rsp_confirm_t *cb_confirm=NULL, void **cb_confirm_param=NULL, bool use_external_data_pipe=false, bool press_and_hold=true, std::function cb_start_audio=NULL, ctrlm_voice_start_audio_params_t *cb_audio_start_params=NULL, const char *transcription_in=NULL, const char *audio_file_in=NULL, const uuid_t *uuid = NULL, bool low_latency=false, bool low_cpu_util=false, int audio_fd = -1); void voice_session_rsp_confirm(bool result, signed long long rsp_time, unsigned int rsp_window, const std::string &err_str, ctrlm_timestamp_t *timestamp); bool voice_session_data(ctrlm_network_id_t network_id, ctrlm_controller_id_t controller_id, const char *buffer, long unsigned int length, ctrlm_timestamp_t *timestamp=NULL, uint8_t *lqi=NULL); bool voice_session_data(ctrlm_network_id_t network_id, ctrlm_controller_id_t controller_id, int fd, const uuid_t *uuid=NULL); @@ -723,6 +746,10 @@ class ctrlm_voice_t { void audio_state_set(bool session); bool vsdk_is_privacy_enabled(void); double vsdk_keyword_sensitivity_limit_check(double sensitivity); + void pre_session_terminate(std::function cb_start_audio, + ctrlm_voice_start_audio_params_t *cb_audio_start_params, + ctrlm_voice_session_rsp_confirm_t *cb_confirm, + void **cb_confirm_param); }; // Helper Functions diff --git a/src/voice/endpoints/ctrlm_voice_endpoint_http.cpp b/src/voice/endpoints/ctrlm_voice_endpoint_http.cpp index 653e2260..93396a4b 100644 --- a/src/voice/endpoints/ctrlm_voice_endpoint_http.cpp +++ b/src/voice/endpoints/ctrlm_voice_endpoint_http.cpp @@ -194,7 +194,7 @@ void ctrlm_voice_endpoint_http_t::voice_session_begin_callback_http(void *data, has_sat = true; } - XLOGD_TELEMETRY("session begin - src <%s> h_SAT <%s> h_MTLS <%s> h_OCSPst <%s> h_OCSPca <%s>", ctrlm_voice_device_str(source), has_sat ? "YES" : "NO", use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO"); + XLOGD_AUTOMATION_TELEMETRY("session begin - src <%s> h_SAT <%s> h_MTLS <%s> h_OCSPst <%s> h_OCSPca <%s>", ctrlm_voice_device_str(source), has_sat ? "YES" : "NO", use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO"); errno_t safec_rc = strcpy_s(this->user_agent, sizeof(this->user_agent), user_agent.str().c_str()); ERR_CHK(safec_rc); diff --git a/src/voice/endpoints/ctrlm_voice_endpoint_sdt.cpp b/src/voice/endpoints/ctrlm_voice_endpoint_sdt.cpp index ca4fe980..2324878c 100644 --- a/src/voice/endpoints/ctrlm_voice_endpoint_sdt.cpp +++ b/src/voice/endpoints/ctrlm_voice_endpoint_sdt.cpp @@ -250,7 +250,7 @@ void ctrlm_voice_endpoint_sdt_t::voice_session_begin_callback_sdt(void *data, in keyword_verification = true; } } - XLOGD_INFO("session begin - ptt <%s> keyword begin <%u> end <%u> doa <%u> gain <%4.1f> db", (stream_params->push_to_talk ? "TRUE" : "FALSE"), stream_params->keyword_sample_begin, stream_params->keyword_sample_end, stream_params->keyword_doa, stream_params->dynamic_gain); + XLOGD_AUTOMATION_INFO("session begin - ptt <%s> keyword begin <%u> end <%u> doa <%u> gain <%4.1f> db", (stream_params->push_to_talk ? "TRUE" : "FALSE"), stream_params->keyword_sample_begin, stream_params->keyword_sample_end, stream_params->keyword_doa, stream_params->dynamic_gain); } // End handle stream parameters diff --git a/src/voice/endpoints/ctrlm_voice_endpoint_ws_nextgen.cpp b/src/voice/endpoints/ctrlm_voice_endpoint_ws_nextgen.cpp index 248832cc..fcf9b12a 100644 --- a/src/voice/endpoints/ctrlm_voice_endpoint_ws_nextgen.cpp +++ b/src/voice/endpoints/ctrlm_voice_endpoint_ws_nextgen.cpp @@ -365,7 +365,7 @@ void ctrlm_voice_endpoint_ws_nextgen_t::voice_session_begin_callback_ws_nextgen( } config_in.ws.app_config = stream_params_out; - XLOGD_TELEMETRY("session begin - src <%s> ptt <%s> w_SAT <%s> w_MTLS <%s> w_OCSPst <%s> w_OCSPca <%s> keyword begin <%u> end <%u> doa <%u> gain <%4.1f> db", ctrlm_voice_device_str(source), (stream_params->push_to_talk ? "TRUE" : "FALSE"), has_sat ? "YES" : "NO", use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO", stream_params->keyword_sample_begin, stream_params->keyword_sample_end, stream_params->keyword_doa, stream_params->dynamic_gain); + XLOGD_AUTOMATION_TELEMETRY("session begin - src <%s> ptt <%s> w_SAT <%s> w_MTLS <%s> w_OCSPst <%s> w_OCSPca <%s> keyword begin <%u> end <%u> doa <%u> gain <%4.1f> db", ctrlm_voice_device_str(source), (stream_params->push_to_talk ? "TRUE" : "FALSE"), has_sat ? "YES" : "NO", use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO", stream_params->keyword_sample_begin, stream_params->keyword_sample_end, stream_params->keyword_doa, stream_params->dynamic_gain); } else if(!is_mic || dqm->configuration.user_initiated) { xrsv_ws_nextgen_stream_params_t *stream_params = (xrsv_ws_nextgen_stream_params_t *)malloc(sizeof(xrsv_ws_nextgen_stream_params_t)); @@ -378,7 +378,7 @@ void ctrlm_voice_endpoint_ws_nextgen_t::voice_session_begin_callback_ws_nextgen( } config_in.ws.app_config = stream_params; - XLOGD_TELEMETRY("session begin - src <%s> ptt w_SAT <%s> w_MTLS <%s> w_OCSPst <%s> w_OCSPca <%s>", ctrlm_voice_device_str(source), has_sat ? "YES" : "NO", use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO"); + XLOGD_AUTOMATION_TELEMETRY("session begin - src <%s> ptt w_SAT <%s> w_MTLS <%s> w_OCSPst <%s> w_OCSPca <%s>", ctrlm_voice_device_str(source), has_sat ? "YES" : "NO", use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO"); } else { XLOGD_ERROR("session begin - invalid params - src <%s>", ctrlm_voice_device_str(source)); } diff --git a/src/voice/endpoints/ctrlm_voice_endpoint_ws_nsp.cpp b/src/voice/endpoints/ctrlm_voice_endpoint_ws_nsp.cpp index 45ad9714..da4d4035 100644 --- a/src/voice/endpoints/ctrlm_voice_endpoint_ws_nsp.cpp +++ b/src/voice/endpoints/ctrlm_voice_endpoint_ws_nsp.cpp @@ -133,7 +133,7 @@ void ctrlm_voice_endpoint_ws_nsp_t::voice_session_begin_callback_ws_nsp(void *da config_in.ws.cert_revoked_allow = false; config_in.ws.ocsp_expired_allow = false; - XLOGD_TELEMETRY("session begin - src <%s> x_MTLS <%s> x_OCSPst <%s> x_OCSPca <%s>", ctrlm_voice_device_str(source), use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO"); + XLOGD_AUTOMATION_TELEMETRY("session begin - src <%s> x_MTLS <%s> x_OCSPst <%s> x_OCSPca <%s>", ctrlm_voice_device_str(source), use_mtls ? "YES" : "NO", ocsp_verify_stapling ? "YES" : "NO", ocsp_verify_ca ? "YES" : "NO"); ctrlm_voice_session_begin_cb_t session_begin; uuid_copy(session_begin.header.uuid, dqm->uuid); diff --git a/src/voice/ipc/ctrlm_voice_ipc_iarm_thunder.cpp b/src/voice/ipc/ctrlm_voice_ipc_iarm_thunder.cpp index 022b71f4..02b4408e 100644 --- a/src/voice/ipc/ctrlm_voice_ipc_iarm_thunder.cpp +++ b/src/voice/ipc/ctrlm_voice_ipc_iarm_thunder.cpp @@ -357,7 +357,7 @@ bool ctrlm_voice_ipc_iarm_thunder_t::session_end(const ctrlm_voice_ipc_event_ses char *json_str = json_dumps(event_data, JSON_ENCODE_FLAGS); if(json_str) { //TODO: surface the event through IARM - XLOGD_INFO("<%s>", this->obj_voice->voice_stb_data_pii_mask_get() ? "***" : json_str); + XLOGD_AUTOMATION_INFO("<%s>", this->obj_voice->voice_stb_data_pii_mask_get() ? "***" : json_str); ret = broadcast_event(CTRLM_MAIN_IARM_BUS_NAME, CTRLM_VOICE_IARM_EVENT_JSON_SESSION_END, json_str); free(json_str); } else { @@ -373,7 +373,7 @@ bool ctrlm_voice_ipc_iarm_thunder_t::session_end(const ctrlm_voice_ipc_event_ses bool ctrlm_voice_ipc_iarm_thunder_t::server_message(const char *message, unsigned long size) { bool ret = false; if(message) { - XLOGD_INFO("%ul : <%s>", size, this->obj_voice->voice_stb_data_pii_mask_get() ? "***" : message); //CID -160950 - Printargs + XLOGD_AUTOMATION_INFO("%ul : <%s>", size, this->obj_voice->voice_stb_data_pii_mask_get() ? "***" : message); //CID -160950 - Printargs ret = broadcast_event(CTRLM_MAIN_IARM_BUS_NAME, CTRLM_VOICE_IARM_EVENT_JSON_SERVER_MESSAGE, message); } return(ret); @@ -793,7 +793,8 @@ IARM_Result_t ctrlm_voice_ipc_iarm_thunder_t::voice_session_request(void *data) ctrlm_voice_session_response_status_t voice_status = voice_obj->voice_session_req( CTRLM_MAIN_NETWORK_ID_INVALID, CTRLM_MAIN_CONTROLLER_ID_INVALID, request_config.device, request_config.format, NULL, str_name_of_source.c_str(), "0.0.0.0", "0.0.0.0", 0.0, - false, NULL, NULL, NULL, (fd >= 0) ? true : false, true, str_transcription.empty() ? NULL : str_transcription.c_str(), str_audio_file.empty() ? NULL : str_audio_file.c_str(), &request_uuid, request_config.low_latency, request_config.low_cpu_util, fd); + false, NULL, NULL, NULL, (fd >= 0) ? true : false, true, NULL, NULL, + str_transcription.empty() ? NULL : str_transcription.c_str(), str_audio_file.empty() ? NULL : str_audio_file.c_str(), &request_uuid, request_config.low_latency, request_config.low_cpu_util, fd); if (voice_status != VOICE_SESSION_RESPONSE_AVAILABLE && voice_status != VOICE_SESSION_RESPONSE_AVAILABLE_PAR_VOICE) { XLOGD_ERROR("Failed opening voice session <%s>", ctrlm_voice_session_response_status_str(voice_status));