cxl: Export optional AFU configuration record in sysfs

An AFU may optionally contain one or more PCIe like configuration
records, which can be used to identify the AFU.

This patch adds support for exposing the raw config space and the
vendor, device and class code under sysfs. These will appear in a
subdirectory of the AFU device corresponding with the configuration
record number, e.g.

cat /sys/class/cxl/afu0.0/cr0/vendor
0x1014

cat /sys/class/cxl/afu0.0/cr0/device
0x4350

cat /sys/class/cxl/afu0.0/cr0/class
0x120000

hexdump -C /sys/class/cxl/afu0.0/cr0/config
00000000  14 10 50 43 00 00 00 00  06 00 00 12 00 00 00 00  |..PC............|
00000010  00 00 00 00 00 00 00 00  00 00 00 00 00 00 00 00  |................|
*
00000100

These files behave in much the same way as the equivalent files for PCI
devices, with one exception being that the config file is currently
read-only and restricted to the root user. It is not necessarily
required to be this strict, but we currently do not have a compelling
use-case to make it writable and/or world-readable, so I erred on the
side of being restrictive.

Signed-off-by: Ian Munsie <imunsie@au1.ibm.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>
This commit is contained in:
Ian Munsie
2015-02-04 19:09:01 +11:00
committed by Michael Ellerman
parent c2c896bee0
commit b087e6190d
4 changed files with 242 additions and 10 deletions

View File

@@ -382,6 +382,10 @@ struct cxl_afu {
int slice;
int modes_supported;
int current_mode;
int crs_num;
u64 crs_len;
u64 crs_offset;
struct list_head crs;
enum prefault_modes prefault_mode;
bool psa;
bool pp_psa;
@@ -551,6 +555,15 @@ static inline void __iomem *_cxl_p2n_addr(struct cxl_afu *afu, cxl_p2n_reg_t reg
#define cxl_p2n_read(afu, reg) \
in_be64(_cxl_p2n_addr(afu, reg))
#define cxl_afu_cr_read64(afu, cr, off) \
in_le64((afu)->afu_desc_mmio + (afu)->crs_offset + ((cr) * (afu)->crs_len) + (off))
#define cxl_afu_cr_read32(afu, cr, off) \
in_le32((afu)->afu_desc_mmio + (afu)->crs_offset + ((cr) * (afu)->crs_len) + (off))
u16 cxl_afu_cr_read16(struct cxl_afu *afu, int cr, u64 off);
u8 cxl_afu_cr_read8(struct cxl_afu *afu, int cr, u64 off);
struct cxl_calls {
void (*cxl_slbia)(struct mm_struct *mm);
struct module *owner;