diff options
author | PixelBot AutoMerger <android-nexus-securitybot@system.gserviceaccount.com> | 2023-12-03 18:55:11 -0800 |
---|---|---|
committer | SecurityBot <android-nexus-securitybot@system.gserviceaccount.com> | 2023-12-03 18:55:12 -0800 |
commit | a7ee00026cd3dd4457c6d9849e019ec0ca2be836 (patch) | |
tree | 8f12f7281ebfd884ee6cfb002e4368952b59e4dd | |
parent | 10bcd0e5a07ac79fc725174aaeb8ec4150d74162 (diff) | |
parent | c69225db7dde64287e2cdb8d17472cc65324f999 (diff) | |
download | aoc-a7ee00026cd3dd4457c6d9849e019ec0ca2be836.tar.gz |
Merge android13-gs-pixel-5.10-24Q1 into android13-gs-pixel-5.10android-u-qpr3-beta-1_r0.7android-u-qpr3-beta-1_r0.5android-u-qpr3-beta-1_r0.4android-u-qpr3-beta-1_r0.3android-u-qpr3-beta-1_r0.2android-u-qpr3-beta-1_r0.1android-15-dp-1_r0.7android-15-dp-1_r0.5android-15-dp-1_r0.4android-15-dp-1_r0.3android-15-dp-1_r0.2android-15-dp-1_r0.1
SBMerger: 571992243
Change-Id: Iac42b53b23a42f55678602fad8c999f8761f3e6c
Signed-off-by: SecurityBot <android-nexus-securitybot@system.gserviceaccount.com>
-rw-r--r-- | Documentation/ABI/sysfs-devices-platform-aoc | 9 | ||||
-rw-r--r-- | alsa/aoc_alsa.h | 1 | ||||
-rw-r--r-- | alsa/aoc_alsa_hw.c | 45 | ||||
-rw-r--r-- | aoc.c | 115 | ||||
-rw-r--r-- | aoc.h | 2 | ||||
-rw-r--r-- | aoc_channel_dev.c | 5 | ||||
-rw-r--r-- | aoc_v1.c | 3 |
7 files changed, 92 insertions, 88 deletions
diff --git a/Documentation/ABI/sysfs-devices-platform-aoc b/Documentation/ABI/sysfs-devices-platform-aoc new file mode 100644 index 0000000..81a5b6c --- /dev/null +++ b/Documentation/ABI/sysfs-devices-platform-aoc @@ -0,0 +1,9 @@ +What: /sys/devices/platform/[0-9]+.aoc/notify_timeout_aoc_status +Date: Nov 2023 +KernelVersion: 2.6.22 +Contact: alexiacobucci@google.com +Description: + Read-only node used by AOC's kernel driver to notify userspace + if a request for AOC fabric to reach a certain state has timed out. + +Users: AOC kernel driver, aocd process in userspace. diff --git a/alsa/aoc_alsa.h b/alsa/aoc_alsa.h index 2ac015c..0707e05 100644 --- a/alsa/aoc_alsa.h +++ b/alsa/aoc_alsa.h @@ -484,6 +484,7 @@ int aoc_incall_init(void); void aoc_incall_exit(void); int aoc_voip_init(void); void aoc_voip_exit(void); +int aoc_audio_mic_mask_set(struct aoc_chip *chip, bool is_voice); int aoc_audio_us_record(struct aoc_chip *chip, bool enable); #endif diff --git a/alsa/aoc_alsa_hw.c b/alsa/aoc_alsa_hw.c index 8da92c6..db0230d 100644 --- a/alsa/aoc_alsa_hw.c +++ b/alsa/aoc_alsa_hw.c @@ -422,6 +422,10 @@ int aoc_audio_capture_mic_prepare(struct aoc_chip *chip) goto exit; } + /* Update mask before start capture */ + if (mic_input_source == AP_INPUT_PROCESSOR_MIC_INPUT_INDEX) + aoc_audio_mic_mask_set(chip, false); + // CMD_AUDIO_INPUT_AP_INPUT_START_ID with mic_input_source pr_info("mic_input_source = %d\n", mic_input_source); @@ -2844,8 +2848,6 @@ int aoc_audio_set_params(struct aoc_alsa_stream *alsa_stream, uint32_t channels, uint32_t samplerate, uint32_t bps, bool pcm_float_fmt, int source_mode) { int err = 0; - struct aoc_chip *chip = alsa_stream->chip; - pr_debug("setting channels(%u), samplerate(%u), bits-per-sample(%u)\n", channels, samplerate, bps); @@ -2861,13 +2863,6 @@ int aoc_audio_set_params(struct aoc_alsa_stream *alsa_stream, uint32_t channels, pr_err("ERR:%d capture audio param set fails\n", err); goto exit; } - - /* To deal with recording with spatial module enabled */ - if (chip->mic_spatial_module_enable && !aoc_pcm_is_mmap_raw(alsa_stream)) { - err = aoc_audio_capture_spatial_module_trigger(chip, START); - if (err < 0) - pr_err("ERR:%d mic proc spatial module failed to start!\n", err); - } } exit: @@ -3023,6 +3018,12 @@ static int aoc_telephony_mic_open(struct aoc_chip *chip, int mic) } mic_input_source = hw_id_to_phone_mic_source(mic); + + /* Update mask before start capture */ + if (mic_input_source == MODEM_MIC_INPUT_INDEX || + mic_input_source == MODEM_INCALL_INPUT_INDEX) + aoc_audio_mic_mask_set(chip, true); + pr_info("open telephony mic: %d - %d\n", mic_input_source, mic); if (mic_input_source != NULL_PATH) { err = aoc_audio_modem_mic_input(chip, START, mic_input_source); @@ -3634,7 +3635,6 @@ int aoc_audio_open(struct aoc_alsa_stream *alsa_stream) int aoc_audio_close(struct aoc_alsa_stream *alsa_stream) { - int err = 0; struct aoc_chip *chip = alsa_stream->chip; struct snd_pcm_substream *substream = alsa_stream->substream; @@ -3643,14 +3643,6 @@ int aoc_audio_close(struct aoc_alsa_stream *alsa_stream) if (alsa_stream->idx == UC_ULTRASONIC_RECORD) ap_record_stop(chip, alsa_stream); else if (ap_filter_capture_stream(alsa_stream)) { - /* Disable spatial module */ - if (chip->mic_spatial_module_enable && !aoc_pcm_is_mmap_raw(alsa_stream)) { - err = aoc_audio_capture_spatial_module_trigger(chip, STOP); - if (err < 0) - pr_err("ERR:%d mic proc spatial module failed to stop!\n", - err); - } - /* Stop the capturing mic*/ if (aoc_audio_capture_active_stream_num(chip) == 0) { pr_info("%s: record stop\n", __func__); @@ -3789,3 +3781,20 @@ int aoc_audio_set_chre_src_aec_timeout(struct aoc_chip *chip, int timeout) return 0; } } + +/* Update PDM mic mask */ +int aoc_audio_mic_mask_set(struct aoc_chip *chip, bool is_voice) +{ + uint32_t value = UINT_MAX; + uint8_t *mask = (uint8_t *)(&value); + int key = is_voice, i; + const int cmd_id = CMD_AUDIO_INPUT_SET_PARAMETER_ID; + const int block = 139; /* ABLOCK_INPUT_PDM_MIC */ + const int component = ASP_ID_NONE; + const int total_lists = min(NUM_OF_BUILTIN_MIC, (int)sizeof(uint32_t)); + + for (i = 0; i < total_lists; i++) + mask[i] = chip->buildin_mic_id_list[i]; + + return aoc_audio_set_parameters(cmd_id, block, component, key, value, chip); +} @@ -938,15 +938,13 @@ static ssize_t reset_store(struct device *dev, struct device_attribute *attr, { struct aoc_prvdata *prvdata = dev_get_drvdata(dev); char reason_str[MAX_RESET_REASON_STRING_LEN + 1]; - size_t reason_str_len = min(MAX_RESET_REASON_STRING_LEN, count); if (aoc_state != AOC_STATE_ONLINE || work_busy(&prvdata->watchdog_work)) { dev_err(dev, "Reset requested while AoC is not online"); return -ENODEV; } - strscpy(reason_str, buf, reason_str_len); - reason_str[reason_str_len] = '\0'; + strscpy(reason_str, buf, sizeof(reason_str)); dev_err(dev, "Reset requested from userspace, reason: %s", reason_str); if (prvdata->no_ap_resets) { @@ -1016,6 +1014,14 @@ static ssize_t sensor_power_enable_store(struct device *dev, static DEVICE_ATTR_WO(sensor_power_enable); +static ssize_t notify_timeout_aoc_status_show(struct device *dev, struct device_attribute *attr, + char *buf) +{ + return 0; +} + +static DEVICE_ATTR_RO(notify_timeout_aoc_status); + static struct attribute *aoc_attrs[] = { &dev_attr_firmware.attr, &dev_attr_revision.attr, @@ -1029,6 +1035,7 @@ static struct attribute *aoc_attrs[] = { &dev_attr_sensor_power_enable.attr, &dev_attr_force_reload.attr, &dev_attr_dmic_power_enable.attr, + &dev_attr_notify_timeout_aoc_status.attr, NULL }; @@ -1571,6 +1578,7 @@ static void aoc_take_offline(struct aoc_prvdata *prvdata) dev_err(prvdata->dev, "timed out waiting for aoc_ack\n"); if (prvdata->protected_by_gsa) dev_err(prvdata->dev, "skipping GSA commands"); + notify_timeout_aoc_status(); return; } } @@ -1637,6 +1645,16 @@ exit: atomic_dec(&prvdata->aoc_process_active); } +void notify_timeout_aoc_status(void) +{ + if (aoc_platform_device == NULL) { + pr_err("AOC platform device is undefined, can't notify aocd\n"); + return; + } + sysfs_notify(&aoc_platform_device->dev.kobj, NULL, + "notify_timeout_aoc_status"); +} + void aoc_set_map_handler(struct aoc_service_dev *dev, aoc_map_handler handler, void *ctx) { @@ -1658,21 +1676,6 @@ void aoc_remove_map_handler(struct aoc_service_dev *dev) } EXPORT_SYMBOL_GPL(aoc_remove_map_handler); -static struct aoc_section_header *find_ramdump_section(struct aoc_ramdump_header - *ramdump_header, int section_type) -{ - int i; - - if (ramdump_header->num_sections != RAMDUMP_NUM_SECTIONS) - return NULL; - - for (i = 0; i < ramdump_header->num_sections; i++) - if (ramdump_header->sections[i].type == section_type) - return &ramdump_header->sections[i]; - - return NULL; -} - static void aoc_watchdog(struct work_struct *work) { struct aoc_prvdata *prvdata = @@ -1696,9 +1699,8 @@ static void aoc_watchdog(struct work_struct *work) int sscd_rc; char crash_info[RAMDUMP_SECTION_CRASH_INFO_SIZE]; int restart_rc; - bool ap_reset = false, invalid_magic; - struct aoc_section_header *crash_info_section = - find_ramdump_section(ramdump_header, SECTION_TYPE_CRASH_INFO); + bool ap_reset = false, valid_magic; + struct aoc_section_header *crash_info_section; prvdata->total_restarts++; @@ -1747,18 +1749,27 @@ static void aoc_watchdog(struct work_struct *work) ramdump_timeout = jiffies + (5 * HZ); while (time_before(jiffies, ramdump_timeout)) { - if (ramdump_header->valid) + valid_magic = memcmp(ramdump_header, RAMDUMP_MAGIC, sizeof(RAMDUMP_MAGIC)) == 0; + if (ramdump_header->valid == 1 && valid_magic) break; msleep(100); } - if (!ramdump_header->valid) { - dev_err(prvdata->dev, "aoc coredump timed out, coredump only contains DRAM\n"); + crash_info_section = &ramdump_header->sections[RAMDUMP_SECTION_CRASH_INFO_INDEX]; + if (crash_info_section->type != SECTION_TYPE_CRASH_INFO) + crash_info_section = NULL; + + if (!(ramdump_header->valid == 1) || !valid_magic) { + if (!(ramdump_header->valid == 1)) + dev_info(prvdata->dev, "aoc coredump timed out, coredump only contains DRAM\n"); + if (!valid_magic) + dev_info(prvdata->dev, "aoc coredump has invalid magic\n"); + if (crash_info_section) { const char *crash_reason = (const char *)ramdump_header + crash_info_section->offset; - bool crash_reason_valid = (strnlen(crash_reason, - sizeof(crash_info)) != 0); + bool crash_reason_valid = crash_reason < (char *)prvdata->dram_virt + + prvdata->dram_size && crash_reason[0] != 0; snprintf(crash_info, sizeof(crash_info), "AoC watchdog : %s (incomplete %u:%u)", @@ -1772,31 +1783,17 @@ static void aoc_watchdog(struct work_struct *work) } } - invalid_magic = memcmp(ramdump_header, RAMDUMP_MAGIC, sizeof(RAMDUMP_MAGIC)); - if (ramdump_header->valid && invalid_magic) { - dev_err(prvdata->dev, - "aoc coredump possibly failed: invalid magic\n"); - if (crash_info_section) { + if (ramdump_header->valid == 1 && valid_magic) { + if (crash_info_section && crash_info_section->flags & RAMDUMP_FLAG_VALID) { const char *crash_reason = (const char *)ramdump_header + crash_info_section->offset; - /* Check that offset was not corrupted and that we are not reading - random bytes */ - bool crash_reason_valid = crash_reason < (char *)prvdata->dram_virt + - prvdata->dram_size && crash_reason[0] != 0; - - if (crash_reason_valid) { - snprintf(crash_info, sizeof(crash_info), - "AoC watchdog : coredump corrupt [%s]", crash_reason); - } else { - snprintf(crash_info, sizeof(crash_info), - "AoC watchdog : coredump corrupt (incomplete %u:%u)", - ramdump_header->breadcrumbs[0], - ramdump_header->breadcrumbs[1]); - } + dev_info(prvdata->dev, + "aoc coredump has valid coredump header, crash reason [%s]", crash_reason); + strscpy(crash_info, crash_reason, sizeof(crash_info)); } else { - dev_err(prvdata->dev, - "could not find crash info section in aoc coredump header"); - strscpy(crash_info, "AoC Watchdog : coredump corrupt", + dev_info(prvdata->dev, + "aoc coredump has valid coredump header, but invalid crash reason"); + strscpy(crash_info, "AoC Watchdog : invalid crash info", sizeof(crash_info)); } } @@ -1824,27 +1821,6 @@ static void aoc_watchdog(struct work_struct *work) sscd_info.segs[0].addr = prvdata->dram_virt; } - if (ramdump_header->valid && !invalid_magic) { - - if (crash_info_section && crash_info_section->flags & RAMDUMP_FLAG_VALID) { - const char *crash_reason = (const char *)ramdump_header + - crash_info_section->offset; - bool crash_reason_valid = crash_reason < (char *)prvdata->dram_virt + - prvdata->dram_size && crash_reason[0] != 0; - - if (crash_reason_valid) - pr_err(">>> valid!!"); - else - pr_err(">>> invalid!!!"); - dev_info(prvdata->dev, "aoc coredump has valid coredump header, crash reason [%s]", - crash_reason); - strscpy(crash_info, crash_reason, sizeof(crash_info)); - } else { - dev_info(prvdata->dev, "aoc coredump has valid coredump header, but invalid crash reason"); - strscpy(crash_info, "AoC Watchdog : invalid crash info", - sizeof(crash_info)); - } - } if (ap_reset) { /* Prefer the user specified reason */ @@ -2553,6 +2529,7 @@ err_memnode: err_chardev: err_failed_prvdata_alloc: err_invalid_dt: + aoc_platform_device = NULL; err_platform_not_null: return rc; } @@ -287,6 +287,8 @@ u32 dt_property(struct device_node *node, const char *key); void configure_crash_interrupts(struct aoc_prvdata *prvdata, bool enable); +void notify_timeout_aoc_status(void); + #define AOC_SERVICE_NAME_LENGTH 32 /* Rings should have the ring flag set, slots = 1, size = ring size diff --git a/aoc_channel_dev.c b/aoc_channel_dev.c index 396b8ab..8e0a513 100644 --- a/aoc_channel_dev.c +++ b/aoc_channel_dev.c @@ -70,6 +70,8 @@ static const char * const channel_service_names[] = { "com.google.usf.non_wake_up", "com.google.chre", "com.google.chre.non_wake_up", + "com.google.bt", + "com.google.bt.non_wake_up", "usf_sh_mem_doorbell", NULL, }; @@ -209,7 +211,8 @@ static int aocc_demux_kthread(void *data) handler_found = 1; if (!node->msg.non_wake_up && (strcmp(dev_name(&service->dev),"com.google.usf") == 0 || - strcmp(dev_name(&service->dev),"com.google.chre") == 0)) { + strcmp(dev_name(&service->dev),"com.google.chre") == 0 || + strcmp(dev_name(&service->dev),"com.google.bt") == 0)) { take_wake_lock = true; } @@ -142,6 +142,7 @@ int aoc_watchdog_restart(struct aoc_prvdata *prvdata, aoc_req_rc = wait_for_aoc_status(prvdata, true); if (aoc_req_rc) { dev_err(prvdata->dev, "timed out waiting for aoc_ack\n"); + notify_timeout_aoc_status(); continue; } dev_info(prvdata->dev, "resetting aoc\n"); @@ -174,6 +175,8 @@ int aoc_watchdog_restart(struct aoc_prvdata *prvdata, if (aoc_req_rc && *(aoc_module_params->aoc_panic_on_req_timeout)) { dev_err(prvdata->dev, "timed out too many times waiting for aoc_ack, triggering kernel panic\n"); + /* Sleep to ensure aocd can process notification of timeout before panic */ + msleep(1000); panic("AoC kernel panic: timed out waiting for aoc_ack"); } |