cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

diag.h (7042B)


      1/* SPDX-License-Identifier: GPL-2.0 */
      2/*
      3 * s390 diagnose functions
      4 *
      5 * Copyright IBM Corp. 2007
      6 * Author(s): Michael Holzheu <holzheu@de.ibm.com>
      7 */
      8
      9#ifndef _ASM_S390_DIAG_H
     10#define _ASM_S390_DIAG_H
     11
     12#include <linux/if_ether.h>
     13#include <linux/percpu.h>
     14#include <asm/asm-extable.h>
     15
     16enum diag_stat_enum {
     17	DIAG_STAT_X008,
     18	DIAG_STAT_X00C,
     19	DIAG_STAT_X010,
     20	DIAG_STAT_X014,
     21	DIAG_STAT_X044,
     22	DIAG_STAT_X064,
     23	DIAG_STAT_X09C,
     24	DIAG_STAT_X0DC,
     25	DIAG_STAT_X204,
     26	DIAG_STAT_X210,
     27	DIAG_STAT_X224,
     28	DIAG_STAT_X250,
     29	DIAG_STAT_X258,
     30	DIAG_STAT_X26C,
     31	DIAG_STAT_X288,
     32	DIAG_STAT_X2C4,
     33	DIAG_STAT_X2FC,
     34	DIAG_STAT_X304,
     35	DIAG_STAT_X308,
     36	DIAG_STAT_X318,
     37	DIAG_STAT_X500,
     38	NR_DIAG_STAT
     39};
     40
     41void diag_stat_inc(enum diag_stat_enum nr);
     42void diag_stat_inc_norecursion(enum diag_stat_enum nr);
     43
     44/*
     45 * Diagnose 10: Release page range
     46 */
     47static inline void diag10_range(unsigned long start_pfn, unsigned long num_pfn)
     48{
     49	unsigned long start_addr, end_addr;
     50
     51	start_addr = pfn_to_phys(start_pfn);
     52	end_addr = pfn_to_phys(start_pfn + num_pfn - 1);
     53
     54	diag_stat_inc(DIAG_STAT_X010);
     55	asm volatile(
     56		"0:	diag	%0,%1,0x10\n"
     57		"1:	nopr	%%r7\n"
     58		EX_TABLE(0b, 1b)
     59		EX_TABLE(1b, 1b)
     60		: : "a" (start_addr), "a" (end_addr));
     61}
     62
     63/*
     64 * Diagnose 14: Input spool file manipulation
     65 */
     66extern int diag14(unsigned long rx, unsigned long ry1, unsigned long subcode);
     67
     68/*
     69 * Diagnose 210: Get information about a virtual device
     70 */
     71struct diag210 {
     72	u16 vrdcdvno;	/* device number (input) */
     73	u16 vrdclen;	/* data block length (input) */
     74	u8 vrdcvcla;	/* virtual device class (output) */
     75	u8 vrdcvtyp;	/* virtual device type (output) */
     76	u8 vrdcvsta;	/* virtual device status (output) */
     77	u8 vrdcvfla;	/* virtual device flags (output) */
     78	u8 vrdcrccl;	/* real device class (output) */
     79	u8 vrdccrty;	/* real device type (output) */
     80	u8 vrdccrmd;	/* real device model (output) */
     81	u8 vrdccrft;	/* real device feature (output) */
     82} __attribute__((packed, aligned(4)));
     83
     84extern int diag210(struct diag210 *addr);
     85
     86/* bit is set in flags, when physical cpu info is included in diag 204 data */
     87#define DIAG204_LPAR_PHYS_FLG 0x80
     88#define DIAG204_LPAR_NAME_LEN 8		/* lpar name len in diag 204 data */
     89#define DIAG204_CPU_NAME_LEN 16		/* type name len of cpus in diag224 name table */
     90
     91/* diag 204 subcodes */
     92enum diag204_sc {
     93	DIAG204_SUBC_STIB4 = 4,
     94	DIAG204_SUBC_RSI = 5,
     95	DIAG204_SUBC_STIB6 = 6,
     96	DIAG204_SUBC_STIB7 = 7
     97};
     98
     99/* The two available diag 204 data formats */
    100enum diag204_format {
    101	DIAG204_INFO_SIMPLE = 0,
    102	DIAG204_INFO_EXT = 0x00010000
    103};
    104
    105enum diag204_cpu_flags {
    106	DIAG204_CPU_ONLINE = 0x20,
    107	DIAG204_CPU_CAPPED = 0x40,
    108};
    109
    110struct diag204_info_blk_hdr {
    111	__u8  npar;
    112	__u8  flags;
    113	__u16 tslice;
    114	__u16 phys_cpus;
    115	__u16 this_part;
    116	__u64 curtod;
    117} __packed;
    118
    119struct diag204_x_info_blk_hdr {
    120	__u8  npar;
    121	__u8  flags;
    122	__u16 tslice;
    123	__u16 phys_cpus;
    124	__u16 this_part;
    125	__u64 curtod1;
    126	__u64 curtod2;
    127	char reserved[40];
    128} __packed;
    129
    130struct diag204_part_hdr {
    131	__u8 pn;
    132	__u8 cpus;
    133	char reserved[6];
    134	char part_name[DIAG204_LPAR_NAME_LEN];
    135} __packed;
    136
    137struct diag204_x_part_hdr {
    138	__u8  pn;
    139	__u8  cpus;
    140	__u8  rcpus;
    141	__u8  pflag;
    142	__u32 mlu;
    143	char  part_name[DIAG204_LPAR_NAME_LEN];
    144	char  lpc_name[8];
    145	char  os_name[8];
    146	__u64 online_cs;
    147	__u64 online_es;
    148	__u8  upid;
    149	__u8  reserved:3;
    150	__u8  mtid:5;
    151	char  reserved1[2];
    152	__u32 group_mlu;
    153	char  group_name[8];
    154	char  hardware_group_name[8];
    155	char  reserved2[24];
    156} __packed;
    157
    158struct diag204_cpu_info {
    159	__u16 cpu_addr;
    160	char  reserved1[2];
    161	__u8  ctidx;
    162	__u8  cflag;
    163	__u16 weight;
    164	__u64 acc_time;
    165	__u64 lp_time;
    166} __packed;
    167
    168struct diag204_x_cpu_info {
    169	__u16 cpu_addr;
    170	char  reserved1[2];
    171	__u8  ctidx;
    172	__u8  cflag;
    173	__u16 weight;
    174	__u64 acc_time;
    175	__u64 lp_time;
    176	__u16 min_weight;
    177	__u16 cur_weight;
    178	__u16 max_weight;
    179	char  reseved2[2];
    180	__u64 online_time;
    181	__u64 wait_time;
    182	__u32 pma_weight;
    183	__u32 polar_weight;
    184	__u32 cpu_type_cap;
    185	__u32 group_cpu_type_cap;
    186	char  reserved3[32];
    187} __packed;
    188
    189struct diag204_phys_hdr {
    190	char reserved1[1];
    191	__u8 cpus;
    192	char reserved2[6];
    193	char mgm_name[8];
    194} __packed;
    195
    196struct diag204_x_phys_hdr {
    197	char reserved1[1];
    198	__u8 cpus;
    199	char reserved2[6];
    200	char mgm_name[8];
    201	char reserved3[80];
    202} __packed;
    203
    204struct diag204_phys_cpu {
    205	__u16 cpu_addr;
    206	char  reserved1[2];
    207	__u8  ctidx;
    208	char  reserved2[3];
    209	__u64 mgm_time;
    210	char  reserved3[8];
    211} __packed;
    212
    213struct diag204_x_phys_cpu {
    214	__u16 cpu_addr;
    215	char  reserved1[2];
    216	__u8  ctidx;
    217	char  reserved2[1];
    218	__u16 weight;
    219	__u64 mgm_time;
    220	char  reserved3[80];
    221} __packed;
    222
    223struct diag204_x_part_block {
    224	struct diag204_x_part_hdr hdr;
    225	struct diag204_x_cpu_info cpus[];
    226} __packed;
    227
    228struct diag204_x_phys_block {
    229	struct diag204_x_phys_hdr hdr;
    230	struct diag204_x_phys_cpu cpus[];
    231} __packed;
    232
    233enum diag26c_sc {
    234	DIAG26C_PORT_VNIC    = 0x00000024,
    235	DIAG26C_MAC_SERVICES = 0x00000030
    236};
    237
    238enum diag26c_version {
    239	DIAG26C_VERSION2	 = 0x00000002,	/* z/VM 5.4.0 */
    240	DIAG26C_VERSION6_VM65918 = 0x00020006	/* z/VM 6.4.0 + VM65918 */
    241};
    242
    243#define DIAG26C_VNIC_INFO	0x0002
    244struct diag26c_vnic_req {
    245	u32	resp_buf_len;
    246	u32	resp_version;
    247	u16	req_format;
    248	u16	vlan_id;
    249	u64	sys_name;
    250	u8	res[2];
    251	u16	devno;
    252} __packed __aligned(8);
    253
    254#define VNIC_INFO_PROT_L3	1
    255#define VNIC_INFO_PROT_L2	2
    256/* Note: this is the bare minimum, use it for uninitialized VNICs only. */
    257struct diag26c_vnic_resp {
    258	u32	version;
    259	u32	entry_cnt;
    260	/* VNIC info: */
    261	u32	next_entry;
    262	u64	owner;
    263	u16	devno;
    264	u8	status;
    265	u8	type;
    266	u64	lan_owner;
    267	u64	lan_name;
    268	u64	port_name;
    269	u8	port_type;
    270	u8	ext_status:6;
    271	u8	protocol:2;
    272	u16	base_devno;
    273	u32	port_num;
    274	u32	ifindex;
    275	u32	maxinfo;
    276	u32	dev_count;
    277	/* 3x device info: */
    278	u8	dev_info1[28];
    279	u8	dev_info2[28];
    280	u8	dev_info3[28];
    281} __packed __aligned(8);
    282
    283#define DIAG26C_GET_MAC	0x0000
    284struct diag26c_mac_req {
    285	u32	resp_buf_len;
    286	u32	resp_version;
    287	u16	op_code;
    288	u16	devno;
    289	u8	res[4];
    290};
    291
    292struct diag26c_mac_resp {
    293	u32	version;
    294	u8	mac[ETH_ALEN];
    295	u8	res[2];
    296} __aligned(8);
    297
    298#define CPNC_LINUX		0x4
    299union diag318_info {
    300	unsigned long val;
    301	struct {
    302		unsigned long cpnc : 8;
    303		unsigned long cpvc : 56;
    304	};
    305};
    306
    307int diag204(unsigned long subcode, unsigned long size, void *addr);
    308int diag224(void *ptr);
    309int diag26c(void *req, void *resp, enum diag26c_sc subcode);
    310
    311struct hypfs_diag0c_entry;
    312
    313/*
    314 * This structure must contain only pointers/references into
    315 * the AMODE31 text section.
    316 */
    317struct diag_ops {
    318	int (*diag210)(struct diag210 *addr);
    319	int (*diag26c)(void *req, void *resp, enum diag26c_sc subcode);
    320	int (*diag14)(unsigned long rx, unsigned long ry1, unsigned long subcode);
    321	void (*diag0c)(struct hypfs_diag0c_entry *entry);
    322	void (*diag308_reset)(void);
    323};
    324
    325extern struct diag_ops diag_amode31_ops;
    326extern struct diag210 *__diag210_tmp_amode31;
    327
    328int _diag210_amode31(struct diag210 *addr);
    329int _diag26c_amode31(void *req, void *resp, enum diag26c_sc subcode);
    330int _diag14_amode31(unsigned long rx, unsigned long ry1, unsigned long subcode);
    331void _diag0c_amode31(struct hypfs_diag0c_entry *entry);
    332void _diag308_reset_amode31(void);
    333
    334#endif /* _ASM_S390_DIAG_H */