1 /* SPDX-License-Identifier: GPL-2.0-only 2 * 3 * Copyright (c) 2021, MediaTek Inc. 4 * Copyright (c) 2021-2022, Intel Corporation. 5 * 6 * Authors: 7 * Amir Hanania <amir.hanania@intel.com> 8 * Haijun Liu <haijun.liu@mediatek.com> 9 * Moises Veleta <moises.veleta@intel.com> 10 * 11 * Contributors: 12 * Eliot Lee <eliot.lee@intel.com> 13 * Ricardo Martinez <ricardo.martinez@linux.intel.com> 14 * Sreehari Kancharla <sreehari.kancharla@intel.com> 15 */ 16 17 #ifndef __T7XX_MONITOR_H__ 18 #define __T7XX_MONITOR_H__ 19 20 #include <linux/bits.h> 21 #include <linux/sched.h> 22 #include <linux/spinlock.h> 23 #include <linux/types.h> 24 #include <linux/wait.h> 25 26 #include "t7xx_modem_ops.h" 27 28 enum t7xx_fsm_state { 29 FSM_STATE_INIT, 30 FSM_STATE_PRE_START, 31 FSM_STATE_STARTING, 32 FSM_STATE_READY, 33 FSM_STATE_EXCEPTION, 34 FSM_STATE_STOPPING, 35 FSM_STATE_STOPPED, 36 }; 37 38 enum t7xx_fsm_event_state { 39 FSM_EVENT_INVALID, 40 FSM_EVENT_MD_HS2, 41 FSM_EVENT_MD_EX, 42 FSM_EVENT_MD_EX_REC_OK, 43 FSM_EVENT_MD_EX_PASS, 44 FSM_EVENT_MD_HS2_EXIT, 45 FSM_EVENT_MAX 46 }; 47 48 enum t7xx_fsm_cmd_state { 49 FSM_CMD_INVALID, 50 FSM_CMD_START, 51 FSM_CMD_EXCEPTION, 52 FSM_CMD_PRE_STOP, 53 FSM_CMD_STOP, 54 }; 55 56 enum t7xx_ex_reason { 57 EXCEPTION_HS_TIMEOUT, 58 EXCEPTION_EVENT, 59 }; 60 61 enum t7xx_md_irq_type { 62 MD_IRQ_WDT, 63 MD_IRQ_CCIF_EX, 64 MD_IRQ_PORT_ENUM, 65 }; 66 67 enum md_state { 68 MD_STATE_INVALID, 69 MD_STATE_WAITING_FOR_HS1, 70 MD_STATE_WAITING_FOR_HS2, 71 MD_STATE_READY, 72 MD_STATE_EXCEPTION, 73 MD_STATE_WAITING_TO_STOP, 74 MD_STATE_STOPPED, 75 }; 76 77 #define FSM_CMD_FLAG_WAIT_FOR_COMPLETION BIT(0) 78 #define FSM_CMD_FLAG_FLIGHT_MODE BIT(1) 79 #define FSM_CMD_FLAG_IN_INTERRUPT BIT(2) 80 #define FSM_CMD_EX_REASON GENMASK(23, 16) 81 82 struct t7xx_fsm_ctl { 83 struct t7xx_modem *md; 84 enum md_state md_state; 85 unsigned int curr_state; 86 struct list_head command_queue; 87 struct list_head event_queue; 88 wait_queue_head_t command_wq; 89 wait_queue_head_t event_wq; 90 wait_queue_head_t async_hk_wq; 91 spinlock_t event_lock; /* Protects event queue */ 92 spinlock_t command_lock; /* Protects command queue */ 93 struct task_struct *fsm_thread; 94 bool exp_flg; 95 spinlock_t notifier_lock; /* Protects notifier list */ 96 struct list_head notifier_list; 97 }; 98 99 struct t7xx_fsm_event { 100 struct list_head entry; 101 enum t7xx_fsm_event_state event_id; 102 unsigned int length; 103 unsigned char data[]; 104 }; 105 106 struct t7xx_fsm_command { 107 struct list_head entry; 108 enum t7xx_fsm_cmd_state cmd_id; 109 unsigned int flag; 110 struct completion *done; 111 int *ret; 112 }; 113 114 struct t7xx_fsm_notifier { 115 struct list_head entry; 116 int (*notifier_fn)(enum md_state state, void *data); 117 void *data; 118 }; 119 120 int t7xx_fsm_append_cmd(struct t7xx_fsm_ctl *ctl, enum t7xx_fsm_cmd_state cmd_id, 121 unsigned int flag); 122 int t7xx_fsm_append_event(struct t7xx_fsm_ctl *ctl, enum t7xx_fsm_event_state event_id, 123 unsigned char *data, unsigned int length); 124 void t7xx_fsm_clr_event(struct t7xx_fsm_ctl *ctl, enum t7xx_fsm_event_state event_id); 125 void t7xx_fsm_broadcast_state(struct t7xx_fsm_ctl *ctl, enum md_state state); 126 void t7xx_fsm_reset(struct t7xx_modem *md); 127 int t7xx_fsm_init(struct t7xx_modem *md); 128 void t7xx_fsm_uninit(struct t7xx_modem *md); 129 int t7xx_fsm_recv_md_intr(struct t7xx_fsm_ctl *ctl, enum t7xx_md_irq_type type); 130 enum md_state t7xx_fsm_get_md_state(struct t7xx_fsm_ctl *ctl); 131 unsigned int t7xx_fsm_get_ctl_state(struct t7xx_fsm_ctl *ctl); 132 void t7xx_fsm_notifier_register(struct t7xx_modem *md, struct t7xx_fsm_notifier *notifier); 133 void t7xx_fsm_notifier_unregister(struct t7xx_modem *md, struct t7xx_fsm_notifier *notifier); 134 135 #endif /* __T7XX_MONITOR_H__ */ 136