xref: /kvmtool/include/kvm/pci.h (revision aa73be708a0195af0494a130bee69cfe28053d6a)
160742802SPekka Enberg #ifndef KVM__PCI_H
260742802SPekka Enberg #define KVM__PCI_H
360742802SPekka Enberg 
43fdf659dSSasha Levin #include <linux/types.h>
51de74957SSasha Levin #include <linux/kvm.h>
620c64ecaSPekka Enberg #include <linux/pci_regs.h>
71de74957SSasha Levin #include <linux/msi.h>
8*aa73be70SMatt Evans #include <endian.h>
976f9c841SCyrill Gorcunov 
109d755a36SMatt Evans #define PCI_MAX_DEVICES			256
114402a581SPekka Enberg /*
124402a581SPekka Enberg  * PCI Configuration Mechanism #1 I/O ports. See Section 3.7.4.1.
134402a581SPekka Enberg  * ("Configuration Mechanism #1") of the PCI Local Bus Specification 2.1 for
144402a581SPekka Enberg  * details.
154402a581SPekka Enberg  */
16305b72ceSCyrill Gorcunov #define PCI_CONFIG_ADDRESS	0xcf8
17305b72ceSCyrill Gorcunov #define PCI_CONFIG_DATA		0xcfc
182b9e4709SCyrill Gorcunov #define PCI_CONFIG_BUS_FORWARD	0xcfa
1995d13a52SSasha Levin #define PCI_IO_SIZE		0x100
20305b72ceSCyrill Gorcunov 
21*aa73be70SMatt Evans union pci_config_address {
22*aa73be70SMatt Evans 	struct {
23*aa73be70SMatt Evans #if __BYTE_ORDER == __LITTLE_ENDIAN
244402a581SPekka Enberg 		unsigned	zeros		: 2;		/* 1  .. 0  */
254402a581SPekka Enberg 		unsigned	register_number	: 6;		/* 7  .. 2  */
264402a581SPekka Enberg 		unsigned	function_number	: 3;		/* 10 .. 8  */
274402a581SPekka Enberg 		unsigned	device_number	: 5;		/* 15 .. 11 */
284402a581SPekka Enberg 		unsigned	bus_number	: 8;		/* 23 .. 16 */
294402a581SPekka Enberg 		unsigned	reserved	: 7;		/* 30 .. 24 */
304402a581SPekka Enberg 		unsigned	enable_bit	: 1;		/* 31       */
31*aa73be70SMatt Evans #else
32*aa73be70SMatt Evans 		unsigned	enable_bit	: 1;		/* 31       */
33*aa73be70SMatt Evans 		unsigned	reserved	: 7;		/* 30 .. 24 */
34*aa73be70SMatt Evans 		unsigned	bus_number	: 8;		/* 23 .. 16 */
35*aa73be70SMatt Evans 		unsigned	device_number	: 5;		/* 15 .. 11 */
36*aa73be70SMatt Evans 		unsigned	function_number	: 3;		/* 10 .. 8  */
37*aa73be70SMatt Evans 		unsigned	register_number	: 6;		/* 7  .. 2  */
38*aa73be70SMatt Evans 		unsigned	zeros		: 2;		/* 1  .. 0  */
39*aa73be70SMatt Evans #endif
40*aa73be70SMatt Evans 	};
41*aa73be70SMatt Evans 	u32 w;
424402a581SPekka Enberg };
434402a581SPekka Enberg 
44bc485053SSasha Levin struct msix_table {
451de74957SSasha Levin 	struct msi_msg msg;
46bc485053SSasha Levin 	u32 ctrl;
47bc485053SSasha Levin };
48bc485053SSasha Levin 
49bc485053SSasha Levin struct msix_cap {
50bc485053SSasha Levin 	u8 cap;
51bc485053SSasha Levin 	u8 next;
5206f48103SSasha Levin 	u16 ctrl;
53bc485053SSasha Levin 	u32 table_offset;
5406f48103SSasha Levin 	u32 pba_offset;
55bc485053SSasha Levin };
56bc485053SSasha Levin 
5776f9c841SCyrill Gorcunov struct pci_device_header {
583fdf659dSSasha Levin 	u16		vendor_id;
593fdf659dSSasha Levin 	u16		device_id;
603fdf659dSSasha Levin 	u16		command;
613fdf659dSSasha Levin 	u16		status;
62*aa73be70SMatt Evans 	u8		revision_id;
63*aa73be70SMatt Evans 	u8		class[3];
643fdf659dSSasha Levin 	u8		cacheline_size;
653fdf659dSSasha Levin 	u8		latency_timer;
663fdf659dSSasha Levin 	u8		header_type;
673fdf659dSSasha Levin 	u8		bist;
683fdf659dSSasha Levin 	u32		bar[6];
693fdf659dSSasha Levin 	u32		card_bus;
703fdf659dSSasha Levin 	u16		subsys_vendor_id;
713fdf659dSSasha Levin 	u16		subsys_id;
723fdf659dSSasha Levin 	u32		exp_rom_bar;
73*aa73be70SMatt Evans 	u8		capabilities;
74*aa73be70SMatt Evans 	u8		reserved1[3];
753fdf659dSSasha Levin 	u32		reserved2;
763fdf659dSSasha Levin 	u8		irq_line;
773fdf659dSSasha Levin 	u8		irq_pin;
783fdf659dSSasha Levin 	u8		min_gnt;
793fdf659dSSasha Levin 	u8		max_lat;
80bc485053SSasha Levin 	struct msix_cap msix;
81c64f7ff0SSasha Levin 	u8		empty[136]; /* Rest of PCI config space */
82c64f7ff0SSasha Levin 	u32		bar_size[6];
83*aa73be70SMatt Evans } __attribute__((packed));
8476f9c841SCyrill Gorcunov 
8560742802SPekka Enberg void pci__init(void);
863fdf659dSSasha Levin void pci__register(struct pci_device_header *dev, u8 dev_num);
8795d13a52SSasha Levin u32 pci_get_io_space_block(u32 size);
8860742802SPekka Enberg 
8960742802SPekka Enberg #endif /* KVM__PCI_H */
90