drivers/hwtracing/coresight/coresight-tmc-etr.c

Source file repositories/reference/linux-study-clean/drivers/hwtracing/coresight/coresight-tmc-etr.c

File Facts

System
Linux kernel
Corpus path
drivers/hwtracing/coresight/coresight-tmc-etr.c
Extension
.c
Size
58014 bytes
Lines
2087
Domain
Driver Families
Bucket
drivers/hwtracing
Inferred role
Driver Families: exported/initcall integration point
Status
integration 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 etr_flat_buf {
	struct device	*dev;
	dma_addr_t	daddr;
	void		*vaddr;
	size_t		size;
};

struct etr_buf_hw {
	bool	has_iommu;
	bool	has_etr_sg;
	bool	has_catu;
	bool	has_resrv;
};

/*
 * etr_perf_buffer - Perf buffer used for ETR
 * @drvdata		- The ETR drvdaga this buffer has been allocated for.
 * @etr_buf		- Actual buffer used by the ETR
 * @pid			- The PID of the session owner that etr_perf_buffer
 *			  belongs to.
 * @snaphost		- Perf session mode
 * @nr_pages		- Number of pages in the ring buffer.
 * @pages		- Array of Pages in the ring buffer.
 */
struct etr_perf_buffer {
	struct tmc_drvdata	*drvdata;
	struct etr_buf		*etr_buf;
	pid_t			pid;
	bool			snapshot;
	int			nr_pages;
	void			**pages;
};

/* Convert the perf index to an offset within the ETR buffer */
#define PERF_IDX2OFF(idx, buf)		\
		((idx) % ((unsigned long)(buf)->nr_pages << PAGE_SHIFT))

/* Lower limit for ETR hardware buffer */
#define TMC_ETR_PERF_MIN_BUF_SIZE	SZ_1M

/*
 * The TMC ETR SG has a page size of 4K. The SG table contains pointers
 * to 4KB buffers. However, the OS may use a PAGE_SIZE different from
 * 4K (i.e, 16KB or 64KB). This implies that a single OS page could
 * contain more than one SG buffer and tables.
 *
 * A table entry has the following format:
 *
 * ---Bit31------------Bit4-------Bit1-----Bit0--
 * |     Address[39:12]    | SBZ |  Entry Type  |
 * ----------------------------------------------
 *
 * Address: Bits [39:12] of a physical page address. Bits [11:0] are
 *	    always zero.
 *
 * Entry type:
 *	b00 - Reserved.
 *	b01 - Last entry in the tables, points to 4K page buffer.
 *	b10 - Normal entry, points to 4K page buffer.
 *	b11 - Link. The address points to the base of next table.
 */

typedef u32 sgte_t;

#define ETR_SG_PAGE_SHIFT		12
#define ETR_SG_PAGE_SIZE		(1UL << ETR_SG_PAGE_SHIFT)
#define ETR_SG_PAGES_PER_SYSPAGE	(PAGE_SIZE / ETR_SG_PAGE_SIZE)
#define ETR_SG_PTRS_PER_PAGE		(ETR_SG_PAGE_SIZE / sizeof(sgte_t))
#define ETR_SG_PTRS_PER_SYSPAGE		(PAGE_SIZE / sizeof(sgte_t))

#define ETR_SG_ET_MASK			0x3
#define ETR_SG_ET_LAST			0x1
#define ETR_SG_ET_NORMAL		0x2
#define ETR_SG_ET_LINK			0x3

#define ETR_SG_ADDR_SHIFT		4

#define ETR_SG_ENTRY(addr, type) \
	(sgte_t)((((addr) >> ETR_SG_PAGE_SHIFT) << ETR_SG_ADDR_SHIFT) | \
		 (type & ETR_SG_ET_MASK))

#define ETR_SG_ADDR(entry) \
	(((dma_addr_t)(entry) >> ETR_SG_ADDR_SHIFT) << ETR_SG_PAGE_SHIFT)
#define ETR_SG_ET(entry)		((entry) & ETR_SG_ET_MASK)

/*
 * struct etr_sg_table : ETR SG Table
 * @sg_table:		Generic SG Table holding the data/table pages.
 * @hwaddr:		hwaddress used by the TMC, which is the base
 *			address of the table.

Annotation

Implementation Notes