^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 (c) 2003-2019, Intel Corporation. All rights reserved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) * Intel Management Engine Interface (Intel MEI) Linux driver
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #ifndef _MEI_DEV_H_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #define _MEI_DEV_H_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/types.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/cdev.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/poll.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/mei.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/mei_cl_bus.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include "hw.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include "hbm.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #define MEI_SLOT_SIZE sizeof(u32)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #define MEI_RD_MSG_BUF_SIZE (128 * MEI_SLOT_SIZE)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) * Number of Maximum MEI Clients
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) #define MEI_CLIENTS_MAX 256
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) * maximum number of consecutive resets
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #define MEI_MAX_CONSEC_RESET 3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) * Number of File descriptors/handles
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) * that can be opened to the driver.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) * Limit to 255: 256 Total Clients
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) * minus internal client for MEI Bus Messages
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) #define MEI_MAX_OPEN_HANDLE_COUNT (MEI_CLIENTS_MAX - 1)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) /* File state */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) enum file_state {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) MEI_FILE_UNINITIALIZED = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) MEI_FILE_INITIALIZING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) MEI_FILE_CONNECTING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) MEI_FILE_CONNECTED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) MEI_FILE_DISCONNECTING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) MEI_FILE_DISCONNECT_REPLY,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) MEI_FILE_DISCONNECT_REQUIRED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) MEI_FILE_DISCONNECTED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) /* MEI device states */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) enum mei_dev_state {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) MEI_DEV_INITIALIZING = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) MEI_DEV_INIT_CLIENTS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) MEI_DEV_ENABLED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) MEI_DEV_RESETTING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) MEI_DEV_DISABLED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) MEI_DEV_POWER_DOWN,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) MEI_DEV_POWER_UP
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) const char *mei_dev_state_str(int state);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) enum mei_file_transaction_states {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) MEI_IDLE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) MEI_WRITING,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) MEI_WRITE_COMPLETE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) * enum mei_cb_file_ops - file operation associated with the callback
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) * @MEI_FOP_READ: read
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) * @MEI_FOP_WRITE: write
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) * @MEI_FOP_CONNECT: connect
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) * @MEI_FOP_DISCONNECT: disconnect
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) * @MEI_FOP_DISCONNECT_RSP: disconnect response
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) * @MEI_FOP_NOTIFY_START: start notification
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) * @MEI_FOP_NOTIFY_STOP: stop notification
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) enum mei_cb_file_ops {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) MEI_FOP_READ = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) MEI_FOP_WRITE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) MEI_FOP_CONNECT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) MEI_FOP_DISCONNECT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) MEI_FOP_DISCONNECT_RSP,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) MEI_FOP_NOTIFY_START,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89) MEI_FOP_NOTIFY_STOP,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) * enum mei_cl_io_mode - io mode between driver and fw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) * @MEI_CL_IO_TX_BLOCKING: send is blocking
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) * @MEI_CL_IO_TX_INTERNAL: internal communication between driver and FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) * @MEI_CL_IO_RX_NONBLOCK: recv is non-blocking
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) enum mei_cl_io_mode {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) MEI_CL_IO_TX_BLOCKING = BIT(0),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) MEI_CL_IO_TX_INTERNAL = BIT(1),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) MEI_CL_IO_RX_NONBLOCK = BIT(2),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) * Intel MEI message data struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) struct mei_msg_data {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) size_t size;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) unsigned char *data;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) * struct mei_dma_dscr - dma address descriptor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) * @vaddr: dma buffer virtual address
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) * @daddr: dma buffer physical address
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) * @size : dma buffer size
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) struct mei_dma_dscr {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) void *vaddr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) dma_addr_t daddr;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) size_t size;
^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) /* Maximum number of processed FW status registers */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) #define MEI_FW_STATUS_MAX 6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) /* Minimal buffer for FW status string (8 bytes in dw + space or '\0') */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) #define MEI_FW_STATUS_STR_SZ (MEI_FW_STATUS_MAX * (8 + 1))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) * struct mei_fw_status - storage of FW status data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) * @count: number of actually available elements in array
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) * @status: FW status registers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) struct mei_fw_status {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) int count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) u32 status[MEI_FW_STATUS_MAX];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) * struct mei_me_client - representation of me (fw) client
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) * @list: link in me client list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) * @refcnt: struct reference count
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) * @props: client properties
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) * @client_id: me client id
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) * @tx_flow_ctrl_creds: flow control credits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) * @connect_count: number connections to this client
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) * @bus_added: added to bus
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) struct mei_me_client {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) struct list_head list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) struct kref refcnt;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) struct mei_client_properties props;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) u8 client_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) u8 tx_flow_ctrl_creds;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) u8 connect_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) u8 bus_added;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) struct mei_cl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) * struct mei_cl_cb - file operation callback structure
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) * @list: link in callback queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) * @cl: file client who is running this operation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) * @fop_type: file operation type
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) * @buf: buffer for data associated with the callback
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) * @buf_idx: last read index
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) * @vtag: virtual tag
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) * @fp: pointer to file structure
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) * @status: io status of the cb
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) * @internal: communication between driver and FW flag
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) * @blocking: transmission blocking mode
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) struct mei_cl_cb {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) struct list_head list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) struct mei_cl *cl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) enum mei_cb_file_ops fop_type;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) struct mei_msg_data buf;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) size_t buf_idx;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) u8 vtag;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) const struct file *fp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) int status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) u32 internal:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) u32 blocking:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) * struct mei_cl_vtag - file pointer to vtag mapping structure
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) * @list: link in map queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) * @fp: file pointer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) * @vtag: corresponding vtag
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) * @pending_read: the read is pending on this file
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) struct mei_cl_vtag {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) struct list_head list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) const struct file *fp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) u8 vtag;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) u8 pending_read:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) * struct mei_cl - me client host representation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) * carried in file->private_data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) * @link: link in the clients list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) * @dev: mei parent device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) * @state: file operation state
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) * @tx_wait: wait queue for tx completion
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) * @rx_wait: wait queue for rx completion
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) * @wait: wait queue for management operation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) * @ev_wait: notification wait queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) * @ev_async: event async notification
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) * @status: connection status
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) * @me_cl: fw client connected
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) * @fp: file associated with client
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) * @host_client_id: host id
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) * @vtag_map: vtag map
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) * @tx_flow_ctrl_creds: transmit flow credentials
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) * @rx_flow_ctrl_creds: receive flow credentials
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) * @timer_count: watchdog timer for operation completion
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) * @notify_en: notification - enabled/disabled
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) * @notify_ev: pending notification event
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) * @tx_cb_queued: number of tx callbacks in queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) * @writing_state: state of the tx
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) * @rd_pending: pending read credits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) * @rd_completed_lock: protects rd_completed queue
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) * @rd_completed: completed read
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) * @cldev: device on the mei client bus
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) struct mei_cl {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) struct list_head link;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) struct mei_device *dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) enum file_state state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) wait_queue_head_t tx_wait;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) wait_queue_head_t rx_wait;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) wait_queue_head_t wait;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) wait_queue_head_t ev_wait;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) struct fasync_struct *ev_async;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) int status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) struct mei_me_client *me_cl;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) const struct file *fp;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) u8 host_client_id;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) struct list_head vtag_map;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) u8 tx_flow_ctrl_creds;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) u8 rx_flow_ctrl_creds;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) u8 timer_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) u8 notify_en;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) u8 notify_ev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) u8 tx_cb_queued;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) enum mei_file_transaction_states writing_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) struct list_head rd_pending;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) spinlock_t rd_completed_lock; /* protects rd_completed queue */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) struct list_head rd_completed;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) struct mei_cl_device *cldev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) #define MEI_TX_QUEUE_LIMIT_DEFAULT 50
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) #define MEI_TX_QUEUE_LIMIT_MAX 255
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) #define MEI_TX_QUEUE_LIMIT_MIN 30
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) * struct mei_hw_ops - hw specific ops
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) * @host_is_ready : query for host readiness
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) * @hw_is_ready : query if hw is ready
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) * @hw_reset : reset hw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) * @hw_start : start hw after reset
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) * @hw_config : configure hw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) * @fw_status : get fw status registers
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) * @trc_status : get trc status register
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) * @pg_state : power gating state of the device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) * @pg_in_transition : is device now in pg transition
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) * @pg_is_enabled : is power gating enabled
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) * @intr_clear : clear pending interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) * @intr_enable : enable interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) * @intr_disable : disable interrupts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) * @synchronize_irq : synchronize irqs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) * @hbuf_free_slots : query for write buffer empty slots
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) * @hbuf_is_ready : query if write buffer is empty
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) * @hbuf_depth : query for write buffer depth
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) * @write : write a message to FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) * @rdbuf_full_slots : query how many slots are filled
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) * @read_hdr : get first 4 bytes (header)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) * @read : read a buffer from the FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) struct mei_hw_ops {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) bool (*host_is_ready)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) bool (*hw_is_ready)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) int (*hw_reset)(struct mei_device *dev, bool enable);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) int (*hw_start)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) int (*hw_config)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) int (*fw_status)(struct mei_device *dev, struct mei_fw_status *fw_sts);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) int (*trc_status)(struct mei_device *dev, u32 *trc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) enum mei_pg_state (*pg_state)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) bool (*pg_in_transition)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) bool (*pg_is_enabled)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) void (*intr_clear)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) void (*intr_enable)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) void (*intr_disable)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) void (*synchronize_irq)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) int (*hbuf_free_slots)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) bool (*hbuf_is_ready)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) u32 (*hbuf_depth)(const struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) int (*write)(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) const void *hdr, size_t hdr_len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) const void *data, size_t data_len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) int (*rdbuf_full_slots)(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) u32 (*read_hdr)(const struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) int (*read)(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) unsigned char *buf, unsigned long len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) /* MEI bus API*/
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) void mei_cl_bus_rescan_work(struct work_struct *work);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) void mei_cl_bus_dev_fixup(struct mei_cl_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) ssize_t __mei_cl_send(struct mei_cl *cl, u8 *buf, size_t length,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) unsigned int mode);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) ssize_t __mei_cl_recv(struct mei_cl *cl, u8 *buf, size_t length,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) unsigned int mode, unsigned long timeout);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) bool mei_cl_bus_rx_event(struct mei_cl *cl);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) bool mei_cl_bus_notify_event(struct mei_cl *cl);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) void mei_cl_bus_remove_devices(struct mei_device *bus);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) int mei_cl_bus_init(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) void mei_cl_bus_exit(void);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) * enum mei_pg_event - power gating transition events
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) * @MEI_PG_EVENT_IDLE: the driver is not in power gating transition
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) * @MEI_PG_EVENT_WAIT: the driver is waiting for a pg event to complete
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) * @MEI_PG_EVENT_RECEIVED: the driver received pg event
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) * @MEI_PG_EVENT_INTR_WAIT: the driver is waiting for a pg event interrupt
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) * @MEI_PG_EVENT_INTR_RECEIVED: the driver received pg event interrupt
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) enum mei_pg_event {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) MEI_PG_EVENT_IDLE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) MEI_PG_EVENT_WAIT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) MEI_PG_EVENT_RECEIVED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) MEI_PG_EVENT_INTR_WAIT,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) MEI_PG_EVENT_INTR_RECEIVED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) * enum mei_pg_state - device internal power gating state
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) * @MEI_PG_OFF: device is not power gated - it is active
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) * @MEI_PG_ON: device is power gated - it is in lower power state
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) enum mei_pg_state {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) MEI_PG_OFF = 0,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) MEI_PG_ON = 1,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) const char *mei_pg_state_str(enum mei_pg_state state);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) * struct mei_fw_version - MEI FW version struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) * @platform: platform identifier
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) * @major: major version field
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) * @minor: minor version field
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) * @buildno: build number version field
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) * @hotfix: hotfix number version field
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) struct mei_fw_version {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) u8 platform;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) u8 major;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) u16 minor;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) u16 buildno;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) u16 hotfix;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) #define MEI_MAX_FW_VER_BLOCKS 3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) * struct mei_device - MEI private device struct
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) * @dev : device on a bus
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) * @cdev : character device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) * @minor : minor number allocated for device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) * @write_list : write pending list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) * @write_waiting_list : write completion list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) * @ctrl_wr_list : pending control write list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) * @ctrl_rd_list : pending control read list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) * @tx_queue_limit: tx queues per client linit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) * @file_list : list of opened handles
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) * @open_handle_count: number of opened handles
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) * @device_lock : big device lock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) * @timer_work : MEI timer delayed work (timeouts)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) * @recvd_hw_ready : hw ready message received flag
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) * @wait_hw_ready : wait queue for receive HW ready message form FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) * @wait_pg : wait queue for receive PG message from FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) * @wait_hbm_start : wait queue for receive HBM start message from FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) * @reset_count : number of consecutive resets
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) * @dev_state : device state
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) * @hbm_state : state of host bus message protocol
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) * @init_clients_timer : HBM init handshake timeout
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) * @pg_event : power gating event
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) * @pg_domain : runtime PM domain
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) * @rd_msg_buf : control messages buffer
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) * @rd_msg_hdr : read message header storage
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) * @rd_msg_hdr_count : how many dwords were already read from header
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) * @hbuf_is_ready : query if the host host/write buffer is ready
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) * @dr_dscr: DMA ring descriptors: TX, RX, and CTRL
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) * @version : HBM protocol version in use
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) * @hbm_f_pg_supported : hbm feature pgi protocol
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) * @hbm_f_dc_supported : hbm feature dynamic clients
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) * @hbm_f_dot_supported : hbm feature disconnect on timeout
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) * @hbm_f_ev_supported : hbm feature event notification
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) * @hbm_f_fa_supported : hbm feature fixed address client
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) * @hbm_f_ie_supported : hbm feature immediate reply to enum request
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) * @hbm_f_os_supported : hbm feature support OS ver message
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) * @hbm_f_dr_supported : hbm feature dma ring supported
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) * @hbm_f_vt_supported : hbm feature vtag supported
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) * @hbm_f_cap_supported : hbm feature capabilities message supported
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) * @fw_ver : FW versions
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) * @fw_f_fw_ver_supported : fw feature: fw version supported
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) * @me_clients_rwsem: rw lock over me_clients list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) * @me_clients : list of FW clients
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) * @me_clients_map : FW clients bit map
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) * @host_clients_map : host clients id pool
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) * @allow_fixed_address: allow user space to connect a fixed client
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) * @override_fixed_address: force allow fixed address behavior
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) * @reset_work : work item for the device reset
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) * @bus_rescan_work : work item for the bus rescan
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) * @device_list : mei client bus list
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) * @cl_bus_lock : client bus list lock
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) * @kind : kind of mei device
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) * @dbgfs_dir : debugfs mei root directory
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) * @ops: : hw specific operations
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) * @hw : hw specific data
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) struct mei_device {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) struct device *dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) struct cdev cdev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) int minor;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) struct list_head write_list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) struct list_head write_waiting_list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) struct list_head ctrl_wr_list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) struct list_head ctrl_rd_list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) u8 tx_queue_limit;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) struct list_head file_list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) long open_handle_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) struct mutex device_lock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) struct delayed_work timer_work;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) bool recvd_hw_ready;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) * waiting queue for receive message from FW
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) wait_queue_head_t wait_hw_ready;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) wait_queue_head_t wait_pg;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) wait_queue_head_t wait_hbm_start;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) * mei device states
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) unsigned long reset_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) enum mei_dev_state dev_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) enum mei_hbm_state hbm_state;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) u16 init_clients_timer;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) * Power Gating support
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) enum mei_pg_event pg_event;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) #ifdef CONFIG_PM
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) struct dev_pm_domain pg_domain;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) #endif /* CONFIG_PM */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) unsigned char rd_msg_buf[MEI_RD_MSG_BUF_SIZE];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) u32 rd_msg_hdr[MEI_RD_MSG_BUF_SIZE];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) int rd_msg_hdr_count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) /* write buffer */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) bool hbuf_is_ready;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) struct mei_dma_dscr dr_dscr[DMA_DSCR_NUM];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) struct hbm_version version;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) unsigned int hbm_f_pg_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) unsigned int hbm_f_dc_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) unsigned int hbm_f_dot_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) unsigned int hbm_f_ev_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) unsigned int hbm_f_fa_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) unsigned int hbm_f_ie_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) unsigned int hbm_f_os_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) unsigned int hbm_f_dr_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) unsigned int hbm_f_vt_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) unsigned int hbm_f_cap_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) struct mei_fw_version fw_ver[MEI_MAX_FW_VER_BLOCKS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) unsigned int fw_f_fw_ver_supported:1;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) struct rw_semaphore me_clients_rwsem;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) struct list_head me_clients;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) DECLARE_BITMAP(me_clients_map, MEI_CLIENTS_MAX);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) DECLARE_BITMAP(host_clients_map, MEI_CLIENTS_MAX);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) bool allow_fixed_address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) bool override_fixed_address;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) struct work_struct reset_work;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) struct work_struct bus_rescan_work;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) /* List of bus devices */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) struct list_head device_list;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) struct mutex cl_bus_lock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) const char *kind;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) #if IS_ENABLED(CONFIG_DEBUG_FS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) struct dentry *dbgfs_dir;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) #endif /* CONFIG_DEBUG_FS */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) const struct mei_hw_ops *ops;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) char hw[] __aligned(sizeof(void *));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) static inline unsigned long mei_secs_to_jiffies(unsigned long sec)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) return msecs_to_jiffies(sec * MSEC_PER_SEC);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) * mei_data2slots - get slots number from a message length
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) * @length: size of the messages in bytes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) * Return: number of slots
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) static inline u32 mei_data2slots(size_t length)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) return DIV_ROUND_UP(length, MEI_SLOT_SIZE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) * mei_hbm2slots - get slots number from a hbm message length
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) * length + size of the mei message header
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) * @length: size of the messages in bytes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) * Return: number of slots
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) static inline u32 mei_hbm2slots(size_t length)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) return DIV_ROUND_UP(sizeof(struct mei_msg_hdr) + length, MEI_SLOT_SIZE);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) * mei_slots2data - get data in slots - bytes from slots
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) * @slots: number of available slots
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) * Return: number of bytes in slots
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) static inline u32 mei_slots2data(int slots)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) return slots * MEI_SLOT_SIZE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) * mei init function prototypes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) void mei_device_init(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) struct device *device,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) const struct mei_hw_ops *hw_ops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) int mei_reset(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) int mei_start(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) int mei_restart(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) void mei_stop(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) void mei_cancel_work(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) void mei_set_devstate(struct mei_device *dev, enum mei_dev_state state);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) int mei_dmam_ring_alloc(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) void mei_dmam_ring_free(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) bool mei_dma_ring_is_allocated(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) void mei_dma_ring_reset(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) void mei_dma_ring_read(struct mei_device *dev, unsigned char *buf, u32 len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) void mei_dma_ring_write(struct mei_device *dev, unsigned char *buf, u32 len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) u32 mei_dma_ring_empty_slots(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) * MEI interrupt functions prototype
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) void mei_timer(struct work_struct *work);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) void mei_schedule_stall_timer(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) int mei_irq_read_handler(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) struct list_head *cmpl_list, s32 *slots);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) int mei_irq_write_handler(struct mei_device *dev, struct list_head *cmpl_list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) void mei_irq_compl_handler(struct mei_device *dev, struct list_head *cmpl_list);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) * Register Access Function
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) static inline int mei_hw_config(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) return dev->ops->hw_config(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) static inline enum mei_pg_state mei_pg_state(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) return dev->ops->pg_state(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) static inline bool mei_pg_in_transition(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) return dev->ops->pg_in_transition(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) static inline bool mei_pg_is_enabled(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) return dev->ops->pg_is_enabled(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) static inline int mei_hw_reset(struct mei_device *dev, bool enable)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) return dev->ops->hw_reset(dev, enable);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) static inline int mei_hw_start(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) return dev->ops->hw_start(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) static inline void mei_clear_interrupts(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) dev->ops->intr_clear(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) static inline void mei_enable_interrupts(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) dev->ops->intr_enable(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) static inline void mei_disable_interrupts(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) dev->ops->intr_disable(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) static inline void mei_synchronize_irq(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) dev->ops->synchronize_irq(dev);
^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 inline bool mei_host_is_ready(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) return dev->ops->host_is_ready(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) static inline bool mei_hw_is_ready(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) return dev->ops->hw_is_ready(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) static inline bool mei_hbuf_is_ready(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) return dev->ops->hbuf_is_ready(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) static inline int mei_hbuf_empty_slots(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) return dev->ops->hbuf_free_slots(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) static inline u32 mei_hbuf_depth(const struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) return dev->ops->hbuf_depth(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) static inline int mei_write_message(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) const void *hdr, size_t hdr_len,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) const void *data, size_t data_len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) return dev->ops->write(dev, hdr, hdr_len, data, data_len);
^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 inline u32 mei_read_hdr(const struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) return dev->ops->read_hdr(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) static inline void mei_read_slots(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) unsigned char *buf, unsigned long len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) dev->ops->read(dev, buf, len);
^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) static inline int mei_count_full_read_slots(struct mei_device *dev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) return dev->ops->rdbuf_full_slots(dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) static inline int mei_trc_status(struct mei_device *dev, u32 *trc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) if (dev->ops->trc_status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) return dev->ops->trc_status(dev, trc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) return -EOPNOTSUPP;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) static inline int mei_fw_status(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) struct mei_fw_status *fw_status)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) return dev->ops->fw_status(dev, fw_status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) bool mei_hbuf_acquire(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) bool mei_write_is_idle(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) #if IS_ENABLED(CONFIG_DEBUG_FS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) void mei_dbgfs_register(struct mei_device *dev, const char *name);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) void mei_dbgfs_deregister(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) #else
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) static inline void mei_dbgfs_register(struct mei_device *dev, const char *name) {}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) static inline void mei_dbgfs_deregister(struct mei_device *dev) {}
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) #endif /* CONFIG_DEBUG_FS */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) int mei_register(struct mei_device *dev, struct device *parent);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) void mei_deregister(struct mei_device *dev);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) #define MEI_HDR_FMT "hdr:host=%02d me=%02d len=%d dma=%1d ext=%1d internal=%1d comp=%1d"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) #define MEI_HDR_PRM(hdr) \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) (hdr)->host_addr, (hdr)->me_addr, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) (hdr)->length, (hdr)->dma_ring, (hdr)->extended, \
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) (hdr)->internal, (hdr)->msg_complete
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) ssize_t mei_fw_status2str(struct mei_fw_status *fw_sts, char *buf, size_t len);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) /**
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) * mei_fw_status_str - fetch and convert fw status registers to printable string
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) * @dev: the device structure
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) * @buf: string buffer at minimal size MEI_FW_STATUS_STR_SZ
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) * @len: buffer len must be >= MEI_FW_STATUS_STR_SZ
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) * Return: number of bytes written or < 0 on failure
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) static inline ssize_t mei_fw_status_str(struct mei_device *dev,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) char *buf, size_t len)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) struct mei_fw_status fw_status;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) buf[0] = '\0';
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) ret = mei_fw_status(dev, &fw_status);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) ret = mei_fw_status2str(&fw_status, buf, MEI_FW_STATUS_STR_SZ);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) #endif