drivers/net/wireless/broadcom/brcm80211/brcmfmac/feature.c

Source file repositories/reference/linux-study-clean/drivers/net/wireless/broadcom/brcm80211/brcmfmac/feature.c

File Facts

System
Linux kernel
Corpus path
drivers/net/wireless/broadcom/brcm80211/brcmfmac/feature.c
Extension
.c
Size
10246 bytes
Lines
386
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 brcmf_feat_fwcap {
	enum brcmf_feat_id feature;
	const char * const fwcap_id;
};

static const struct brcmf_feat_fwcap brcmf_fwcap_map[] = {
	{ BRCMF_FEAT_MBSS, "mbss" },
	{ BRCMF_FEAT_MCHAN, "mchan" },
	{ BRCMF_FEAT_P2P, "p2p" },
	{ BRCMF_FEAT_MONITOR, "monitor" },
	{ BRCMF_FEAT_MONITOR_FLAG, "rtap" },
	{ BRCMF_FEAT_MONITOR_FMT_RADIOTAP, "rtap" },
	{ BRCMF_FEAT_DOT11H, "802.11h" },
	{ BRCMF_FEAT_SAE, "sae " },
	{ BRCMF_FEAT_FWAUTH, "idauth" },
	{ BRCMF_FEAT_SAE_EXT, "sae_ext" },
};

#ifdef DEBUG
/*
 * expand quirk list to array of quirk strings.
 */
#define BRCMF_QUIRK_DEF(_q) \
	#_q,
static const char * const brcmf_quirk_names[] = {
	BRCMF_QUIRK_LIST
};
#undef BRCMF_QUIRK_DEF

/**
 * brcmf_feat_debugfs_read() - expose feature info to debugfs.
 *
 * @seq: sequence for debugfs entry.
 * @data: raw data pointer.
 */
static int brcmf_feat_debugfs_read(struct seq_file *seq, void *data)
{
	struct brcmf_bus *bus_if = dev_get_drvdata(seq->private);
	u32 feats = bus_if->drvr->feat_flags;
	u32 quirks = bus_if->drvr->chip_quirks;
	int id;

	seq_printf(seq, "Features: %08x\n", feats);
	for (id = 0; id < BRCMF_FEAT_LAST; id++)
		if (feats & BIT(id))
			seq_printf(seq, "\t%s\n", brcmf_feat_names[id]);
	seq_printf(seq, "\nQuirks:   %08x\n", quirks);
	for (id = 0; id < BRCMF_FEAT_QUIRK_LAST; id++)
		if (quirks & BIT(id))
			seq_printf(seq, "\t%s\n", brcmf_quirk_names[id]);
	return 0;
}
#else
static int brcmf_feat_debugfs_read(struct seq_file *seq, void *data)
{
	return 0;
}
#endif /* DEBUG */

struct brcmf_feat_fwfeat {
	const char * const fwid;
	u32 feat_flags;
};

static const struct brcmf_feat_fwfeat brcmf_feat_fwfeat_map[] = {
	/* brcmfmac43602-pcie.ap.bin from linux-firmware.git commit ea1178515b88 */
	{ "01-6cb8e269", BIT(BRCMF_FEAT_MONITOR) },
	/* brcmfmac4366b-pcie.bin from linux-firmware.git commit 52442afee990 */
	{ "01-c47a91a4", BIT(BRCMF_FEAT_MONITOR) },
	/* brcmfmac4366b-pcie.bin from linux-firmware.git commit 211de1679a68 */
	{ "01-801fb449", BIT(BRCMF_FEAT_MONITOR_FMT_HW_RX_HDR) },
	/* brcmfmac4366c-pcie.bin from linux-firmware.git commit 211de1679a68 */
	{ "01-d2cbb8fd", BIT(BRCMF_FEAT_MONITOR_FMT_HW_RX_HDR) },
};

static void brcmf_feat_firmware_overrides(struct brcmf_pub *drv)
{
	const struct brcmf_feat_fwfeat *e;
	u32 feat_flags = 0;
	int i;

	for (i = 0; i < ARRAY_SIZE(brcmf_feat_fwfeat_map); i++) {
		e = &brcmf_feat_fwfeat_map[i];
		if (!strcmp(e->fwid, drv->fwver)) {
			feat_flags = e->feat_flags;
			break;
		}
	}

	if (!feat_flags)

Annotation

Implementation Notes