drivers/net/wwan/t7xx/t7xx_state_monitor.c

Source file repositories/reference/linux-study-clean/drivers/net/wwan/t7xx/t7xx_state_monitor.c

File Facts

System
Linux kernel
Corpus path
drivers/net/wwan/t7xx/t7xx_state_monitor.c
Extension
.c
Size
17045 bytes
Lines
650
Domain
Driver Families
Bucket
drivers/net
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

if (event) {
			event_received = event->event_id == event_expected;
			if (event_received || event->event_id == event_ignore) {
				fsm_del_kf_event(event);
				sleep_required = false;
			}
		}
		spin_unlock_irqrestore(&ctl->event_lock, flags);

		if (sleep_required)
			msleep(FSM_EVENT_POLL_INTERVAL_MS);
	}
}

static void fsm_routine_exception(struct t7xx_fsm_ctl *ctl, struct t7xx_fsm_command *cmd,
				  enum t7xx_ex_reason reason)
{
	struct device *dev = &ctl->md->t7xx_dev->pdev->dev;

	if (ctl->curr_state != FSM_STATE_READY && ctl->curr_state != FSM_STATE_STARTING) {
		if (cmd)
			fsm_finish_command(ctl, cmd, -EINVAL);

		return;
	}

	ctl->curr_state = FSM_STATE_EXCEPTION;

	switch (reason) {
	case EXCEPTION_HS_TIMEOUT:
		dev_err(dev, "Boot Handshake failure\n");
		break;

	case EXCEPTION_EVENT:
		dev_err(dev, "Exception event\n");
		t7xx_fsm_broadcast_state(ctl, MD_STATE_EXCEPTION);
		t7xx_pci_pm_exp_detected(ctl->md->t7xx_dev);
		t7xx_md_exception_handshake(ctl->md);

		fsm_wait_for_event(ctl, FSM_EVENT_MD_EX_REC_OK, FSM_EVENT_MD_EX,
				   FSM_MD_EX_REC_OK_TIMEOUT_MS / FSM_EVENT_POLL_INTERVAL_MS);
		fsm_wait_for_event(ctl, FSM_EVENT_MD_EX_PASS, FSM_EVENT_INVALID,
				   FSM_MD_EX_PASS_TIMEOUT_MS / FSM_EVENT_POLL_INTERVAL_MS);
		break;

	default:
		dev_err(dev, "Exception %d\n", reason);
		break;
	}

	if (cmd)
		fsm_finish_command(ctl, cmd, 0);
}

static void t7xx_lk_stage_event_handling(struct t7xx_fsm_ctl *ctl, unsigned int status)
{
	struct t7xx_modem *md = ctl->md;
	struct cldma_ctrl *md_ctrl;
	enum lk_event_id lk_event;
	struct device *dev;
	struct t7xx_port *port;

	dev = &md->t7xx_dev->pdev->dev;
	lk_event = FIELD_GET(MISC_LK_EVENT_MASK, status);
	switch (lk_event) {
	case LK_EVENT_NORMAL:
	case LK_EVENT_RESET:
		break;

	case LK_EVENT_CREATE_PD_PORT:
	case LK_EVENT_CREATE_POST_DL_PORT:
		md_ctrl = md->md_ctrl[CLDMA_ID_AP];
		t7xx_cldma_hif_hw_init(md_ctrl);
		t7xx_cldma_stop(md_ctrl);
		t7xx_cldma_switch_cfg(md_ctrl, CLDMA_DEDICATED_Q_CFG);

		port = &ctl->md->port_prox->ports[0];
		port->port_conf->ops->enable_chl(port);

		t7xx_cldma_start(md_ctrl);

		if (lk_event == LK_EVENT_CREATE_POST_DL_PORT)
			t7xx_mode_update(md->t7xx_dev, T7XX_FASTBOOT_DOWNLOAD);
		else
			t7xx_mode_update(md->t7xx_dev, T7XX_FASTBOOT_DUMP);
		break;

	default:
		dev_err(dev, "Invalid LK event %d\n", lk_event);
		break;

Annotation

Implementation Notes