^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Copyright IBM Corp. 2016
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) * Author(s): Martin Schwidefsky <schwidefsky@de.ibm.com>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) * Adjunct processor bus, queue related code.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #define KMSG_COMPONENT "ap"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #define pr_fmt(fmt) KMSG_COMPONENT ": " fmt
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/init.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <asm/facility.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include "ap_bus.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include "ap_debug.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) static void __ap_flush_queue(struct ap_queue *aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) * ap_queue_enable_irq(): Enable interrupt support on this AP queue.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * @qid: The AP queue number
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) * @ind: the notification indicator byte
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) * Enables interruption on AP queue via ap_aqic(). Based on the return
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) * value it waits a while and tests the AP queue if interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) * have been switched on using ap_test_queue().
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) static int ap_queue_enable_irq(struct ap_queue *aq, void *ind)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) struct ap_qirq_ctrl qirqctrl = { 0 };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) qirqctrl.ir = 1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) qirqctrl.isc = AP_ISC;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) status = ap_aqic(aq->qid, qirqctrl, ind);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) case AP_RESPONSE_OTHERWISE_CHANGED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) case AP_RESPONSE_Q_NOT_AVAIL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) case AP_RESPONSE_DECONFIGURED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) case AP_RESPONSE_CHECKSTOPPED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) case AP_RESPONSE_INVALID_ADDRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) pr_err("Registering adapter interrupts for AP device %02x.%04x failed\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) AP_QID_CARD(aq->qid),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) case AP_RESPONSE_RESET_IN_PROGRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) case AP_RESPONSE_BUSY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) return -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) * __ap_send(): Send message to adjunct processor queue.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) * @qid: The AP queue number
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) * @psmid: The program supplied message identifier
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) * @msg: The message text
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) * @length: The message length
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) * @special: Special Bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65) * Returns AP queue status structure.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) * Condition code 1 on NQAP can't happen because the L bit is 1.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) * Condition code 2 on NQAP also means the send is incomplete,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) * because a segment boundary was reached. The NQAP is repeated.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) static inline struct ap_queue_status
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) __ap_send(ap_qid_t qid, unsigned long long psmid, void *msg, size_t length,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) int special)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) if (special)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) qid |= 0x400000UL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) return ap_nqap(qid, psmid, msg, length);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) int ap_send(ap_qid_t qid, unsigned long long psmid, void *msg, size_t length)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) status = __ap_send(qid, psmid, msg, length, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) case AP_RESPONSE_Q_FULL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) case AP_RESPONSE_RESET_IN_PROGRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) return -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) case AP_RESPONSE_REQ_FAC_NOT_INST:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) default: /* Device is gone. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) EXPORT_SYMBOL(ap_send);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) int ap_recv(ap_qid_t qid, unsigned long long *psmid, void *msg, size_t length)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) if (msg == NULL)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) return -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) status = ap_dqap(qid, psmid, msg, length);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) case AP_RESPONSE_NO_PENDING_REPLY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) if (status.queue_empty)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) return -ENOENT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) return -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) case AP_RESPONSE_RESET_IN_PROGRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) return -EBUSY;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) EXPORT_SYMBOL(ap_recv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) /* State machine definitions and helpers */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) static enum ap_sm_wait ap_sm_nop(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) * ap_sm_recv(): Receive pending reply messages from an AP queue but do
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) * not change the state of the device.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) * @aq: pointer to the AP queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) * Returns AP_SM_WAIT_NONE, AP_SM_WAIT_AGAIN, or AP_SM_WAIT_INTERRUPT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) static struct ap_queue_status ap_sm_recv(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) struct ap_message *ap_msg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) bool found = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) status = ap_dqap(aq->qid, &aq->reply->psmid,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) aq->reply->msg, aq->reply->len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) aq->queue_count = max_t(int, 0, aq->queue_count - 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) if (!status.queue_empty && !aq->queue_count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) aq->queue_count++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) if (aq->queue_count > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) mod_timer(&aq->timeout,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) jiffies + aq->request_timeout);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) list_for_each_entry(ap_msg, &aq->pendingq, list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) if (ap_msg->psmid != aq->reply->psmid)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) continue;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) list_del_init(&ap_msg->list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) aq->pendingq_count--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) ap_msg->receive(aq, ap_msg, aq->reply);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) found = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) if (!found) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) AP_DBF_WARN("%s unassociated reply psmid=0x%016llx on 0x%02x.%04x\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) __func__, aq->reply->psmid,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) AP_QID_CARD(aq->qid), AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) case AP_RESPONSE_NO_PENDING_REPLY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) if (!status.queue_empty || aq->queue_count <= 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) /* The card shouldn't forget requests but who knows. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) aq->queue_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) list_splice_init(&aq->pendingq, &aq->requestq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) aq->requestq_count += aq->pendingq_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) aq->pendingq_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) return status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) * ap_sm_read(): Receive pending reply messages from an AP queue.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) * @aq: pointer to the AP queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) * Returns AP_SM_WAIT_NONE, AP_SM_WAIT_AGAIN, or AP_SM_WAIT_INTERRUPT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) static enum ap_sm_wait ap_sm_read(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) if (!aq->reply)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) status = ap_sm_recv(aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) if (aq->queue_count > 0) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) aq->sm_state = AP_SM_STATE_WORKING;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) return AP_SM_WAIT_AGAIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) aq->sm_state = AP_SM_STATE_IDLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) case AP_RESPONSE_NO_PENDING_REPLY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) if (aq->queue_count > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) return aq->interrupt ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) AP_SM_WAIT_INTERRUPT : AP_SM_WAIT_TIMEOUT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) aq->sm_state = AP_SM_STATE_IDLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) aq->dev_state = AP_DEV_STATE_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) aq->last_err_rc = status.response_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) AP_DBF_WARN("%s RC 0x%02x on 0x%02x.%04x -> AP_DEV_STATE_ERROR\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) __func__, status.response_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) AP_QID_CARD(aq->qid), AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) * ap_sm_write(): Send messages from the request queue to an AP queue.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) * @aq: pointer to the AP queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) * Returns AP_SM_WAIT_NONE, AP_SM_WAIT_AGAIN, or AP_SM_WAIT_INTERRUPT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) static enum ap_sm_wait ap_sm_write(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) struct ap_message *ap_msg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) ap_qid_t qid = aq->qid;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) if (aq->requestq_count <= 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) /* Start the next request on the queue. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) ap_msg = list_entry(aq->requestq.next, struct ap_message, list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) #ifdef CONFIG_ZCRYPT_DEBUG
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) if (ap_msg->fi.action == AP_FI_ACTION_NQAP_QID_INVAL) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) AP_DBF_WARN("%s fi cmd 0x%04x: forcing invalid qid 0xFF00\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) __func__, ap_msg->fi.cmd);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) qid = 0xFF00;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) status = __ap_send(qid, ap_msg->psmid,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) ap_msg->msg, ap_msg->len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) ap_msg->flags & AP_MSG_FLAG_SPECIAL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) aq->queue_count = max_t(int, 1, aq->queue_count + 1);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) if (aq->queue_count == 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) mod_timer(&aq->timeout, jiffies + aq->request_timeout);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) list_move_tail(&ap_msg->list, &aq->pendingq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) aq->requestq_count--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) aq->pendingq_count++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) if (aq->queue_count < aq->card->queue_depth) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) aq->sm_state = AP_SM_STATE_WORKING;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) return AP_SM_WAIT_AGAIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) case AP_RESPONSE_Q_FULL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) aq->sm_state = AP_SM_STATE_QUEUE_FULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) return aq->interrupt ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) AP_SM_WAIT_INTERRUPT : AP_SM_WAIT_TIMEOUT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) case AP_RESPONSE_RESET_IN_PROGRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) aq->sm_state = AP_SM_STATE_RESET_WAIT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) return AP_SM_WAIT_TIMEOUT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) case AP_RESPONSE_INVALID_DOMAIN:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) AP_DBF(DBF_WARN, "AP_RESPONSE_INVALID_DOMAIN on NQAP\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) case AP_RESPONSE_MESSAGE_TOO_BIG:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) case AP_RESPONSE_REQ_FAC_NOT_INST:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) list_del_init(&ap_msg->list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) aq->requestq_count--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) ap_msg->rc = -EINVAL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) ap_msg->receive(aq, ap_msg, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) return AP_SM_WAIT_AGAIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) aq->dev_state = AP_DEV_STATE_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) aq->last_err_rc = status.response_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) AP_DBF_WARN("%s RC 0x%02x on 0x%02x.%04x -> AP_DEV_STATE_ERROR\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) __func__, status.response_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) AP_QID_CARD(aq->qid), AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) * ap_sm_read_write(): Send and receive messages to/from an AP queue.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) * @aq: pointer to the AP queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) * Returns AP_SM_WAIT_NONE, AP_SM_WAIT_AGAIN, or AP_SM_WAIT_INTERRUPT
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) static enum ap_sm_wait ap_sm_read_write(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) return min(ap_sm_read(aq), ap_sm_write(aq));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) * ap_sm_reset(): Reset an AP queue.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) * @qid: The AP queue number
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) * Submit the Reset command to an AP queue.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) static enum ap_sm_wait ap_sm_reset(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) status = ap_rapq(aq->qid);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) case AP_RESPONSE_RESET_IN_PROGRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) aq->sm_state = AP_SM_STATE_RESET_WAIT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) aq->interrupt = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) return AP_SM_WAIT_TIMEOUT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) aq->dev_state = AP_DEV_STATE_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) aq->last_err_rc = status.response_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) AP_DBF_WARN("%s RC 0x%02x on 0x%02x.%04x -> AP_DEV_STATE_ERROR\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) __func__, status.response_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) AP_QID_CARD(aq->qid), AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) * ap_sm_reset_wait(): Test queue for completion of the reset operation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) * @aq: pointer to the AP queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) * Returns AP_POLL_IMMEDIATELY, AP_POLL_AFTER_TIMEROUT or 0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) static enum ap_sm_wait ap_sm_reset_wait(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) void *lsi_ptr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) if (aq->queue_count > 0 && aq->reply)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) /* Try to read a completed message and get the status */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) status = ap_sm_recv(aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) /* Get the status with TAPQ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) status = ap_tapq(aq->qid, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) lsi_ptr = ap_airq_ptr();
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) if (lsi_ptr && ap_queue_enable_irq(aq, lsi_ptr) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) aq->sm_state = AP_SM_STATE_SETIRQ_WAIT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) aq->sm_state = (aq->queue_count > 0) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) AP_SM_STATE_WORKING : AP_SM_STATE_IDLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) return AP_SM_WAIT_AGAIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) case AP_RESPONSE_BUSY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) case AP_RESPONSE_RESET_IN_PROGRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) return AP_SM_WAIT_TIMEOUT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) case AP_RESPONSE_Q_NOT_AVAIL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) case AP_RESPONSE_DECONFIGURED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) case AP_RESPONSE_CHECKSTOPPED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) aq->dev_state = AP_DEV_STATE_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) aq->last_err_rc = status.response_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) AP_DBF_WARN("%s RC 0x%02x on 0x%02x.%04x -> AP_DEV_STATE_ERROR\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) __func__, status.response_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) AP_QID_CARD(aq->qid), AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) * ap_sm_setirq_wait(): Test queue for completion of the irq enablement
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) * @aq: pointer to the AP queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) * Returns AP_POLL_IMMEDIATELY, AP_POLL_AFTER_TIMEROUT or 0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) static enum ap_sm_wait ap_sm_setirq_wait(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) struct ap_queue_status status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) if (aq->queue_count > 0 && aq->reply)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) /* Try to read a completed message and get the status */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) status = ap_sm_recv(aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) /* Get the status with TAPQ */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) status = ap_tapq(aq->qid, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) if (status.irq_enabled == 1) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) /* Irqs are now enabled */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) aq->interrupt = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) aq->sm_state = (aq->queue_count > 0) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) AP_SM_STATE_WORKING : AP_SM_STATE_IDLE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) switch (status.response_code) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) if (aq->queue_count > 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) return AP_SM_WAIT_AGAIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) fallthrough;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) case AP_RESPONSE_NO_PENDING_REPLY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) return AP_SM_WAIT_TIMEOUT;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) aq->dev_state = AP_DEV_STATE_ERROR;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) aq->last_err_rc = status.response_code;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) AP_DBF_WARN("%s RC 0x%02x on 0x%02x.%04x -> AP_DEV_STATE_ERROR\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) __func__, status.response_code,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) AP_QID_CARD(aq->qid), AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) * AP state machine jump table
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) static ap_func_t *ap_jumptable[NR_AP_SM_STATES][NR_AP_SM_EVENTS] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) [AP_SM_STATE_RESET_START] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) [AP_SM_EVENT_POLL] = ap_sm_reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) [AP_SM_EVENT_TIMEOUT] = ap_sm_nop,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) [AP_SM_STATE_RESET_WAIT] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) [AP_SM_EVENT_POLL] = ap_sm_reset_wait,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) [AP_SM_EVENT_TIMEOUT] = ap_sm_nop,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) [AP_SM_STATE_SETIRQ_WAIT] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) [AP_SM_EVENT_POLL] = ap_sm_setirq_wait,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) [AP_SM_EVENT_TIMEOUT] = ap_sm_nop,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) [AP_SM_STATE_IDLE] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) [AP_SM_EVENT_POLL] = ap_sm_write,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) [AP_SM_EVENT_TIMEOUT] = ap_sm_nop,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) [AP_SM_STATE_WORKING] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) [AP_SM_EVENT_POLL] = ap_sm_read_write,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) [AP_SM_EVENT_TIMEOUT] = ap_sm_reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) [AP_SM_STATE_QUEUE_FULL] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) [AP_SM_EVENT_POLL] = ap_sm_read,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) [AP_SM_EVENT_TIMEOUT] = ap_sm_reset,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) enum ap_sm_wait ap_sm_event(struct ap_queue *aq, enum ap_sm_event event)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) if (aq->dev_state > AP_DEV_STATE_UNINITIATED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) return ap_jumptable[aq->sm_state][event](aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) return AP_SM_WAIT_NONE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) enum ap_sm_wait ap_sm_event_loop(struct ap_queue *aq, enum ap_sm_event event)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) enum ap_sm_wait wait;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) while ((wait = ap_sm_event(aq, event)) == AP_SM_WAIT_AGAIN)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) ;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) return wait;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) * AP queue related attributes.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) static ssize_t request_count_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) struct device_attribute *attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) bool valid = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) u64 req_cnt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) if (aq->dev_state > AP_DEV_STATE_UNINITIATED) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) req_cnt = aq->total_request_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) valid = true;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) if (valid)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) return scnprintf(buf, PAGE_SIZE, "%llu\n", req_cnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) return scnprintf(buf, PAGE_SIZE, "-\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) static ssize_t request_count_store(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) struct device_attribute *attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) const char *buf, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) aq->total_request_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) static DEVICE_ATTR_RW(request_count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) static ssize_t requestq_count_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) unsigned int reqq_cnt = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) if (aq->dev_state > AP_DEV_STATE_UNINITIATED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) reqq_cnt = aq->requestq_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) return scnprintf(buf, PAGE_SIZE, "%d\n", reqq_cnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) static DEVICE_ATTR_RO(requestq_count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) static ssize_t pendingq_count_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) unsigned int penq_cnt = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) if (aq->dev_state > AP_DEV_STATE_UNINITIATED)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) penq_cnt = aq->pendingq_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) return scnprintf(buf, PAGE_SIZE, "%d\n", penq_cnt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) static DEVICE_ATTR_RO(pendingq_count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) static ssize_t reset_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) int rc = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) switch (aq->sm_state) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) case AP_SM_STATE_RESET_START:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) case AP_SM_STATE_RESET_WAIT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) rc = scnprintf(buf, PAGE_SIZE, "Reset in progress.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) case AP_SM_STATE_WORKING:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) case AP_SM_STATE_QUEUE_FULL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) rc = scnprintf(buf, PAGE_SIZE, "Reset Timer armed.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) rc = scnprintf(buf, PAGE_SIZE, "No Reset Timer set.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) static ssize_t reset_store(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) struct device_attribute *attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) const char *buf, size_t count)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) __ap_flush_queue(aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) aq->sm_state = AP_SM_STATE_RESET_START;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) ap_wait(ap_sm_event(aq, AP_SM_EVENT_POLL));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) AP_DBF(DBF_INFO, "reset queue=%02x.%04x triggered by user\n",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) AP_QID_CARD(aq->qid), AP_QID_QUEUE(aq->qid));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) return count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) static DEVICE_ATTR_RW(reset);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) static ssize_t interrupt_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) int rc = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) if (aq->sm_state == AP_SM_STATE_SETIRQ_WAIT)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) rc = scnprintf(buf, PAGE_SIZE, "Enable Interrupt pending.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) else if (aq->interrupt)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) rc = scnprintf(buf, PAGE_SIZE, "Interrupts enabled.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) rc = scnprintf(buf, PAGE_SIZE, "Interrupts disabled.\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) static DEVICE_ATTR_RO(interrupt);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) static ssize_t config_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) rc = scnprintf(buf, PAGE_SIZE, "%d\n", aq->config ? 1 : 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) static DEVICE_ATTR_RO(config);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) #ifdef CONFIG_ZCRYPT_DEBUG
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) static ssize_t states_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) int rc = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) /* queue device state */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) switch (aq->dev_state) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) case AP_DEV_STATE_UNINITIATED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) rc = scnprintf(buf, PAGE_SIZE, "UNINITIATED\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) case AP_DEV_STATE_OPERATING:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) rc = scnprintf(buf, PAGE_SIZE, "OPERATING");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) case AP_DEV_STATE_SHUTDOWN:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) rc = scnprintf(buf, PAGE_SIZE, "SHUTDOWN");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) case AP_DEV_STATE_ERROR:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) rc = scnprintf(buf, PAGE_SIZE, "ERROR");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) rc = scnprintf(buf, PAGE_SIZE, "UNKNOWN");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) /* state machine state */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) if (aq->dev_state) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) switch (aq->sm_state) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) case AP_SM_STATE_RESET_START:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) rc += scnprintf(buf + rc, PAGE_SIZE - rc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) " [RESET_START]\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) case AP_SM_STATE_RESET_WAIT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) rc += scnprintf(buf + rc, PAGE_SIZE - rc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) " [RESET_WAIT]\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) case AP_SM_STATE_SETIRQ_WAIT:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) rc += scnprintf(buf + rc, PAGE_SIZE - rc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) " [SETIRQ_WAIT]\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) case AP_SM_STATE_IDLE:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) rc += scnprintf(buf + rc, PAGE_SIZE - rc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) " [IDLE]\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) case AP_SM_STATE_WORKING:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) rc += scnprintf(buf + rc, PAGE_SIZE - rc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) " [WORKING]\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) case AP_SM_STATE_QUEUE_FULL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) rc += scnprintf(buf + rc, PAGE_SIZE - rc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) " [FULL]\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) break;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) rc += scnprintf(buf + rc, PAGE_SIZE - rc,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) " [UNKNOWN]\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) static DEVICE_ATTR_RO(states);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) static ssize_t last_err_rc_show(struct device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) struct device_attribute *attr, char *buf)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) int rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) rc = aq->last_err_rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) switch (rc) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) case AP_RESPONSE_NORMAL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) return scnprintf(buf, PAGE_SIZE, "NORMAL\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) case AP_RESPONSE_Q_NOT_AVAIL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) return scnprintf(buf, PAGE_SIZE, "Q_NOT_AVAIL\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) case AP_RESPONSE_RESET_IN_PROGRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) return scnprintf(buf, PAGE_SIZE, "RESET_IN_PROGRESS\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) case AP_RESPONSE_DECONFIGURED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) return scnprintf(buf, PAGE_SIZE, "DECONFIGURED\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) case AP_RESPONSE_CHECKSTOPPED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) return scnprintf(buf, PAGE_SIZE, "CHECKSTOPPED\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) case AP_RESPONSE_BUSY:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) return scnprintf(buf, PAGE_SIZE, "BUSY\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) case AP_RESPONSE_INVALID_ADDRESS:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) return scnprintf(buf, PAGE_SIZE, "INVALID_ADDRESS\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) case AP_RESPONSE_OTHERWISE_CHANGED:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) return scnprintf(buf, PAGE_SIZE, "OTHERWISE_CHANGED\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) case AP_RESPONSE_Q_FULL:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) return scnprintf(buf, PAGE_SIZE, "Q_FULL/NO_PENDING_REPLY\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) case AP_RESPONSE_INDEX_TOO_BIG:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) return scnprintf(buf, PAGE_SIZE, "INDEX_TOO_BIG\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) case AP_RESPONSE_NO_FIRST_PART:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) return scnprintf(buf, PAGE_SIZE, "NO_FIRST_PART\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) case AP_RESPONSE_MESSAGE_TOO_BIG:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) return scnprintf(buf, PAGE_SIZE, "MESSAGE_TOO_BIG\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) case AP_RESPONSE_REQ_FAC_NOT_INST:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) return scnprintf(buf, PAGE_SIZE, "REQ_FAC_NOT_INST\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) default:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) return scnprintf(buf, PAGE_SIZE, "response code %d\n", rc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) static DEVICE_ATTR_RO(last_err_rc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) static struct attribute *ap_queue_dev_attrs[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) &dev_attr_request_count.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) &dev_attr_requestq_count.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) &dev_attr_pendingq_count.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) &dev_attr_reset.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) &dev_attr_interrupt.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) &dev_attr_config.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) #ifdef CONFIG_ZCRYPT_DEBUG
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) &dev_attr_states.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) &dev_attr_last_err_rc.attr,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) #endif
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) static struct attribute_group ap_queue_dev_attr_group = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) .attrs = ap_queue_dev_attrs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) static const struct attribute_group *ap_queue_dev_attr_groups[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) &ap_queue_dev_attr_group,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) NULL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) static struct device_type ap_queue_type = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) .name = "ap_queue",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) .groups = ap_queue_dev_attr_groups,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) static void ap_queue_device_release(struct device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) struct ap_queue *aq = to_ap_queue(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) spin_lock_bh(&ap_queues_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) hash_del(&aq->hnode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) spin_unlock_bh(&ap_queues_lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) kfree(aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) struct ap_queue *ap_queue_create(ap_qid_t qid, int device_type)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) struct ap_queue *aq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) aq = kzalloc(sizeof(*aq), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) if (!aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) return NULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) aq->ap_dev.device.release = ap_queue_device_release;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) aq->ap_dev.device.type = &ap_queue_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) aq->ap_dev.device_type = device_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) aq->qid = qid;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) aq->interrupt = false;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) spin_lock_init(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) INIT_LIST_HEAD(&aq->pendingq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) INIT_LIST_HEAD(&aq->requestq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) timer_setup(&aq->timeout, ap_request_timeout, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) return aq;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) void ap_queue_init_reply(struct ap_queue *aq, struct ap_message *reply)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) aq->reply = reply;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) ap_wait(ap_sm_event(aq, AP_SM_EVENT_POLL));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) EXPORT_SYMBOL(ap_queue_init_reply);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) * ap_queue_message(): Queue a request to an AP device.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) * @aq: The AP device to queue the message to
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) * @ap_msg: The message that is to be added
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) int ap_queue_message(struct ap_queue *aq, struct ap_message *ap_msg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) int rc = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) /* msg needs to have a valid receive-callback */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) BUG_ON(!ap_msg->receive);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) /* only allow to queue new messages if device state is ok */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) if (aq->dev_state == AP_DEV_STATE_OPERATING) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) list_add_tail(&ap_msg->list, &aq->requestq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) aq->requestq_count++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) aq->total_request_count++;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) atomic64_inc(&aq->card->total_request_count);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) } else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) rc = -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) /* Send/receive as many request from the queue as possible. */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) ap_wait(ap_sm_event_loop(aq, AP_SM_EVENT_POLL));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) return rc;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) EXPORT_SYMBOL(ap_queue_message);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) * ap_cancel_message(): Cancel a crypto request.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) * @aq: The AP device that has the message queued
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) * @ap_msg: The message that is to be removed
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) * Cancel a crypto request. This is done by removing the request
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) * from the device pending or request queue. Note that the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) * request stays on the AP queue. When it finishes the message
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) * reply will be discarded because the psmid can't be found.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) void ap_cancel_message(struct ap_queue *aq, struct ap_message *ap_msg)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) struct ap_message *tmp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) if (!list_empty(&ap_msg->list)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) list_for_each_entry(tmp, &aq->pendingq, list)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) if (tmp->psmid == ap_msg->psmid) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) aq->pendingq_count--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) goto found;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) aq->requestq_count--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) found:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) list_del_init(&ap_msg->list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) EXPORT_SYMBOL(ap_cancel_message);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) * __ap_flush_queue(): Flush requests.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) * @aq: Pointer to the AP queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) * Flush all requests from the request/pending queue of an AP device.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) static void __ap_flush_queue(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) struct ap_message *ap_msg, *next;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) list_for_each_entry_safe(ap_msg, next, &aq->pendingq, list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) list_del_init(&ap_msg->list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) aq->pendingq_count--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) ap_msg->rc = -EAGAIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) ap_msg->receive(aq, ap_msg, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) list_for_each_entry_safe(ap_msg, next, &aq->requestq, list) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) list_del_init(&ap_msg->list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) aq->requestq_count--;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) ap_msg->rc = -EAGAIN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854) ap_msg->receive(aq, ap_msg, NULL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) aq->queue_count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) void ap_flush_queue(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) __ap_flush_queue(aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) EXPORT_SYMBOL(ap_flush_queue);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) void ap_queue_prepare_remove(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) /* flush queue */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871) __ap_flush_queue(aq);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872) /* move queue device state to SHUTDOWN in progress */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) aq->dev_state = AP_DEV_STATE_SHUTDOWN;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875) del_timer_sync(&aq->timeout);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878) void ap_queue_remove(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881) * all messages have been flushed and the device state
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) * is SHUTDOWN. Now reset with zero which also clears
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) * the irq registration and move the device state
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) * to the initial value AP_DEV_STATE_UNINITIATED.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887) ap_zapq(aq->qid);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) aq->dev_state = AP_DEV_STATE_UNINITIATED;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892) void ap_queue_init_state(struct ap_queue *aq)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894) spin_lock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) aq->dev_state = AP_DEV_STATE_OPERATING;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896) aq->sm_state = AP_SM_STATE_RESET_START;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897) ap_wait(ap_sm_event(aq, AP_SM_EVENT_POLL));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898) spin_unlock_bh(&aq->lock);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900) EXPORT_SYMBOL(ap_queue_init_state);