1 /*
2  * Copyright (c) 2019 Intel Corporation.
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 /**
8  * @file
9  * @brief Public APIs for eSPI driver
10  */
11 
12 #ifndef ZEPHYR_INCLUDE_ESPI_H_
13 #define ZEPHYR_INCLUDE_ESPI_H_
14 
15 #include <errno.h>
16 
17 #include <zephyr/sys/__assert.h>
18 #include <zephyr/types.h>
19 #include <zephyr/device.h>
20 #include <zephyr/sys/slist.h>
21 
22 #ifdef __cplusplus
23 extern "C" {
24 #endif
25 
26 /**
27  * @brief eSPI Driver APIs
28  * @defgroup espi_interface ESPI Driver APIs
29  * @ingroup io_interfaces
30  * @{
31  */
32 
33 /**
34  * @brief eSPI I/O mode capabilities
35  */
36 enum espi_io_mode {
37 	ESPI_IO_MODE_SINGLE_LINE = BIT(0),
38 	ESPI_IO_MODE_DUAL_LINES = BIT(1),
39 	ESPI_IO_MODE_QUAD_LINES = BIT(2),
40 };
41 
42 /**
43  * @code
44  *+----------------------------------------------------------------------+
45  *|                                                                      |
46  *|  eSPI controller                     +-------------+                 |
47  *|                      +-----------+   |    Power    |   +----------+  |
48  *|                      |Out of band|   |  management |   |   GPIO   |  |
49  *|  +------------+      |processor  |   |  controller |   |  sources |  |
50  *|  |  SPI flash |      +-----------+   +-------------+   +----------+  |
51  *|  | controller |            |                |               |        |
52  *|  +------------+            |                |               |        |
53  *|   |  |    |                +--------+       +---------------+        |
54  *|   |  |    |                         |               |                |
55  *|   |  |    +-----+   +--------+   +----------+  +----v-----+          |
56  *|   |  |          |   |  LPC   |   | Tunneled |  | Tunneled |          |
57  *|   |  |          |   | bridge |   |  SMBus   |  |   GPIO   |          |
58  *|   |  |          |   +--------+   +----------+  +----------+          |
59  *|   |  |          |        |             |             |               |
60  *|   |  |          |        ------+       |             |               |
61  *|   |  |          |              |       |             |               |
62  *|   |  |   +------v-----+    +---v-------v-------------v----+          |
63  *|   |  |   | eSPI Flash |    |    eSPI protocol block       |          |
64  *|   |  |   |   access   +--->+                              |          |
65  *|   |  |   +------------+    +------------------------------+          |
66  *|   |  |                             |                                 |
67  *|   |  +-----------+                 |                                 |
68  *|   |              v                 v                                 |
69  *|   |           XXXXXXXXXXXXXXXXXXXXXXX                                |
70  *|   |            XXXXXXXXXXXXXXXXXXXXX                                 |
71  *|   |             XXXXXXXXXXXXXXXXXXX                                  |
72  *+----------------------------------------------------------------------+
73  *   |                      |
74  *   v             +-----------------+
75  * +---------+     |  |   |   |   |  |
76  * |  Flash  |     |  |   |   |   |  |
77  * +---------+     |  +   +   +   +  |    eSPI bus
78  *                 | CH0 CH1 CH2 CH3 |    (logical channels)
79  *                 |  +   +   +   +  |
80  *                 |  |   |   |   |  |
81  *                 +-----------------+
82  *                          |
83  *+-----------------------------------------------------------------------+
84  *|  eSPI target                                                          |
85  *|                                                                       |
86  *|       CH0         |     CH1      |      CH2      |    CH3             |
87  *|   eSPI endpoint   |    VWIRE     |      OOB      |   Flash            |
88  *+-----------------------------------------------------------------------+
89  * @endcode
90  */
91 
92 /**
93  * @brief eSPI channel.
94  *
95  * Identifies each eSPI logical channel supported by eSPI controller
96  * Each channel allows independent traffic, but the assignment of channel
97  * type to channel number is fixed.
98  *
99  * Note that generic commands are not associated with any channel, so traffic
100  * over eSPI can occur if all channels are disabled or not ready
101  */
102 enum espi_channel {
103 	ESPI_CHANNEL_PERIPHERAL = BIT(0),
104 	ESPI_CHANNEL_VWIRE      = BIT(1),
105 	ESPI_CHANNEL_OOB        = BIT(2),
106 	ESPI_CHANNEL_FLASH      = BIT(3),
107 };
108 
109 /**
110  * @brief eSPI bus event.
111  *
112  * eSPI bus event to indicate events for which user can register callbacks
113  */
114 enum espi_bus_event {
115 	/** Indicates the eSPI bus was reset either via eSPI reset pin.
116 	 * eSPI drivers should convey the eSPI reset status to eSPI driver clients
117 	 * following eSPI specification reset pin convention:
118 	 * 0-eSPI bus in reset, 1-eSPI bus out-of-reset
119 	 *
120 	 * Note: There is no need to send this callback for in-band reset.
121 	 */
122 	ESPI_BUS_RESET                      = BIT(0),
123 
124 	/** Indicates the eSPI HW has received channel enable notification from eSPI host,
125 	 * once the eSPI channel is signal as ready to the eSPI host,
126 	 * eSPI drivers should convey the eSPI channel ready to eSPI driver client via this event.
127 	 */
128 	ESPI_BUS_EVENT_CHANNEL_READY        = BIT(1),
129 
130 	/** Indicates the eSPI HW has received a virtual wire message from eSPI host.
131 	 * eSPI drivers should convey the eSPI virtual wire latest status.
132 	 */
133 	ESPI_BUS_EVENT_VWIRE_RECEIVED       = BIT(2),
134 
135 	/** Indicates the eSPI HW has received a Out-of-band package from eSPI host.
136 	 */
137 	ESPI_BUS_EVENT_OOB_RECEIVED         = BIT(3),
138 
139 	/** Indicates the eSPI HW has received a peripheral eSPI host event.
140 	 * eSPI drivers should convey the peripheral type.
141 	 */
142 	ESPI_BUS_PERIPHERAL_NOTIFICATION    = BIT(4),
143 	ESPI_BUS_TAF_NOTIFICATION           = BIT(5),
144 };
145 
146 
147 /**
148  * @brief eSPI peripheral channel events.
149  *
150  * eSPI peripheral channel event types to indicate users.
151  */
152 enum espi_pc_event {
153 	ESPI_PC_EVT_BUS_CHANNEL_READY = BIT(0),
154 	ESPI_PC_EVT_BUS_MASTER_ENABLE = BIT(1),
155 };
156 
157 /**
158  * @cond INTERNAL_HIDDEN
159  *
160  */
161 #define ESPI_PERIPHERAL_INDEX_0  0ul
162 #define ESPI_PERIPHERAL_INDEX_1  1ul
163 #define ESPI_PERIPHERAL_INDEX_2  2ul
164 
165 #define ESPI_TARGET_TO_CONTROLLER   0ul
166 #define ESPI_CONTROLLER_TO_TARGET   1ul
167 
168 #define ESPI_VWIRE_SRC_ID0       0ul
169 #define ESPI_VWIRE_SRC_ID1       1ul
170 #define ESPI_VWIRE_SRC_ID2       2ul
171 #define ESPI_VWIRE_SRC_ID3       3ul
172 #define ESPI_VWIRE_SRC_ID_MAX    4ul
173 
174 #define ESPI_PERIPHERAL_NODATA   0ul
175 
176 #define E8042_START_OPCODE      0x50
177 #define E8042_MAX_OPCODE        0x5F
178 
179 #define EACPI_START_OPCODE      0x60
180 #define EACPI_MAX_OPCODE        0x6F
181 
182 #define ECUSTOM_START_OPCODE    0xF0
183 #define ECUSTOM_MAX_OPCODE      0xFF
184 
185 /** @endcond */
186 
187 /**
188  * @brief eSPI peripheral notification type.
189  *
190  * eSPI peripheral notification event details to indicate which peripheral
191  * trigger the eSPI callback
192  */
193 enum espi_virtual_peripheral {
194 	ESPI_PERIPHERAL_UART,
195 	ESPI_PERIPHERAL_8042_KBC,
196 	ESPI_PERIPHERAL_HOST_IO,
197 	ESPI_PERIPHERAL_DEBUG_PORT80,
198 	ESPI_PERIPHERAL_HOST_IO_PVT,
199 #if defined(CONFIG_ESPI_PERIPHERAL_EC_HOST_CMD)
200 	ESPI_PERIPHERAL_EC_HOST_CMD,
201 #endif /* CONFIG_ESPI_PERIPHERAL_EC_HOST_CMD */
202 };
203 
204 /**
205  * @brief eSPI cycle types supported over eSPI peripheral channel
206  */
207 enum espi_cycle_type {
208 	ESPI_CYCLE_MEMORY_READ32,
209 	ESPI_CYCLE_MEMORY_READ64,
210 	ESPI_CYCLE_MEMORY_WRITE32,
211 	ESPI_CYCLE_MEMORY_WRITE64,
212 	ESPI_CYCLE_MESSAGE_NODATA,
213 	ESPI_CYCLE_MESSAGE_DATA,
214 	ESPI_CYCLE_OK_COMPLETION_NODATA,
215 	ESPI_CYCLE_OKCOMPLETION_DATA,
216 	ESPI_CYCLE_NOK_COMPLETION_NODATA,
217 };
218 
219 /**
220  * @brief eSPI system platform signals that can be send or receive through
221  * virtual wire channel
222  */
223 enum espi_vwire_signal {
224 	/* Virtual wires that can only be send from controller to target */
225 	ESPI_VWIRE_SIGNAL_SLP_S3,
226 	ESPI_VWIRE_SIGNAL_SLP_S4,
227 	ESPI_VWIRE_SIGNAL_SLP_S5,
228 	ESPI_VWIRE_SIGNAL_OOB_RST_WARN,
229 	ESPI_VWIRE_SIGNAL_PLTRST,
230 	ESPI_VWIRE_SIGNAL_SUS_STAT,
231 	ESPI_VWIRE_SIGNAL_NMIOUT,
232 	ESPI_VWIRE_SIGNAL_SMIOUT,
233 	ESPI_VWIRE_SIGNAL_HOST_RST_WARN,
234 	ESPI_VWIRE_SIGNAL_SLP_A,
235 	ESPI_VWIRE_SIGNAL_SUS_PWRDN_ACK,
236 	ESPI_VWIRE_SIGNAL_SUS_WARN,
237 	ESPI_VWIRE_SIGNAL_SLP_WLAN,
238 	ESPI_VWIRE_SIGNAL_SLP_LAN,
239 	ESPI_VWIRE_SIGNAL_HOST_C10,
240 	ESPI_VWIRE_SIGNAL_DNX_WARN,
241 	/* Virtual wires that can only be sent from target to controller */
242 	ESPI_VWIRE_SIGNAL_PME,
243 	ESPI_VWIRE_SIGNAL_WAKE,
244 	ESPI_VWIRE_SIGNAL_OOB_RST_ACK,
245 	ESPI_VWIRE_SIGNAL_TARGET_BOOT_STS,
246 	ESPI_VWIRE_SIGNAL_ERR_NON_FATAL,
247 	ESPI_VWIRE_SIGNAL_ERR_FATAL,
248 	ESPI_VWIRE_SIGNAL_TARGET_BOOT_DONE,
249 	ESPI_VWIRE_SIGNAL_HOST_RST_ACK,
250 	ESPI_VWIRE_SIGNAL_RST_CPU_INIT,
251 	/* System management interrupt */
252 	ESPI_VWIRE_SIGNAL_SMI,
253 	/* System control interrupt */
254 	ESPI_VWIRE_SIGNAL_SCI,
255 	ESPI_VWIRE_SIGNAL_DNX_ACK,
256 	ESPI_VWIRE_SIGNAL_SUS_ACK,
257 	/*
258 	 * Virtual wire GPIOs that can be sent from target to controller for
259 	 * platform specific usage.
260 	 */
261 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_0,
262 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_1,
263 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_2,
264 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_3,
265 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_4,
266 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_5,
267 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_6,
268 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_7,
269 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_8,
270 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_9,
271 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_10,
272 	ESPI_VWIRE_SIGNAL_TARGET_GPIO_11,
273 
274 	/* Number of Virtual Wires */
275 	ESPI_VWIRE_SIGNAL_COUNT
276 };
277 
278 /* USB-C port over current */
279 #define ESPI_VWIRE_SIGNAL_OCB_0 ESPI_VWIRE_SIGNAL_TARGET_GPIO_0
280 #define ESPI_VWIRE_SIGNAL_OCB_1 ESPI_VWIRE_SIGNAL_TARGET_GPIO_1
281 #define ESPI_VWIRE_SIGNAL_OCB_2 ESPI_VWIRE_SIGNAL_TARGET_GPIO_2
282 #define ESPI_VWIRE_SIGNAL_OCB_3 ESPI_VWIRE_SIGNAL_TARGET_GPIO_3
283 
284 /* eSPI LPC peripherals. */
285 enum lpc_peripheral_opcode {
286 	/* Read transactions */
287 	E8042_OBF_HAS_CHAR = 0x50,
288 	E8042_IBF_HAS_CHAR,
289 	/* Write transactions */
290 	E8042_WRITE_KB_CHAR,
291 	E8042_WRITE_MB_CHAR,
292 	/* Write transactions without input parameters */
293 	E8042_RESUME_IRQ,
294 	E8042_PAUSE_IRQ,
295 	E8042_CLEAR_OBF,
296 	/* Status transactions */
297 	E8042_READ_KB_STS,
298 	E8042_SET_FLAG,
299 	E8042_CLEAR_FLAG,
300 	/* ACPI read transactions */
301 	EACPI_OBF_HAS_CHAR = EACPI_START_OPCODE,
302 	EACPI_IBF_HAS_CHAR,
303 	/* ACPI write transactions */
304 	EACPI_WRITE_CHAR,
305 	/* ACPI status transactions */
306 	EACPI_READ_STS,
307 	EACPI_WRITE_STS,
308 #if defined(CONFIG_ESPI_PERIPHERAL_ACPI_SHM_REGION)
309 	/* Shared memory region support to return the ACPI response data */
310 	EACPI_GET_SHARED_MEMORY,
311 #endif /* CONFIG_ESPI_PERIPHERAL_ACPI_SHM_REGION */
312 #if defined(CONFIG_ESPI_PERIPHERAL_CUSTOM_OPCODE)
313 	/* Other customized transactions */
314 	ECUSTOM_HOST_SUBS_INTERRUPT_EN = ECUSTOM_START_OPCODE,
315 	ECUSTOM_HOST_CMD_GET_PARAM_MEMORY,
316 	ECUSTOM_HOST_CMD_GET_PARAM_MEMORY_SIZE,
317 	ECUSTOM_HOST_CMD_SEND_RESULT,
318 #endif /* CONFIG_ESPI_PERIPHERAL_CUSTOM_OPCODE */
319 };
320 
321 /* KBC 8042 event: Input Buffer Full */
322 #define HOST_KBC_EVT_IBF BIT(0)
323 /* KBC 8042 event: Output Buffer Empty */
324 #define HOST_KBC_EVT_OBE BIT(1)
325 /**
326  * @brief Bit field definition of evt_data in struct espi_event for KBC.
327  */
328 struct espi_evt_data_kbc {
329 	uint32_t type:8;
330 	uint32_t data:8;
331 	uint32_t evt:8;
332 	uint32_t reserved:8;
333 };
334 
335 /**
336  * @brief Bit field definition of evt_data in struct espi_event for ACPI.
337  */
338 struct espi_evt_data_acpi {
339 	uint32_t type:8;
340 	uint32_t data:8;
341 	uint32_t reserved:16;
342 };
343 
344 /**
345  * @brief eSPI event
346  */
347 struct espi_event {
348 	/** Event type */
349 	enum espi_bus_event evt_type;
350 	/** Additional details for bus event type */
351 	uint32_t evt_details;
352 	/** Data associated to the event */
353 	uint32_t evt_data;
354 };
355 
356 /**
357  * @brief eSPI bus configuration parameters
358  */
359 struct espi_cfg {
360 	/** Supported I/O mode */
361 	enum espi_io_mode io_caps;
362 	/** Supported channels */
363 	enum espi_channel channel_caps;
364 	/** Maximum supported frequency in MHz */
365 	uint8_t max_freq;
366 };
367 
368 /**
369  * @brief eSPI peripheral request packet format
370  */
371 struct espi_request_packet {
372 	enum espi_cycle_type cycle_type;
373 	uint8_t tag;
374 	uint16_t len;
375 	uint32_t address;
376 	uint8_t *data;
377 };
378 
379 /**
380  * @brief eSPI out-of-band transaction packet format
381  *
382  * For Tx packet, eSPI driver client shall specify the OOB payload data and its length in bytes.
383  * For Rx packet, eSPI driver client shall indicate the maximum number of bytes that can receive,
384  * while the eSPI driver should update the length field with the actual data received/available.
385  *
386  * In all cases, the length does not include OOB header size 3 bytes.
387  */
388 struct espi_oob_packet {
389 	uint8_t *buf;
390 	uint16_t len;
391 };
392 
393 /**
394  * @brief eSPI flash transactions packet format
395  */
396 struct espi_flash_packet {
397 	uint8_t *buf;
398 	uint32_t flash_addr;
399 	uint16_t len;
400 };
401 
402 struct espi_callback;
403 
404 /**
405  * @typedef espi_callback_handler_t
406  * @brief Define the application callback handler function signature.
407  *
408  * @param dev Device struct for the eSPI device.
409  * @param cb Original struct espi_callback owning this handler.
410  * @param espi_evt event details that trigger the callback handler.
411  *
412  */
413 typedef void (*espi_callback_handler_t) (const struct device *dev,
414 					 struct espi_callback *cb,
415 					 struct espi_event espi_evt);
416 
417 /**
418  * @cond INTERNAL_HIDDEN
419  *
420  * Used to register a callback in the driver instance callback list.
421  * As many callbacks as needed can be added as long as each of them
422  * are unique pointers of struct espi_callback.
423  * Beware such structure should not be allocated on stack.
424  *
425  * Note: To help setting it, see espi_init_callback() below
426  */
427 struct espi_callback {
428 	/** This is meant to be used in the driver only */
429 	sys_snode_t node;
430 
431 	/** Actual callback function being called when relevant */
432 	espi_callback_handler_t handler;
433 
434 	/** An event which user is interested in, if 0 the callback
435 	 * will never be called. Such evt_mask can be modified whenever
436 	 * necessary by the owner, and thus will affect the handler being
437 	 * called or not.
438 	 */
439 	enum espi_bus_event evt_type;
440 };
441 /** @endcond */
442 
443 /**
444  * @cond INTERNAL_HIDDEN
445  *
446  * eSPI driver API definition and system call entry points
447  *
448  * (Internal use only.)
449  */
450 typedef int (*espi_api_config)(const struct device *dev, struct espi_cfg *cfg);
451 typedef bool (*espi_api_get_channel_status)(const struct device *dev,
452 					    enum espi_channel ch);
453 /* Logical Channel 0 APIs */
454 typedef int (*espi_api_read_request)(const struct device *dev,
455 				     struct espi_request_packet *req);
456 typedef int (*espi_api_write_request)(const struct device *dev,
457 				      struct espi_request_packet *req);
458 typedef int (*espi_api_lpc_read_request)(const struct device *dev,
459 					 enum lpc_peripheral_opcode op,
460 					 uint32_t *data);
461 typedef int (*espi_api_lpc_write_request)(const struct device *dev,
462 					  enum lpc_peripheral_opcode op,
463 					  uint32_t *data);
464 /* Logical Channel 1 APIs */
465 typedef int (*espi_api_send_vwire)(const struct device *dev,
466 				   enum espi_vwire_signal vw,
467 				   uint8_t level);
468 typedef int (*espi_api_receive_vwire)(const struct device *dev,
469 				      enum espi_vwire_signal vw,
470 				      uint8_t *level);
471 /* Logical Channel 2 APIs */
472 typedef int (*espi_api_send_oob)(const struct device *dev,
473 				 struct espi_oob_packet *pckt);
474 typedef int (*espi_api_receive_oob)(const struct device *dev,
475 				    struct espi_oob_packet *pckt);
476 /* Logical Channel 3 APIs */
477 typedef int (*espi_api_flash_read)(const struct device *dev,
478 				   struct espi_flash_packet *pckt);
479 typedef int (*espi_api_flash_write)(const struct device *dev,
480 				    struct espi_flash_packet *pckt);
481 typedef int (*espi_api_flash_erase)(const struct device *dev,
482 				    struct espi_flash_packet *pckt);
483 /* Callbacks and traffic intercept */
484 typedef int (*espi_api_manage_callback)(const struct device *dev,
485 					struct espi_callback *callback,
486 					bool set);
487 
488 __subsystem struct espi_driver_api {
489 	espi_api_config config;
490 	espi_api_get_channel_status get_channel_status;
491 	espi_api_read_request read_request;
492 	espi_api_write_request write_request;
493 	espi_api_lpc_read_request read_lpc_request;
494 	espi_api_lpc_write_request write_lpc_request;
495 	espi_api_send_vwire send_vwire;
496 	espi_api_receive_vwire receive_vwire;
497 	espi_api_send_oob send_oob;
498 	espi_api_receive_oob receive_oob;
499 	espi_api_flash_read flash_read;
500 	espi_api_flash_write flash_write;
501 	espi_api_flash_erase flash_erase;
502 	espi_api_manage_callback manage_callback;
503 };
504 
505 /**
506  * @endcond
507  */
508 
509 /**
510  * @brief Configure operation of a eSPI controller.
511  *
512  * This routine provides a generic interface to override eSPI controller
513  * capabilities.
514  *
515  * If this eSPI controller is acting as target, the values set here
516  * will be discovered as part through the GET_CONFIGURATION command
517  * issued by the eSPI controller during initialization.
518  *
519  * If this eSPI controller is acting as controller, the values set here
520  * will be used by eSPI controller to determine minimum common capabilities with
521  * eSPI target then send via SET_CONFIGURATION command.
522  *
523  * @code
524  * +---------+   +---------+     +------+          +---------+   +---------+
525  * |  eSPI   |   |  eSPI   |     | eSPI |          |  eSPI   |   |  eSPI   |
526  * |  target |   | driver  |     |  bus |          |  driver |   |  host   |
527  * +--------+   +---------+     +------+          +---------+   +---------+
528  *     |              |            |                   |             |
529  *     | espi_config  | Set eSPI   |       Set eSPI    | espi_config |
530  *     +--------------+ ctrl regs  |       cap ctrl reg| +-----------+
531  *     |              +-------+    |          +--------+             |
532  *     |              |<------+    |          +------->|             |
533  *     |              |            |                   |             |
534  *     |              |            |                   |             |
535  *     |              |            | GET_CONFIGURATION |             |
536  *     |              |            +<------------------+             |
537  *     |              |<-----------|                   |             |
538  *     |              | eSPI caps  |                   |             |
539  *     |              |----------->+    response       |             |
540  *     |              |            |------------------>+             |
541  *     |              |            |                   |             |
542  *     |              |            | SET_CONFIGURATION |             |
543  *     |              |            +<------------------+             |
544  *     |              |            |  accept           |             |
545  *     |              |            +------------------>+             |
546  *     +              +            +                   +             +
547  * @endcode
548  *
549  * @param dev Pointer to the device structure for the driver instance.
550  * @param cfg the device runtime configuration for the eSPI controller.
551  *
552  * @retval 0 If successful.
553  * @retval -EIO General input / output error, failed to configure device.
554  * @retval -EINVAL invalid capabilities, failed to configure device.
555  * @retval -ENOTSUP capability not supported by eSPI target.
556  */
557 __syscall int espi_config(const struct device *dev, struct espi_cfg *cfg);
558 
z_impl_espi_config(const struct device * dev,struct espi_cfg * cfg)559 static inline int z_impl_espi_config(const struct device *dev,
560 				     struct espi_cfg *cfg)
561 {
562 	const struct espi_driver_api *api =
563 		(const struct espi_driver_api *)dev->api;
564 
565 	return api->config(dev, cfg);
566 }
567 
568 /**
569  * @brief Query to see if it a channel is ready.
570  *
571  * This routine allows to check if logical channel is ready before use.
572  * Note that queries for channels not supported will always return false.
573  *
574  * @param dev Pointer to the device structure for the driver instance.
575  * @param ch the eSPI channel for which status is to be retrieved.
576  *
577  * @retval true If eSPI channel is ready.
578  * @retval false otherwise.
579  */
580 __syscall bool espi_get_channel_status(const struct device *dev,
581 				       enum espi_channel ch);
582 
z_impl_espi_get_channel_status(const struct device * dev,enum espi_channel ch)583 static inline bool z_impl_espi_get_channel_status(const struct device *dev,
584 						  enum espi_channel ch)
585 {
586 	const struct espi_driver_api *api =
587 		(const struct espi_driver_api *)dev->api;
588 
589 	return api->get_channel_status(dev, ch);
590 }
591 
592 /**
593  * @brief Sends memory, I/O or message read request over eSPI.
594  *
595  * This routines provides a generic interface to send a read request packet.
596  *
597  * @param dev Pointer to the device structure for the driver instance.
598  * @param req Address of structure representing a memory,
599  *            I/O or message read request.
600  *
601  * @retval 0 If successful.
602  * @retval -ENOTSUP if eSPI controller doesn't support raw packets and instead
603  *         low memory transactions are handled by controller hardware directly.
604  * @retval -EIO General input / output error, failed to send over the bus.
605  */
606 __syscall int espi_read_request(const struct device *dev,
607 				struct espi_request_packet *req);
608 
z_impl_espi_read_request(const struct device * dev,struct espi_request_packet * req)609 static inline int z_impl_espi_read_request(const struct device *dev,
610 					   struct espi_request_packet *req)
611 {
612 	const struct espi_driver_api *api =
613 		(const struct espi_driver_api *)dev->api;
614 
615 	if (!api->read_request) {
616 		return -ENOTSUP;
617 	}
618 
619 	return api->read_request(dev, req);
620 }
621 
622 /**
623  * @brief Sends memory, I/O or message write request over eSPI.
624  *
625  * This routines provides a generic interface to send a write request packet.
626  *
627  * @param dev Pointer to the device structure for the driver instance.
628  * @param req Address of structure representing a memory, I/O or
629  *            message write request.
630  *
631  * @retval 0 If successful.
632  * @retval -ENOTSUP if eSPI controller doesn't support raw packets and instead
633  *         low memory transactions are handled by controller hardware directly.
634  * @retval -EINVAL General input / output error, failed to send over the bus.
635  */
636 __syscall int espi_write_request(const struct device *dev,
637 				 struct espi_request_packet *req);
638 
z_impl_espi_write_request(const struct device * dev,struct espi_request_packet * req)639 static inline int z_impl_espi_write_request(const struct device *dev,
640 					    struct espi_request_packet *req)
641 {
642 	const struct espi_driver_api *api =
643 		(const struct espi_driver_api *)dev->api;
644 
645 	if (!api->write_request) {
646 		return -ENOTSUP;
647 	}
648 
649 	return api->write_request(dev, req);
650 }
651 
652 /**
653  * @brief Reads SOC data from a LPC peripheral with information
654  * updated over eSPI.
655  *
656  * This routine provides a generic interface to read a block whose
657  * information was updated by an eSPI transaction. Reading may trigger
658  * a transaction. The eSPI packet is assembled by the HW block.
659  *
660  * @param dev Pointer to the device structure for the driver instance.
661  * @param op Enum representing opcode for peripheral type and read request.
662  * @param data Parameter to be read from to the LPC peripheral.
663  *
664  * @retval 0 If successful.
665  * @retval -ENOTSUP if eSPI peripheral is off or not supported.
666  * @retval -EINVAL for unimplemented lpc opcode, but in range.
667  */
668 __syscall int espi_read_lpc_request(const struct device *dev,
669 				    enum lpc_peripheral_opcode op,
670 				    uint32_t *data);
671 
z_impl_espi_read_lpc_request(const struct device * dev,enum lpc_peripheral_opcode op,uint32_t * data)672 static inline int z_impl_espi_read_lpc_request(const struct device *dev,
673 					       enum lpc_peripheral_opcode op,
674 					       uint32_t *data)
675 {
676 	const struct espi_driver_api *api =
677 		(const struct espi_driver_api *)dev->api;
678 
679 	if (!api->read_lpc_request) {
680 		return -ENOTSUP;
681 	}
682 
683 	return api->read_lpc_request(dev, op, data);
684 }
685 
686 /**
687  * @brief Writes data to a LPC peripheral which generates an eSPI transaction.
688  *
689  * This routine provides a generic interface to write data to a block which
690  * triggers an eSPI transaction. The eSPI packet is assembled by the HW
691  * block.
692  *
693  * @param dev Pointer to the device structure for the driver instance.
694  * @param op Enum representing an opcode for peripheral type and write request.
695  * @param data Represents the parameter passed to the LPC peripheral.
696  *
697  * @retval 0 If successful.
698  * @retval -ENOTSUP if eSPI peripheral is off or not supported.
699  * @retval -EINVAL for unimplemented lpc opcode, but in range.
700  */
701 __syscall int espi_write_lpc_request(const struct device *dev,
702 				     enum lpc_peripheral_opcode op,
703 				     uint32_t *data);
704 
z_impl_espi_write_lpc_request(const struct device * dev,enum lpc_peripheral_opcode op,uint32_t * data)705 static inline int z_impl_espi_write_lpc_request(const struct device *dev,
706 						enum lpc_peripheral_opcode op,
707 						uint32_t *data)
708 {
709 	const struct espi_driver_api *api =
710 		(const struct espi_driver_api *)dev->api;
711 
712 	if (!api->write_lpc_request) {
713 		return -ENOTSUP;
714 	}
715 
716 	return api->write_lpc_request(dev, op, data);
717 }
718 
719 /**
720  * @brief Sends system/platform signal as a virtual wire packet.
721  *
722  * This routines provides a generic interface to send a virtual wire packet
723  * from target to controller.
724  *
725  * @param dev Pointer to the device structure for the driver instance.
726  * @param signal The signal to be send to eSPI controller.
727  * @param level The level of signal requested LOW or HIGH.
728  *
729  * @retval 0 If successful.
730  * @retval -EIO General input / output error, failed to send over the bus.
731  */
732 __syscall int espi_send_vwire(const struct device *dev,
733 			      enum espi_vwire_signal signal,
734 			      uint8_t level);
735 
z_impl_espi_send_vwire(const struct device * dev,enum espi_vwire_signal signal,uint8_t level)736 static inline int z_impl_espi_send_vwire(const struct device *dev,
737 					 enum espi_vwire_signal signal,
738 					 uint8_t level)
739 {
740 	const struct espi_driver_api *api =
741 		(const struct espi_driver_api *)dev->api;
742 
743 	return api->send_vwire(dev, signal, level);
744 }
745 
746 /**
747  * @brief Retrieves level status for a signal encapsulated in a virtual wire.
748  *
749  * This routines provides a generic interface to request a virtual wire packet
750  * from eSPI controller and retrieve the signal level.
751  *
752  * @param dev Pointer to the device structure for the driver instance.
753  * @param signal the signal to be requested from eSPI controller.
754  * @param level the level of signal requested 0b LOW, 1b HIGH.
755  *
756  * @retval -EIO General input / output error, failed request to controller.
757  */
758 __syscall int espi_receive_vwire(const struct device *dev,
759 				 enum espi_vwire_signal signal,
760 				 uint8_t *level);
761 
z_impl_espi_receive_vwire(const struct device * dev,enum espi_vwire_signal signal,uint8_t * level)762 static inline int z_impl_espi_receive_vwire(const struct device *dev,
763 					    enum espi_vwire_signal signal,
764 					    uint8_t *level)
765 {
766 	const struct espi_driver_api *api =
767 		(const struct espi_driver_api *)dev->api;
768 
769 	return api->receive_vwire(dev, signal, level);
770 }
771 
772 /**
773  * @brief Sends SMBus transaction (out-of-band) packet over eSPI bus.
774  *
775  * This routines provides an interface to encapsulate a SMBus transaction
776  * and send into packet over eSPI bus
777  *
778  * @param dev Pointer to the device structure for the driver instance.
779  * @param pckt Address of the packet representation of SMBus transaction.
780  *
781  * @retval -EIO General input / output error, failed request to controller.
782  */
783 __syscall int espi_send_oob(const struct device *dev,
784 			    struct espi_oob_packet *pckt);
785 
z_impl_espi_send_oob(const struct device * dev,struct espi_oob_packet * pckt)786 static inline int z_impl_espi_send_oob(const struct device *dev,
787 				       struct espi_oob_packet *pckt)
788 {
789 	const struct espi_driver_api *api =
790 		(const struct espi_driver_api *)dev->api;
791 
792 	if (!api->send_oob) {
793 		return -ENOTSUP;
794 	}
795 
796 	return api->send_oob(dev, pckt);
797 }
798 
799 /**
800  * @brief Receives SMBus transaction (out-of-band) packet from eSPI bus.
801  *
802  * This routines provides an interface to receive and decoded a SMBus
803  * transaction from eSPI bus
804  *
805  * @param dev Pointer to the device structure for the driver instance.
806  * @param pckt Address of the packet representation of SMBus transaction.
807  *
808  * @retval -EIO General input / output error, failed request to controller.
809  */
810 __syscall int espi_receive_oob(const struct device *dev,
811 			       struct espi_oob_packet *pckt);
812 
z_impl_espi_receive_oob(const struct device * dev,struct espi_oob_packet * pckt)813 static inline int z_impl_espi_receive_oob(const struct device *dev,
814 					  struct espi_oob_packet *pckt)
815 {
816 	const struct espi_driver_api *api =
817 		(const struct espi_driver_api *)dev->api;
818 
819 	if (!api->receive_oob) {
820 		return -ENOTSUP;
821 	}
822 
823 	return api->receive_oob(dev, pckt);
824 }
825 
826 /**
827  * @brief Sends a read request packet for shared flash.
828  *
829  * This routines provides an interface to send a request to read the flash
830  * component shared between the eSPI controller and eSPI targets.
831  *
832  * @param dev Pointer to the device structure for the driver instance.
833  * @param pckt Address of the representation of read flash transaction.
834  *
835  * @retval -ENOTSUP eSPI flash logical channel transactions not supported.
836  * @retval -EBUSY eSPI flash channel is not ready or disabled by controller.
837  * @retval -EIO General input / output error, failed request to controller.
838  */
839 __syscall int espi_read_flash(const struct device *dev,
840 			      struct espi_flash_packet *pckt);
841 
z_impl_espi_read_flash(const struct device * dev,struct espi_flash_packet * pckt)842 static inline int z_impl_espi_read_flash(const struct device *dev,
843 					 struct espi_flash_packet *pckt)
844 {
845 	const struct espi_driver_api *api =
846 		(const struct espi_driver_api *)dev->api;
847 
848 	if (!api->flash_read) {
849 		return -ENOTSUP;
850 	}
851 
852 	return api->flash_read(dev, pckt);
853 }
854 
855 /**
856  * @brief Sends a write request packet for shared flash.
857  *
858  * This routines provides an interface to send a request to write to the flash
859  * components shared between the eSPI controller and eSPI targets.
860  *
861  * @param dev Pointer to the device structure for the driver instance.
862  * @param pckt Address of the representation of write flash transaction.
863  *
864  * @retval -ENOTSUP eSPI flash logical channel transactions not supported.
865  * @retval -EBUSY eSPI flash channel is not ready or disabled by controller.
866  * @retval -EIO General input / output error, failed request to controller.
867  */
868 __syscall int espi_write_flash(const struct device *dev,
869 			       struct espi_flash_packet *pckt);
870 
z_impl_espi_write_flash(const struct device * dev,struct espi_flash_packet * pckt)871 static inline int z_impl_espi_write_flash(const struct device *dev,
872 					  struct espi_flash_packet *pckt)
873 {
874 	const struct espi_driver_api *api =
875 		(const struct espi_driver_api *)dev->api;
876 
877 	if (!api->flash_write) {
878 		return -ENOTSUP;
879 	}
880 
881 	return api->flash_write(dev, pckt);
882 }
883 
884 /**
885  * @brief Sends a write request packet for shared flash.
886  *
887  * This routines provides an interface to send a request to write to the flash
888  * components shared between the eSPI controller and eSPI targets.
889  *
890  * @param dev Pointer to the device structure for the driver instance.
891  * @param pckt Address of the representation of write flash transaction.
892  *
893  * @retval -ENOTSUP eSPI flash logical channel transactions not supported.
894  * @retval -EBUSY eSPI flash channel is not ready or disabled by controller.
895  * @retval -EIO General input / output error, failed request to controller.
896  */
897 __syscall int espi_flash_erase(const struct device *dev,
898 			       struct espi_flash_packet *pckt);
899 
z_impl_espi_flash_erase(const struct device * dev,struct espi_flash_packet * pckt)900 static inline int z_impl_espi_flash_erase(const struct device *dev,
901 					  struct espi_flash_packet *pckt)
902 {
903 	const struct espi_driver_api *api =
904 		(const struct espi_driver_api *)dev->api;
905 
906 	if (!api->flash_erase) {
907 		return -ENOTSUP;
908 	}
909 
910 	return api->flash_erase(dev, pckt);
911 }
912 
913 /**
914  * Callback model
915  *
916  * @code
917  *+-------+                  +-------------+   +------+     +---------+
918  *|  App  |                  | eSPI driver |   |  HW  |     |eSPI Host|
919  *+---+---+                  +-------+-----+   +---+--+     +----+----+
920  *    |                              |             |             |
921  *    |   espi_init_callback         |             |             |
922  *    +----------------------------> |             |             |
923  *    |   espi_add_callback          |             |
924  *    +----------------------------->+             |
925  *    |                              |             |  eSPI reset |  eSPI host
926  *    |                              |    IRQ      +<------------+  resets the
927  *    |                              | <-----------+             |  bus
928  *    |<-----------------------------|             |             |
929  *    | Report eSPI bus reset        | Processed   |             |
930  *    |                              | within the  |             |
931  *    |                              | driver      |             |
932  *    |                              |             |             |
933  *    |                              |             |  VW CH ready|  eSPI host
934  *    |                              |    IRQ      +<------------+  enables VW
935  *    |                              | <-----------+             |  channel
936  *    |                              |             |             |
937  *    |                              | Processed   |             |
938  *    |                              | within the  |             |
939  *    |                              | driver      |             |
940  *    |                              |             |             |
941  *    |                              |             | Memory I/O  |  Peripheral
942  *    |                              |             <-------------+  event
943  *    |                              +<------------+             |
944  *    +<-----------------------------+ callback    |             |
945  *    | Report peripheral event      |             |             |
946  *    | and data for the event       |             |             |
947  *    |                              |             |             |
948  *    |                              |             | SLP_S5      |  eSPI host
949  *    |                              |             <-------------+  send VWire
950  *    |                              +<------------+             |
951  *    +<-----------------------------+ callback    |             |
952  *    | App enables/configures       |             |             |
953  *    | discrete regulator           |             |             |
954  *    |                              |             |             |
955  *    |   espi_send_vwire_signal     |             |             |
956  *    +------------------------------>------------>|------------>|
957  *    |                              |             |             |
958  *    |                              |             | HOST_RST    |  eSPI host
959  *    |                              |             <-------------+  send VWire
960  *    |                              +<------------+             |
961  *    +<-----------------------------+ callback    |             |
962  *    | App reset host-related       |             |             |
963  *    | data structures              |             |             |
964  *    |                              |             |             |
965  *    |                              |             |   C10       |  eSPI host
966  *    |                              |             +<------------+  send VWire
967  *    |                              <-------------+             |
968  *    <------------------------------+             |             |
969  *    | App executes                 |             |             |
970  *    + power mgmt policy            |             |             |
971  * @endcode
972  */
973 
974 /**
975  * @brief Helper to initialize a struct espi_callback properly.
976  *
977  * @param callback A valid Application's callback structure pointer.
978  * @param handler A valid handler function pointer.
979  * @param evt_type indicates the eSPI event relevant for the handler.
980  * for VWIRE_RECEIVED event the data will indicate the new level asserted
981  */
espi_init_callback(struct espi_callback * callback,espi_callback_handler_t handler,enum espi_bus_event evt_type)982 static inline void espi_init_callback(struct espi_callback *callback,
983 				      espi_callback_handler_t handler,
984 				      enum espi_bus_event evt_type)
985 {
986 	__ASSERT(callback, "Callback pointer should not be NULL");
987 	__ASSERT(handler, "Callback handler pointer should not be NULL");
988 
989 	callback->handler = handler;
990 	callback->evt_type = evt_type;
991 }
992 
993 /**
994  * @brief Add an application callback.
995  * @param dev Pointer to the device structure for the driver instance.
996  * @param callback A valid Application's callback structure pointer.
997  * @return 0 if successful, negative errno code on failure.
998  *
999  * @note Callbacks may be added to the device from within a callback
1000  * handler invocation, but whether they are invoked for the current
1001  * eSPI event is not specified.
1002  *
1003  * Note: enables to add as many callback as needed on the same device.
1004  */
espi_add_callback(const struct device * dev,struct espi_callback * callback)1005 static inline int espi_add_callback(const struct device *dev,
1006 				    struct espi_callback *callback)
1007 {
1008 	const struct espi_driver_api *api =
1009 		(const struct espi_driver_api *)dev->api;
1010 
1011 	if (!api->manage_callback) {
1012 		return -ENOTSUP;
1013 	}
1014 
1015 	return api->manage_callback(dev, callback, true);
1016 }
1017 
1018 /**
1019  * @brief Remove an application callback.
1020  * @param dev Pointer to the device structure for the driver instance.
1021  * @param callback A valid application's callback structure pointer.
1022  * @return 0 if successful, negative errno code on failure.
1023  *
1024  * @warning It is explicitly permitted, within a callback handler, to
1025  * remove the registration for the callback that is running, i.e. @p
1026  * callback.  Attempts to remove other registrations on the same
1027  * device may result in undefined behavior, including failure to
1028  * invoke callbacks that remain registered and unintended invocation
1029  * of removed callbacks.
1030  *
1031  * Note: enables to remove as many callbacks as added through
1032  *       espi_add_callback().
1033  */
espi_remove_callback(const struct device * dev,struct espi_callback * callback)1034 static inline int espi_remove_callback(const struct device *dev,
1035 				       struct espi_callback *callback)
1036 {
1037 	const struct espi_driver_api *api =
1038 		(const struct espi_driver_api *)dev->api;
1039 
1040 	if (!api->manage_callback) {
1041 		return -ENOTSUP;
1042 	}
1043 
1044 	return api->manage_callback(dev, callback, false);
1045 }
1046 
1047 #ifdef __cplusplus
1048 }
1049 #endif
1050 
1051 /**
1052  * @}
1053  */
1054 #include <zephyr/syscalls/espi.h>
1055 #endif /* ZEPHYR_INCLUDE_ESPI_H_ */
1056