drivers/net/wwan/t7xx/t7xx_modem_ops.c

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

File Facts

System
Linux kernel
Corpus path
drivers/net/wwan/t7xx/t7xx_modem_ops.c
Extension
.c
Size
22887 bytes
Lines
832
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

struct feature_query {
	__le32 head_pattern;
	u8 feature_set[FEATURE_COUNT];
	__le32 tail_pattern;
};

static void t7xx_prepare_host_rt_data_query(struct t7xx_sys_info *core)
{
	struct feature_query *ft_query;
	struct sk_buff *skb;

	skb = t7xx_ctrl_alloc_skb(sizeof(*ft_query));
	if (!skb)
		return;

	ft_query = skb_put(skb, sizeof(*ft_query));
	ft_query->head_pattern = cpu_to_le32(MD_FEATURE_QUERY_ID);
	memcpy(ft_query->feature_set, core->feature_set, FEATURE_COUNT);
	ft_query->tail_pattern = cpu_to_le32(MD_FEATURE_QUERY_ID);

	/* Send HS1 message to device */
	t7xx_port_send_ctl_skb(core->ctl_port, skb, CTL_ID_HS1_MSG, 0);
}

static int t7xx_prepare_device_rt_data(struct t7xx_sys_info *core, struct device *dev,
				       void *data)
{
	struct feature_query *md_feature = data;
	struct mtk_runtime_feature *rt_feature;
	unsigned int i, rt_data_len = 0;
	struct sk_buff *skb;

	/* Parse MD runtime data query */
	if (le32_to_cpu(md_feature->head_pattern) != MD_FEATURE_QUERY_ID ||
	    le32_to_cpu(md_feature->tail_pattern) != MD_FEATURE_QUERY_ID) {
		dev_err(dev, "Invalid feature pattern: head 0x%x, tail 0x%x\n",
			le32_to_cpu(md_feature->head_pattern),
			le32_to_cpu(md_feature->tail_pattern));
		return -EINVAL;
	}

	for (i = 0; i < FEATURE_COUNT; i++) {
		if (FIELD_GET(FEATURE_MSK, md_feature->feature_set[i]) !=
		    MTK_FEATURE_MUST_BE_SUPPORTED)
			rt_data_len += sizeof(*rt_feature);
	}

	skb = t7xx_ctrl_alloc_skb(rt_data_len);
	if (!skb)
		return -ENOMEM;

	rt_feature = skb_put(skb, rt_data_len);
	memset(rt_feature, 0, rt_data_len);

	/* Fill runtime feature */
	for (i = 0; i < FEATURE_COUNT; i++) {
		u8 md_feature_mask = FIELD_GET(FEATURE_MSK, md_feature->feature_set[i]);

		if (md_feature_mask == MTK_FEATURE_MUST_BE_SUPPORTED)
			continue;

		rt_feature->feature_id = i;
		if (md_feature_mask == MTK_FEATURE_DOES_NOT_EXIST)
			rt_feature->support_info = md_feature->feature_set[i];

		rt_feature++;
	}

	/* Send HS3 message to device */
	t7xx_port_send_ctl_skb(core->ctl_port, skb, CTL_ID_HS3_MSG, 0);
	return 0;
}

static int t7xx_parse_host_rt_data(struct t7xx_fsm_ctl *ctl, struct t7xx_sys_info *core,
				   struct device *dev, void *data, int data_length)
{
	enum mtk_feature_support_type ft_spt_st, ft_spt_cfg;
	struct mtk_runtime_feature *rt_feature;
	int i, offset;

	offset = sizeof(struct feature_query);
	for (i = 0; i < FEATURE_COUNT && offset < data_length; i++) {
		size_t remaining = data_length - offset;
		size_t feat_data_len, feat_total;

		if (remaining < sizeof(*rt_feature))
			break;

		rt_feature = data + offset;
		feat_data_len = le32_to_cpu(rt_feature->data_len);

Annotation

Implementation Notes