Lines Matching +full:rpmsg +full:- +full:channel +full:- +full:name

1 // SPDX-License-Identifier: GPL-2.0
14 #include <linux/rpmsg.h>
29 const char *name;
76 * sysmon_send_event() - send notification of other remote's SSR event
87 len = snprintf(req, sizeof(req), "ssr:%s:%s", event->subsys_name,
88 sysmon_state_string[event->ssr_event]);
92 mutex_lock(&sysmon->lock);
93 reinit_completion(&sysmon->comp);
94 sysmon->ssr_ack = false;
96 ret = rpmsg_send(sysmon->ept, req, len);
98 dev_err(sysmon->dev, "failed to send sysmon event\n");
102 ret = wait_for_completion_timeout(&sysmon->comp,
105 dev_err(sysmon->dev, "timeout waiting for sysmon ack\n");
109 if (!sysmon->ssr_ack)
110 dev_err(sysmon->dev, "unexpected response to sysmon event\n");
113 mutex_unlock(&sysmon->lock);
117 * sysmon_request_shutdown() - request graceful shutdown of remote
128 mutex_lock(&sysmon->lock);
129 reinit_completion(&sysmon->comp);
130 sysmon->ssr_ack = false;
132 ret = rpmsg_send(sysmon->ept, req, strlen(req) + 1);
134 dev_err(sysmon->dev, "send sysmon shutdown request failed\n");
138 ret = wait_for_completion_timeout(&sysmon->comp,
141 dev_err(sysmon->dev, "timeout waiting for sysmon ack\n");
145 if (!sysmon->ssr_ack)
146 dev_err(sysmon->dev,
152 mutex_unlock(&sysmon->lock);
165 return -EINVAL;
168 sysmon->ssr_ack = true;
170 complete(&sysmon->comp);
294 complete(&sysmon->ind_comp);
312 ret = wait_for_completion_timeout(&sysmon->shutdown_comp, 10 * HZ);
316 ret = try_wait_for_completion(&sysmon->ind_comp);
320 dev_err(sysmon->dev, "timeout waiting for shutdown ack\n");
325 * ssctl_request_shutdown() - request shutdown via SSCTL QMI service
337 reinit_completion(&sysmon->ind_comp);
338 reinit_completion(&sysmon->shutdown_comp);
339 ret = qmi_txn_init(&sysmon->qmi, &txn, ssctl_shutdown_resp_ei, &resp);
341 dev_err(sysmon->dev, "failed to allocate QMI txn\n");
345 ret = qmi_send_request(&sysmon->qmi, &sysmon->ssctl, &txn,
348 dev_err(sysmon->dev, "failed to send shutdown request\n");
355 dev_err(sysmon->dev, "timeout waiting for shutdown response\n");
357 dev_err(sysmon->dev, "shutdown request rejected\n");
359 dev_dbg(sysmon->dev, "shutdown request completed\n");
363 if (sysmon->shutdown_irq > 0)
370 * ssctl_send_event() - send notification of other remote's SSR event
383 ret = qmi_txn_init(&sysmon->qmi, &txn, ssctl_subsys_event_resp_ei, &resp);
385 dev_err(sysmon->dev, "failed to allocate QMI txn\n");
390 strscpy(req.subsys_name, event->subsys_name, sizeof(req.subsys_name));
392 req.event = event->ssr_event;
396 ret = qmi_send_request(&sysmon->qmi, &sysmon->ssctl, &txn,
400 dev_err(sysmon->dev, "failed to send subsystem event\n");
407 dev_err(sysmon->dev, "timeout waiting for subsystem event response\n");
409 dev_err(sysmon->dev, "subsystem event rejected\n");
411 dev_dbg(sysmon->dev, "subsystem event accepted\n");
415 * ssctl_new_server() - QMI callback indicating a new service
419 * Return: 0 if we're interested in this service, -EINVAL otherwise.
425 switch (svc->version) {
427 if (svc->instance != 0)
428 return -EINVAL;
429 if (strcmp(sysmon->name, "modem"))
430 return -EINVAL;
433 if (svc->instance != sysmon->ssctl_instance)
434 return -EINVAL;
437 return -EINVAL;
440 sysmon->ssctl_version = svc->version;
442 sysmon->ssctl.sq_family = AF_QIPCRTR;
443 sysmon->ssctl.sq_node = svc->node;
444 sysmon->ssctl.sq_port = svc->port;
446 svc->priv = sysmon;
448 complete(&sysmon->ssctl_comp);
454 * ssctl_del_server() - QMI callback indicating that @svc is removed
460 struct qcom_sysmon *sysmon = svc->priv;
462 sysmon->ssctl_version = 0;
475 .subsys_name = sysmon->name,
479 mutex_lock(&sysmon->state_lock);
480 sysmon->state = SSCTL_SSR_EVENT_BEFORE_POWERUP;
482 mutex_unlock(&sysmon->state_lock);
488 * sysmon_start() - start callback for the sysmon remoteproc subdevice
502 .subsys_name = sysmon->name,
506 reinit_completion(&sysmon->ssctl_comp);
507 mutex_lock(&sysmon->state_lock);
508 sysmon->state = SSCTL_SSR_EVENT_AFTER_POWERUP;
510 mutex_unlock(&sysmon->state_lock);
514 mutex_lock(&target->state_lock);
515 if (target == sysmon || target->state != SSCTL_SSR_EVENT_AFTER_POWERUP) {
516 mutex_unlock(&target->state_lock);
520 event.subsys_name = target->name;
521 event.ssr_event = target->state;
523 if (sysmon->ssctl_version == 2)
525 else if (sysmon->ept)
527 mutex_unlock(&target->state_lock);
538 .subsys_name = sysmon->name,
542 sysmon->shutdown_acked = false;
544 mutex_lock(&sysmon->state_lock);
545 sysmon->state = SSCTL_SSR_EVENT_BEFORE_SHUTDOWN;
547 mutex_unlock(&sysmon->state_lock);
553 if (sysmon->ssctl_instance) {
554 if (!wait_for_completion_timeout(&sysmon->ssctl_comp, HZ / 2))
555 dev_err(sysmon->dev, "timeout waiting for ssctl service\n");
558 if (sysmon->ssctl_version)
559 sysmon->shutdown_acked = ssctl_request_shutdown(sysmon);
560 else if (sysmon->ept)
561 sysmon->shutdown_acked = sysmon_request_shutdown(sysmon);
569 .subsys_name = sysmon->name,
573 mutex_lock(&sysmon->state_lock);
574 sysmon->state = SSCTL_SSR_EVENT_AFTER_SHUTDOWN;
576 mutex_unlock(&sysmon->state_lock);
580 * sysmon_notify() - notify sysmon target of another's SSR
591 /* Skip non-running rprocs and the originating instance */
592 if (sysmon->state != SSCTL_SSR_EVENT_AFTER_POWERUP ||
593 !strcmp(sysmon_event->subsys_name, sysmon->name)) {
594 dev_dbg(sysmon->dev, "not notifying %s\n", sysmon->name);
599 if (sysmon->ssctl_version == 2)
601 else if (sysmon->ept)
611 complete(&sysmon->shutdown_comp);
617 * qcom_add_sysmon_subdev() - create a sysmon subdev for the given remoteproc
619 * @name: name of this subdev, to use in SSR
625 const char *name,
633 return ERR_PTR(-ENOMEM);
635 sysmon->dev = rproc->dev.parent;
636 sysmon->rproc = rproc;
638 sysmon->name = name;
639 sysmon->ssctl_instance = ssctl_instance;
641 init_completion(&sysmon->comp);
642 init_completion(&sysmon->ind_comp);
643 init_completion(&sysmon->shutdown_comp);
644 init_completion(&sysmon->ssctl_comp);
645 mutex_init(&sysmon->lock);
646 mutex_init(&sysmon->state_lock);
648 sysmon->shutdown_irq = of_irq_get_byname(sysmon->dev->of_node,
649 "shutdown-ack");
650 if (sysmon->shutdown_irq < 0) {
651 if (sysmon->shutdown_irq != -ENODATA) {
652 dev_err(sysmon->dev,
653 "failed to retrieve shutdown-ack IRQ\n");
654 ret = sysmon->shutdown_irq;
659 ret = devm_request_threaded_irq(sysmon->dev,
660 sysmon->shutdown_irq,
663 "q6v5 shutdown-ack", sysmon);
665 dev_err(sysmon->dev,
666 "failed to acquire shutdown-ack IRQ\n");
672 ret = qmi_handle_init(&sysmon->qmi, SSCTL_MAX_MSG_LEN, &ssctl_ops,
675 dev_err(sysmon->dev, "failed to initialize qmi handle\n");
680 qmi_add_lookup(&sysmon->qmi, 43, 0, 0);
682 sysmon->subdev.prepare = sysmon_prepare;
683 sysmon->subdev.start = sysmon_start;
684 sysmon->subdev.stop = sysmon_stop;
685 sysmon->subdev.unprepare = sysmon_unprepare;
687 rproc_add_subdev(rproc, &sysmon->subdev);
689 sysmon->nb.notifier_call = sysmon_notify;
690 blocking_notifier_chain_register(&sysmon_notifiers, &sysmon->nb);
693 list_add(&sysmon->node, &sysmon_list);
701 * qcom_remove_sysmon_subdev() - release a qcom_sysmon
710 list_del(&sysmon->node);
713 blocking_notifier_chain_unregister(&sysmon_notifiers, &sysmon->nb);
715 rproc_remove_subdev(sysmon->rproc, &sysmon->subdev);
717 qmi_handle_release(&sysmon->qmi);
724 * qcom_sysmon_shutdown_acked() - query the success of the last shutdown
735 return sysmon && sysmon->shutdown_acked;
740 * sysmon_probe() - probe sys_mon channel
741 * @rpdev: rpmsg device handle
744 * this rpmsg device with said sysmon context.
753 rproc = rproc_get_by_child(&rpdev->dev);
755 dev_err(&rpdev->dev, "sysmon device not child of rproc\n");
756 return -EINVAL;
761 if (sysmon->rproc == rproc)
766 dev_err(&rpdev->dev, "no sysmon associated with parent rproc\n");
768 return -EINVAL;
773 rpdev->ept->priv = sysmon;
774 sysmon->ept = rpdev->ept;
780 * sysmon_remove() - sys_mon channel remove handler
781 * @rpdev: rpmsg device handle
783 * Disassociate the rpmsg device with the sysmon instance.
787 struct qcom_sysmon *sysmon = rpdev->ept->priv;
789 sysmon->ept = NULL;
803 .name = "qcom_sysmon",