1*4882a593Smuzhiyun.. SPDX-License-Identifier: GPL-2.0 2*4882a593Smuzhiyun 3*4882a593Smuzhiyun:Author: Kishon Vijay Abraham I <kishon@ti.com> 4*4882a593Smuzhiyun 5*4882a593SmuzhiyunThis document is a guide to use the PCI Endpoint Framework in order to create 6*4882a593Smuzhiyunendpoint controller driver, endpoint function driver, and using configfs 7*4882a593Smuzhiyuninterface to bind the function driver to the controller driver. 8*4882a593Smuzhiyun 9*4882a593SmuzhiyunIntroduction 10*4882a593Smuzhiyun============ 11*4882a593Smuzhiyun 12*4882a593SmuzhiyunLinux has a comprehensive PCI subsystem to support PCI controllers that 13*4882a593Smuzhiyunoperates in Root Complex mode. The subsystem has capability to scan PCI bus, 14*4882a593Smuzhiyunassign memory resources and IRQ resources, load PCI driver (based on 15*4882a593Smuzhiyunvendor ID, device ID), support other services like hot-plug, power management, 16*4882a593Smuzhiyunadvanced error reporting and virtual channels. 17*4882a593Smuzhiyun 18*4882a593SmuzhiyunHowever the PCI controller IP integrated in some SoCs is capable of operating 19*4882a593Smuzhiyuneither in Root Complex mode or Endpoint mode. PCI Endpoint Framework will 20*4882a593Smuzhiyunadd endpoint mode support in Linux. This will help to run Linux in an 21*4882a593SmuzhiyunEP system which can have a wide variety of use cases from testing or 22*4882a593Smuzhiyunvalidation, co-processor accelerator, etc. 23*4882a593Smuzhiyun 24*4882a593SmuzhiyunPCI Endpoint Core 25*4882a593Smuzhiyun================= 26*4882a593Smuzhiyun 27*4882a593SmuzhiyunThe PCI Endpoint Core layer comprises 3 components: the Endpoint Controller 28*4882a593Smuzhiyunlibrary, the Endpoint Function library, and the configfs layer to bind the 29*4882a593Smuzhiyunendpoint function with the endpoint controller. 30*4882a593Smuzhiyun 31*4882a593SmuzhiyunPCI Endpoint Controller(EPC) Library 32*4882a593Smuzhiyun------------------------------------ 33*4882a593Smuzhiyun 34*4882a593SmuzhiyunThe EPC library provides APIs to be used by the controller that can operate 35*4882a593Smuzhiyunin endpoint mode. It also provides APIs to be used by function driver/library 36*4882a593Smuzhiyunin order to implement a particular endpoint function. 37*4882a593Smuzhiyun 38*4882a593SmuzhiyunAPIs for the PCI controller Driver 39*4882a593Smuzhiyun~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 40*4882a593Smuzhiyun 41*4882a593SmuzhiyunThis section lists the APIs that the PCI Endpoint core provides to be used 42*4882a593Smuzhiyunby the PCI controller driver. 43*4882a593Smuzhiyun 44*4882a593Smuzhiyun* devm_pci_epc_create()/pci_epc_create() 45*4882a593Smuzhiyun 46*4882a593Smuzhiyun The PCI controller driver should implement the following ops: 47*4882a593Smuzhiyun 48*4882a593Smuzhiyun * write_header: ops to populate configuration space header 49*4882a593Smuzhiyun * set_bar: ops to configure the BAR 50*4882a593Smuzhiyun * clear_bar: ops to reset the BAR 51*4882a593Smuzhiyun * alloc_addr_space: ops to allocate in PCI controller address space 52*4882a593Smuzhiyun * free_addr_space: ops to free the allocated address space 53*4882a593Smuzhiyun * raise_irq: ops to raise a legacy, MSI or MSI-X interrupt 54*4882a593Smuzhiyun * start: ops to start the PCI link 55*4882a593Smuzhiyun * stop: ops to stop the PCI link 56*4882a593Smuzhiyun 57*4882a593Smuzhiyun The PCI controller driver can then create a new EPC device by invoking 58*4882a593Smuzhiyun devm_pci_epc_create()/pci_epc_create(). 59*4882a593Smuzhiyun 60*4882a593Smuzhiyun* devm_pci_epc_destroy()/pci_epc_destroy() 61*4882a593Smuzhiyun 62*4882a593Smuzhiyun The PCI controller driver can destroy the EPC device created by either 63*4882a593Smuzhiyun devm_pci_epc_create() or pci_epc_create() using devm_pci_epc_destroy() or 64*4882a593Smuzhiyun pci_epc_destroy(). 65*4882a593Smuzhiyun 66*4882a593Smuzhiyun* pci_epc_linkup() 67*4882a593Smuzhiyun 68*4882a593Smuzhiyun In order to notify all the function devices that the EPC device to which 69*4882a593Smuzhiyun they are linked has established a link with the host, the PCI controller 70*4882a593Smuzhiyun driver should invoke pci_epc_linkup(). 71*4882a593Smuzhiyun 72*4882a593Smuzhiyun* pci_epc_mem_init() 73*4882a593Smuzhiyun 74*4882a593Smuzhiyun Initialize the pci_epc_mem structure used for allocating EPC addr space. 75*4882a593Smuzhiyun 76*4882a593Smuzhiyun* pci_epc_mem_exit() 77*4882a593Smuzhiyun 78*4882a593Smuzhiyun Cleanup the pci_epc_mem structure allocated during pci_epc_mem_init(). 79*4882a593Smuzhiyun 80*4882a593Smuzhiyun 81*4882a593SmuzhiyunEPC APIs for the PCI Endpoint Function Driver 82*4882a593Smuzhiyun~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 83*4882a593Smuzhiyun 84*4882a593SmuzhiyunThis section lists the APIs that the PCI Endpoint core provides to be used 85*4882a593Smuzhiyunby the PCI endpoint function driver. 86*4882a593Smuzhiyun 87*4882a593Smuzhiyun* pci_epc_write_header() 88*4882a593Smuzhiyun 89*4882a593Smuzhiyun The PCI endpoint function driver should use pci_epc_write_header() to 90*4882a593Smuzhiyun write the standard configuration header to the endpoint controller. 91*4882a593Smuzhiyun 92*4882a593Smuzhiyun* pci_epc_set_bar() 93*4882a593Smuzhiyun 94*4882a593Smuzhiyun The PCI endpoint function driver should use pci_epc_set_bar() to configure 95*4882a593Smuzhiyun the Base Address Register in order for the host to assign PCI addr space. 96*4882a593Smuzhiyun Register space of the function driver is usually configured 97*4882a593Smuzhiyun using this API. 98*4882a593Smuzhiyun 99*4882a593Smuzhiyun* pci_epc_clear_bar() 100*4882a593Smuzhiyun 101*4882a593Smuzhiyun The PCI endpoint function driver should use pci_epc_clear_bar() to reset 102*4882a593Smuzhiyun the BAR. 103*4882a593Smuzhiyun 104*4882a593Smuzhiyun* pci_epc_raise_irq() 105*4882a593Smuzhiyun 106*4882a593Smuzhiyun The PCI endpoint function driver should use pci_epc_raise_irq() to raise 107*4882a593Smuzhiyun Legacy Interrupt, MSI or MSI-X Interrupt. 108*4882a593Smuzhiyun 109*4882a593Smuzhiyun* pci_epc_mem_alloc_addr() 110*4882a593Smuzhiyun 111*4882a593Smuzhiyun The PCI endpoint function driver should use pci_epc_mem_alloc_addr(), to 112*4882a593Smuzhiyun allocate memory address from EPC addr space which is required to access 113*4882a593Smuzhiyun RC's buffer 114*4882a593Smuzhiyun 115*4882a593Smuzhiyun* pci_epc_mem_free_addr() 116*4882a593Smuzhiyun 117*4882a593Smuzhiyun The PCI endpoint function driver should use pci_epc_mem_free_addr() to 118*4882a593Smuzhiyun free the memory space allocated using pci_epc_mem_alloc_addr(). 119*4882a593Smuzhiyun 120*4882a593SmuzhiyunOther EPC APIs 121*4882a593Smuzhiyun~~~~~~~~~~~~~~ 122*4882a593Smuzhiyun 123*4882a593SmuzhiyunThere are other APIs provided by the EPC library. These are used for binding 124*4882a593Smuzhiyunthe EPF device with EPC device. pci-ep-cfs.c can be used as reference for 125*4882a593Smuzhiyunusing these APIs. 126*4882a593Smuzhiyun 127*4882a593Smuzhiyun* pci_epc_get() 128*4882a593Smuzhiyun 129*4882a593Smuzhiyun Get a reference to the PCI endpoint controller based on the device name of 130*4882a593Smuzhiyun the controller. 131*4882a593Smuzhiyun 132*4882a593Smuzhiyun* pci_epc_put() 133*4882a593Smuzhiyun 134*4882a593Smuzhiyun Release the reference to the PCI endpoint controller obtained using 135*4882a593Smuzhiyun pci_epc_get() 136*4882a593Smuzhiyun 137*4882a593Smuzhiyun* pci_epc_add_epf() 138*4882a593Smuzhiyun 139*4882a593Smuzhiyun Add a PCI endpoint function to a PCI endpoint controller. A PCIe device 140*4882a593Smuzhiyun can have up to 8 functions according to the specification. 141*4882a593Smuzhiyun 142*4882a593Smuzhiyun* pci_epc_remove_epf() 143*4882a593Smuzhiyun 144*4882a593Smuzhiyun Remove the PCI endpoint function from PCI endpoint controller. 145*4882a593Smuzhiyun 146*4882a593Smuzhiyun* pci_epc_start() 147*4882a593Smuzhiyun 148*4882a593Smuzhiyun The PCI endpoint function driver should invoke pci_epc_start() once it 149*4882a593Smuzhiyun has configured the endpoint function and wants to start the PCI link. 150*4882a593Smuzhiyun 151*4882a593Smuzhiyun* pci_epc_stop() 152*4882a593Smuzhiyun 153*4882a593Smuzhiyun The PCI endpoint function driver should invoke pci_epc_stop() to stop 154*4882a593Smuzhiyun the PCI LINK. 155*4882a593Smuzhiyun 156*4882a593Smuzhiyun 157*4882a593SmuzhiyunPCI Endpoint Function(EPF) Library 158*4882a593Smuzhiyun---------------------------------- 159*4882a593Smuzhiyun 160*4882a593SmuzhiyunThe EPF library provides APIs to be used by the function driver and the EPC 161*4882a593Smuzhiyunlibrary to provide endpoint mode functionality. 162*4882a593Smuzhiyun 163*4882a593SmuzhiyunEPF APIs for the PCI Endpoint Function Driver 164*4882a593Smuzhiyun~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 165*4882a593Smuzhiyun 166*4882a593SmuzhiyunThis section lists the APIs that the PCI Endpoint core provides to be used 167*4882a593Smuzhiyunby the PCI endpoint function driver. 168*4882a593Smuzhiyun 169*4882a593Smuzhiyun* pci_epf_register_driver() 170*4882a593Smuzhiyun 171*4882a593Smuzhiyun The PCI Endpoint Function driver should implement the following ops: 172*4882a593Smuzhiyun * bind: ops to perform when a EPC device has been bound to EPF device 173*4882a593Smuzhiyun * unbind: ops to perform when a binding has been lost between a EPC 174*4882a593Smuzhiyun device and EPF device 175*4882a593Smuzhiyun * linkup: ops to perform when the EPC device has established a 176*4882a593Smuzhiyun connection with a host system 177*4882a593Smuzhiyun 178*4882a593Smuzhiyun The PCI Function driver can then register the PCI EPF driver by using 179*4882a593Smuzhiyun pci_epf_register_driver(). 180*4882a593Smuzhiyun 181*4882a593Smuzhiyun* pci_epf_unregister_driver() 182*4882a593Smuzhiyun 183*4882a593Smuzhiyun The PCI Function driver can unregister the PCI EPF driver by using 184*4882a593Smuzhiyun pci_epf_unregister_driver(). 185*4882a593Smuzhiyun 186*4882a593Smuzhiyun* pci_epf_alloc_space() 187*4882a593Smuzhiyun 188*4882a593Smuzhiyun The PCI Function driver can allocate space for a particular BAR using 189*4882a593Smuzhiyun pci_epf_alloc_space(). 190*4882a593Smuzhiyun 191*4882a593Smuzhiyun* pci_epf_free_space() 192*4882a593Smuzhiyun 193*4882a593Smuzhiyun The PCI Function driver can free the allocated space 194*4882a593Smuzhiyun (using pci_epf_alloc_space) by invoking pci_epf_free_space(). 195*4882a593Smuzhiyun 196*4882a593SmuzhiyunAPIs for the PCI Endpoint Controller Library 197*4882a593Smuzhiyun~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 198*4882a593Smuzhiyun 199*4882a593SmuzhiyunThis section lists the APIs that the PCI Endpoint core provides to be used 200*4882a593Smuzhiyunby the PCI endpoint controller library. 201*4882a593Smuzhiyun 202*4882a593Smuzhiyun* pci_epf_linkup() 203*4882a593Smuzhiyun 204*4882a593Smuzhiyun The PCI endpoint controller library invokes pci_epf_linkup() when the 205*4882a593Smuzhiyun EPC device has established the connection to the host. 206*4882a593Smuzhiyun 207*4882a593SmuzhiyunOther EPF APIs 208*4882a593Smuzhiyun~~~~~~~~~~~~~~ 209*4882a593Smuzhiyun 210*4882a593SmuzhiyunThere are other APIs provided by the EPF library. These are used to notify 211*4882a593Smuzhiyunthe function driver when the EPF device is bound to the EPC device. 212*4882a593Smuzhiyunpci-ep-cfs.c can be used as reference for using these APIs. 213*4882a593Smuzhiyun 214*4882a593Smuzhiyun* pci_epf_create() 215*4882a593Smuzhiyun 216*4882a593Smuzhiyun Create a new PCI EPF device by passing the name of the PCI EPF device. 217*4882a593Smuzhiyun This name will be used to bind the EPF device to a EPF driver. 218*4882a593Smuzhiyun 219*4882a593Smuzhiyun* pci_epf_destroy() 220*4882a593Smuzhiyun 221*4882a593Smuzhiyun Destroy the created PCI EPF device. 222*4882a593Smuzhiyun 223*4882a593Smuzhiyun* pci_epf_bind() 224*4882a593Smuzhiyun 225*4882a593Smuzhiyun pci_epf_bind() should be invoked when the EPF device has been bound to 226*4882a593Smuzhiyun a EPC device. 227*4882a593Smuzhiyun 228*4882a593Smuzhiyun* pci_epf_unbind() 229*4882a593Smuzhiyun 230*4882a593Smuzhiyun pci_epf_unbind() should be invoked when the binding between EPC device 231*4882a593Smuzhiyun and EPF device is lost. 232