Lines Matching +full:port +full:- +full:phys
1 // SPDX-License-Identifier: GPL-2.0
4 #include <dt-bindings/soc/qcom,gpr.h>
16 #include <sound/soc-dapm.h>
34 gpr_device_t *gdev = apm->gdev; in q6apm_send_cmd_sync()
36 return audioreach_send_cmd_sync(&gdev->dev, gdev, &apm->result, &apm->lock, in q6apm_send_cmd_sync()
37 NULL, &apm->wait, pkt, rsp_opcode); in q6apm_send_cmd_sync()
46 mutex_lock(&apm->lock); in q6apm_get_audioreach_graph()
47 graph = idr_find(&apm->graph_idr, graph_id); in q6apm_get_audioreach_graph()
48 mutex_unlock(&apm->lock); in q6apm_get_audioreach_graph()
51 kref_get(&graph->refcount); in q6apm_get_audioreach_graph()
55 info = idr_find(&apm->graph_info_idr, graph_id); in q6apm_get_audioreach_graph()
58 return ERR_PTR(-ENODEV); in q6apm_get_audioreach_graph()
62 return ERR_PTR(-ENOMEM); in q6apm_get_audioreach_graph()
64 graph->apm = apm; in q6apm_get_audioreach_graph()
65 graph->info = info; in q6apm_get_audioreach_graph()
66 graph->id = graph_id; in q6apm_get_audioreach_graph()
68 graph->graph = audioreach_alloc_graph_pkt(apm, info); in q6apm_get_audioreach_graph()
69 if (IS_ERR(graph->graph)) { in q6apm_get_audioreach_graph()
70 void *err = graph->graph; in q6apm_get_audioreach_graph()
76 mutex_lock(&apm->lock); in q6apm_get_audioreach_graph()
77 id = idr_alloc(&apm->graph_idr, graph, graph_id, graph_id + 1, GFP_KERNEL); in q6apm_get_audioreach_graph()
79 dev_err(apm->dev, "Unable to allocate graph id (%d)\n", graph_id); in q6apm_get_audioreach_graph()
80 kfree(graph->graph); in q6apm_get_audioreach_graph()
82 mutex_unlock(&apm->lock); in q6apm_get_audioreach_graph()
85 mutex_unlock(&apm->lock); in q6apm_get_audioreach_graph()
87 kref_init(&graph->refcount); in q6apm_get_audioreach_graph()
89 q6apm_send_cmd_sync(apm, graph->graph, 0); in q6apm_get_audioreach_graph()
96 struct audioreach_graph_info *info = graph->info; in audioreach_graph_mgmt_cmd()
97 int num_sub_graphs = info->num_sub_graphs; in audioreach_graph_mgmt_cmd()
101 struct q6apm *apm = graph->apm; in audioreach_graph_mgmt_cmd()
113 mgmt_cmd->num_sub_graphs = num_sub_graphs; in audioreach_graph_mgmt_cmd()
115 param_data = &mgmt_cmd->param_data; in audioreach_graph_mgmt_cmd()
116 param_data->module_instance_id = APM_MODULE_INSTANCE_ID; in audioreach_graph_mgmt_cmd()
117 param_data->param_id = APM_PARAM_ID_SUB_GRAPH_LIST; in audioreach_graph_mgmt_cmd()
118 param_data->param_size = payload_size - APM_MODULE_PARAM_DATA_SIZE; in audioreach_graph_mgmt_cmd()
120 list_for_each_entry(sg, &info->sg_list, node) in audioreach_graph_mgmt_cmd()
121 mgmt_cmd->sub_graph_id_list[i++] = sg->sub_graph_id; in audioreach_graph_mgmt_cmd()
136 apm = graph->apm; in q6apm_put_audioreach_graph()
140 mutex_lock(&apm->lock); in q6apm_put_audioreach_graph()
141 graph = idr_remove(&apm->graph_idr, graph->id); in q6apm_put_audioreach_graph()
142 mutex_unlock(&apm->lock); in q6apm_put_audioreach_graph()
144 kfree(graph->graph); in q6apm_put_audioreach_graph()
161 return apm->state; in q6apm_get_apm_state()
181 list_for_each_entry(sgs, &info->sg_list, node) { in __q6apm_find_module_by_mid()
182 list_for_each_entry(container, &sgs->container_list, node) { in __q6apm_find_module_by_mid()
183 list_for_each_entry(module, &container->modules_list, node) { in __q6apm_find_module_by_mid()
184 if (mid == module->module_id) in __q6apm_find_module_by_mid()
198 if (cfg->direction == SNDRV_PCM_STREAM_CAPTURE) in q6apm_graph_media_format_shmem()
204 return -ENODEV; in q6apm_graph_media_format_shmem()
213 int q6apm_map_memory_regions(struct q6apm_graph *graph, unsigned int dir, phys_addr_t phys, in q6apm_map_memory_regions() argument
222 data = &graph->rx_data; in q6apm_map_memory_regions()
224 data = &graph->tx_data; in q6apm_map_memory_regions()
226 mutex_lock(&graph->lock); in q6apm_map_memory_regions()
228 if (data->buf) { in q6apm_map_memory_regions()
229 mutex_unlock(&graph->lock); in q6apm_map_memory_regions()
235 mutex_unlock(&graph->lock); in q6apm_map_memory_regions()
236 return -ENOMEM; in q6apm_map_memory_regions()
240 data = &graph->rx_data; in q6apm_map_memory_regions()
242 data = &graph->tx_data; in q6apm_map_memory_regions()
244 data->buf = buf; in q6apm_map_memory_regions()
246 buf[0].phys = phys; in q6apm_map_memory_regions()
251 buf[cnt].phys = buf[0].phys + (cnt * period_sz); in q6apm_map_memory_regions()
255 data->num_periods = periods; in q6apm_map_memory_regions()
257 mutex_unlock(&graph->lock); in q6apm_map_memory_regions()
261 dev_err(graph->dev, "Memory_map_regions failed\n"); in q6apm_map_memory_regions()
277 data = &graph->rx_data; in q6apm_unmap_memory_regions()
279 data = &graph->tx_data; in q6apm_unmap_memory_regions()
281 if (!data->mem_map_handle) in q6apm_unmap_memory_regions()
285 graph->port->id); in q6apm_unmap_memory_regions()
290 cmd->mem_map_handle = data->mem_map_handle; in q6apm_unmap_memory_regions()
307 return -ENODEV; in q6apm_remove_initial_silence()
319 return -ENODEV; in q6apm_remove_trailing_silence()
331 return -ENODEV; in q6apm_enable_compress_module()
345 return -ENODEV; in q6apm_set_real_module_id()
358 return -EINVAL; in q6apm_set_real_module_id()
368 struct audioreach_graph_info *info = graph->info; in q6apm_graph_media_format_pcm()
373 list_for_each_entry(sgs, &info->sg_list, node) { in q6apm_graph_media_format_pcm()
374 list_for_each_entry(container, &sgs->container_list, node) { in q6apm_graph_media_format_pcm()
375 list_for_each_entry(module, &container->modules_list, node) { in q6apm_graph_media_format_pcm()
376 if ((module->module_id == MODULE_ID_WR_SHARED_MEM_EP) || in q6apm_graph_media_format_pcm()
377 (module->module_id == MODULE_ID_RD_SHARED_MEM_EP)) in q6apm_graph_media_format_pcm()
396 return -ENODEV; in q6apm_graph_get_tx_shmem_module_iid()
398 return module->instance_id; in q6apm_graph_get_tx_shmem_module_iid()
408 return -ENODEV; in q6apm_graph_get_rx_shmem_module_iid()
410 return module->instance_id; in q6apm_graph_get_rx_shmem_module_iid()
425 graph->rx_data.dsp_buf | (len << APM_WRITE_TOKEN_LEN_SHIFT), in q6apm_write_async()
426 graph->port->id, iid); in q6apm_write_async()
432 mutex_lock(&graph->lock); in q6apm_write_async()
433 ab = &graph->rx_data.buf[graph->rx_data.dsp_buf]; in q6apm_write_async()
435 write_buffer->buf_addr_lsw = lower_32_bits(ab->phys); in q6apm_write_async()
436 write_buffer->buf_addr_msw = upper_32_bits(ab->phys); in q6apm_write_async()
437 write_buffer->buf_size = len; in q6apm_write_async()
438 write_buffer->timestamp_lsw = lsw_ts; in q6apm_write_async()
439 write_buffer->timestamp_msw = msw_ts; in q6apm_write_async()
440 write_buffer->mem_map_handle = graph->rx_data.mem_map_handle; in q6apm_write_async()
441 write_buffer->flags = wflags; in q6apm_write_async()
443 graph->rx_data.dsp_buf++; in q6apm_write_async()
445 if (graph->rx_data.dsp_buf >= graph->rx_data.num_periods) in q6apm_write_async()
446 graph->rx_data.dsp_buf = 0; in q6apm_write_async()
448 mutex_unlock(&graph->lock); in q6apm_write_async()
450 rc = gpr_send_port_pkt(graph->port, pkt); in q6apm_write_async()
461 struct audioreach_graph_data *port; in q6apm_read() local
468 graph->tx_data.dsp_buf, graph->port->id, iid); in q6apm_read()
474 mutex_lock(&graph->lock); in q6apm_read()
475 port = &graph->tx_data; in q6apm_read()
476 ab = &port->buf[port->dsp_buf]; in q6apm_read()
478 read_buffer->buf_addr_lsw = lower_32_bits(ab->phys); in q6apm_read()
479 read_buffer->buf_addr_msw = upper_32_bits(ab->phys); in q6apm_read()
480 read_buffer->mem_map_handle = port->mem_map_handle; in q6apm_read()
481 read_buffer->buf_size = ab->size; in q6apm_read()
483 port->dsp_buf++; in q6apm_read()
485 if (port->dsp_buf >= port->num_periods) in q6apm_read()
486 port->dsp_buf = 0; in q6apm_read()
488 mutex_unlock(&graph->lock); in q6apm_read()
490 rc = gpr_send_port_pkt(graph->port, pkt); in q6apm_read()
504 struct gpr_hdr *hdr = &data->hdr; in graph_callback()
505 struct device *dev = graph->dev; in graph_callback()
507 phys_addr_t phys; in graph_callback() local
510 result = data->payload; in graph_callback()
512 switch (hdr->opcode) { in graph_callback()
514 if (!graph->ar_graph) in graph_callback()
517 mutex_lock(&graph->lock); in graph_callback()
518 token = hdr->token & APM_WRITE_TOKEN_MASK; in graph_callback()
520 done = data->payload; in graph_callback()
521 phys = graph->rx_data.buf[token].phys; in graph_callback()
522 mutex_unlock(&graph->lock); in graph_callback()
524 if (lower_32_bits(phys) == done->buf_addr_lsw && in graph_callback()
525 upper_32_bits(phys) == done->buf_addr_msw) { in graph_callback()
526 graph->result.opcode = hdr->opcode; in graph_callback()
527 graph->result.status = done->status; in graph_callback()
528 if (graph->cb) in graph_callback()
529 graph->cb(client_event, hdr->token, data->payload, graph->priv); in graph_callback()
531 dev_err(dev, "WR BUFF Unexpected addr %08x-%08x\n", done->buf_addr_lsw, in graph_callback()
532 done->buf_addr_msw); in graph_callback()
537 graph->result.opcode = hdr->opcode; in graph_callback()
538 graph->result.status = 0; in graph_callback()
539 rsp = data->payload; in graph_callback()
541 if (hdr->token == SNDRV_PCM_STREAM_PLAYBACK) in graph_callback()
542 graph->rx_data.mem_map_handle = rsp->mem_map_handle; in graph_callback()
544 graph->tx_data.mem_map_handle = rsp->mem_map_handle; in graph_callback()
546 wake_up(&graph->cmd_wait); in graph_callback()
549 if (!graph->ar_graph) in graph_callback()
552 mutex_lock(&graph->lock); in graph_callback()
553 rd_done = data->payload; in graph_callback()
554 phys = graph->tx_data.buf[hdr->token].phys; in graph_callback()
555 mutex_unlock(&graph->lock); in graph_callback()
557 if (upper_32_bits(phys) == rd_done->buf_addr_msw && in graph_callback()
558 lower_32_bits(phys) == rd_done->buf_addr_lsw) { in graph_callback()
559 graph->result.opcode = hdr->opcode; in graph_callback()
560 graph->result.status = rd_done->status; in graph_callback()
561 if (graph->cb) in graph_callback()
562 graph->cb(client_event, hdr->token, data->payload, graph->priv); in graph_callback()
564 dev_err(dev, "RD BUFF Unexpected addr %08x-%08x\n", rd_done->buf_addr_lsw, in graph_callback()
565 rd_done->buf_addr_msw); in graph_callback()
570 if (graph->cb) in graph_callback()
571 graph->cb(client_event, hdr->token, data->payload, graph->priv); in graph_callback()
574 switch (result->opcode) { in graph_callback()
576 graph->result.opcode = result->opcode; in graph_callback()
577 graph->result.status = 0; in graph_callback()
578 if (hdr->token == SNDRV_PCM_STREAM_PLAYBACK) in graph_callback()
579 graph->rx_data.mem_map_handle = 0; in graph_callback()
581 graph->tx_data.mem_map_handle = 0; in graph_callback()
583 wake_up(&graph->cmd_wait); in graph_callback()
588 graph->result.opcode = result->opcode; in graph_callback()
589 graph->result.status = result->status; in graph_callback()
590 if (result->status) in graph_callback()
592 result->status, result->opcode); in graph_callback()
593 wake_up(&graph->cmd_wait); in graph_callback()
608 struct q6apm *apm = dev_get_drvdata(dev->parent); in q6apm_graph_open()
621 ret = -ENOMEM; in q6apm_graph_open()
625 graph->apm = apm; in q6apm_graph_open()
626 graph->priv = priv; in q6apm_graph_open()
627 graph->cb = cb; in q6apm_graph_open()
628 graph->info = ar_graph->info; in q6apm_graph_open()
629 graph->ar_graph = ar_graph; in q6apm_graph_open()
630 graph->id = ar_graph->id; in q6apm_graph_open()
631 graph->dev = dev; in q6apm_graph_open()
633 mutex_init(&graph->lock); in q6apm_graph_open()
634 init_waitqueue_head(&graph->cmd_wait); in q6apm_graph_open()
636 graph->port = gpr_alloc_port(apm->gdev, dev, graph_callback, graph); in q6apm_graph_open()
637 if (IS_ERR(graph->port)) { in q6apm_graph_open()
638 ret = PTR_ERR(graph->port); in q6apm_graph_open()
647 kref_put(&ar_graph->refcount, q6apm_put_audioreach_graph); in q6apm_graph_open()
654 struct audioreach_graph *ar_graph = graph->ar_graph; in q6apm_graph_close()
656 graph->ar_graph = NULL; in q6apm_graph_close()
657 kref_put(&ar_graph->refcount, q6apm_put_audioreach_graph); in q6apm_graph_close()
658 gpr_free_port(graph->port); in q6apm_graph_close()
667 return audioreach_graph_mgmt_cmd(graph->ar_graph, APM_CMD_GRAPH_PREPARE); in q6apm_graph_prepare()
673 struct audioreach_graph *ar_graph = graph->ar_graph; in q6apm_graph_start()
676 if (ar_graph->start_count == 0) in q6apm_graph_start()
679 ar_graph->start_count++; in q6apm_graph_start()
687 struct audioreach_graph *ar_graph = graph->ar_graph; in q6apm_graph_stop()
689 if (--ar_graph->start_count > 0) in q6apm_graph_stop()
698 return audioreach_graph_mgmt_cmd(graph->ar_graph, APM_CMD_GRAPH_FLUSH); in q6apm_graph_flush()
713 #define APM_AUDIO_DRV_NAME "q6apm-audio"
723 struct device *dev = &gdev->dev; in apm_probe()
729 return -ENOMEM; in apm_probe()
733 mutex_init(&apm->lock); in apm_probe()
734 apm->dev = dev; in apm_probe()
735 apm->gdev = gdev; in apm_probe()
736 init_waitqueue_head(&apm->wait); in apm_probe()
738 INIT_LIST_HEAD(&apm->widget_list); in apm_probe()
739 idr_init(&apm->graph_idr); in apm_probe()
740 idr_init(&apm->graph_info_idr); in apm_probe()
741 idr_init(&apm->sub_graphs_idr); in apm_probe()
742 idr_init(&apm->containers_idr); in apm_probe()
744 idr_init(&apm->modules_idr); in apm_probe()
756 return of_platform_populate(dev->of_node, NULL, NULL, dev); in apm_probe()
761 struct audioreach_graph_info *info = graph->info; in q6apm_find_module_by_mid()
762 struct q6apm *apm = graph->apm; in q6apm_find_module_by_mid()
771 struct q6apm *apm = dev_get_drvdata(&gdev->dev); in apm_callback()
772 struct device *dev = &gdev->dev; in apm_callback()
774 struct gpr_hdr *hdr = &data->hdr; in apm_callback()
776 result = data->payload; in apm_callback()
778 switch (hdr->opcode) { in apm_callback()
780 apm->result.opcode = hdr->opcode; in apm_callback()
781 apm->result.status = 0; in apm_callback()
783 apm->state = result->opcode; in apm_callback()
784 wake_up(&apm->wait); in apm_callback()
787 switch (result->opcode) { in apm_callback()
795 apm->result.opcode = result->opcode; in apm_callback()
796 apm->result.status = result->status; in apm_callback()
797 if (result->status) in apm_callback()
798 dev_err(dev, "Error (%d) Processing 0x%08x cmd\n", result->status, in apm_callback()
799 result->opcode); in apm_callback()
800 wake_up(&apm->wait); in apm_callback()
825 .name = "qcom-apm",