xref: /kernel/linux/linux-5.10/drivers/s390/cio/cio.h (revision 8c2ecf20)
18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0 */
28c2ecf20Sopenharmony_ci#ifndef S390_CIO_H
38c2ecf20Sopenharmony_ci#define S390_CIO_H
48c2ecf20Sopenharmony_ci
58c2ecf20Sopenharmony_ci#include <linux/mutex.h>
68c2ecf20Sopenharmony_ci#include <linux/device.h>
78c2ecf20Sopenharmony_ci#include <linux/mod_devicetable.h>
88c2ecf20Sopenharmony_ci#include <asm/chpid.h>
98c2ecf20Sopenharmony_ci#include <asm/cio.h>
108c2ecf20Sopenharmony_ci#include <asm/fcx.h>
118c2ecf20Sopenharmony_ci#include <asm/schid.h>
128c2ecf20Sopenharmony_ci#include "chsc.h"
138c2ecf20Sopenharmony_ci
148c2ecf20Sopenharmony_ci/*
158c2ecf20Sopenharmony_ci * path management control word
168c2ecf20Sopenharmony_ci */
178c2ecf20Sopenharmony_cistruct pmcw {
188c2ecf20Sopenharmony_ci	u32 intparm;		/* interruption parameter */
198c2ecf20Sopenharmony_ci	u32 qf	 : 1;		/* qdio facility */
208c2ecf20Sopenharmony_ci	u32 w	 : 1;
218c2ecf20Sopenharmony_ci	u32 isc  : 3;		/* interruption sublass */
228c2ecf20Sopenharmony_ci	u32 res5 : 3;		/* reserved zeros */
238c2ecf20Sopenharmony_ci	u32 ena  : 1;		/* enabled */
248c2ecf20Sopenharmony_ci	u32 lm	 : 2;		/* limit mode */
258c2ecf20Sopenharmony_ci	u32 mme  : 2;		/* measurement-mode enable */
268c2ecf20Sopenharmony_ci	u32 mp	 : 1;		/* multipath mode */
278c2ecf20Sopenharmony_ci	u32 tf	 : 1;		/* timing facility */
288c2ecf20Sopenharmony_ci	u32 dnv  : 1;		/* device number valid */
298c2ecf20Sopenharmony_ci	u32 dev  : 16;		/* device number */
308c2ecf20Sopenharmony_ci	u8  lpm;		/* logical path mask */
318c2ecf20Sopenharmony_ci	u8  pnom;		/* path not operational mask */
328c2ecf20Sopenharmony_ci	u8  lpum;		/* last path used mask */
338c2ecf20Sopenharmony_ci	u8  pim;		/* path installed mask */
348c2ecf20Sopenharmony_ci	u16 mbi;		/* measurement-block index */
358c2ecf20Sopenharmony_ci	u8  pom;		/* path operational mask */
368c2ecf20Sopenharmony_ci	u8  pam;		/* path available mask */
378c2ecf20Sopenharmony_ci	u8  chpid[8];		/* CHPID 0-7 (if available) */
388c2ecf20Sopenharmony_ci	u32 unused1 : 8;	/* reserved zeros */
398c2ecf20Sopenharmony_ci	u32 st	    : 3;	/* subchannel type */
408c2ecf20Sopenharmony_ci	u32 unused2 : 18;	/* reserved zeros */
418c2ecf20Sopenharmony_ci	u32 mbfc    : 1;	/* measurement block format control */
428c2ecf20Sopenharmony_ci	u32 xmwme   : 1;	/* extended measurement word mode enable */
438c2ecf20Sopenharmony_ci	u32 csense  : 1;	/* concurrent sense; can be enabled ...*/
448c2ecf20Sopenharmony_ci				/*  ... per MSCH, however, if facility */
458c2ecf20Sopenharmony_ci				/*  ... is not installed, this results */
468c2ecf20Sopenharmony_ci				/*  ... in an operand exception.       */
478c2ecf20Sopenharmony_ci} __attribute__ ((packed));
488c2ecf20Sopenharmony_ci
498c2ecf20Sopenharmony_ci/* I/O-Interruption Code as stored by TEST PENDING INTERRUPTION (TPI). */
508c2ecf20Sopenharmony_cistruct tpi_info {
518c2ecf20Sopenharmony_ci	struct subchannel_id schid;
528c2ecf20Sopenharmony_ci	u32 intparm;
538c2ecf20Sopenharmony_ci	u32 adapter_IO:1;
548c2ecf20Sopenharmony_ci	u32 directed_irq:1;
558c2ecf20Sopenharmony_ci	u32 isc:3;
568c2ecf20Sopenharmony_ci	u32 :27;
578c2ecf20Sopenharmony_ci	u32 type:3;
588c2ecf20Sopenharmony_ci	u32 :12;
598c2ecf20Sopenharmony_ci} __packed __aligned(4);
608c2ecf20Sopenharmony_ci
618c2ecf20Sopenharmony_ci/* Target SCHIB configuration. */
628c2ecf20Sopenharmony_cistruct schib_config {
638c2ecf20Sopenharmony_ci	u64 mba;
648c2ecf20Sopenharmony_ci	u32 intparm;
658c2ecf20Sopenharmony_ci	u16 mbi;
668c2ecf20Sopenharmony_ci	u32 isc:3;
678c2ecf20Sopenharmony_ci	u32 ena:1;
688c2ecf20Sopenharmony_ci	u32 mme:2;
698c2ecf20Sopenharmony_ci	u32 mp:1;
708c2ecf20Sopenharmony_ci	u32 csense:1;
718c2ecf20Sopenharmony_ci	u32 mbfc:1;
728c2ecf20Sopenharmony_ci} __attribute__ ((packed));
738c2ecf20Sopenharmony_ci
748c2ecf20Sopenharmony_ci/*
758c2ecf20Sopenharmony_ci * subchannel information block
768c2ecf20Sopenharmony_ci */
778c2ecf20Sopenharmony_cistruct schib {
788c2ecf20Sopenharmony_ci	struct pmcw pmcw;	 /* path management control word */
798c2ecf20Sopenharmony_ci	union scsw scsw;	 /* subchannel status word */
808c2ecf20Sopenharmony_ci	__u64 mba;               /* measurement block address */
818c2ecf20Sopenharmony_ci	__u8 mda[4];		 /* model dependent area */
828c2ecf20Sopenharmony_ci} __attribute__ ((packed,aligned(4)));
838c2ecf20Sopenharmony_ci
848c2ecf20Sopenharmony_ci/*
858c2ecf20Sopenharmony_ci * When rescheduled, todo's with higher values will overwrite those
868c2ecf20Sopenharmony_ci * with lower values.
878c2ecf20Sopenharmony_ci */
888c2ecf20Sopenharmony_cienum sch_todo {
898c2ecf20Sopenharmony_ci	SCH_TODO_NOTHING,
908c2ecf20Sopenharmony_ci	SCH_TODO_EVAL,
918c2ecf20Sopenharmony_ci	SCH_TODO_UNREG,
928c2ecf20Sopenharmony_ci};
938c2ecf20Sopenharmony_ci
948c2ecf20Sopenharmony_ci/* subchannel data structure used by I/O subroutines */
958c2ecf20Sopenharmony_cistruct subchannel {
968c2ecf20Sopenharmony_ci	struct subchannel_id schid;
978c2ecf20Sopenharmony_ci	spinlock_t *lock;	/* subchannel lock */
988c2ecf20Sopenharmony_ci	struct mutex reg_mutex;
998c2ecf20Sopenharmony_ci	enum {
1008c2ecf20Sopenharmony_ci		SUBCHANNEL_TYPE_IO = 0,
1018c2ecf20Sopenharmony_ci		SUBCHANNEL_TYPE_CHSC = 1,
1028c2ecf20Sopenharmony_ci		SUBCHANNEL_TYPE_MSG = 2,
1038c2ecf20Sopenharmony_ci		SUBCHANNEL_TYPE_ADM = 3,
1048c2ecf20Sopenharmony_ci	} st;			/* subchannel type */
1058c2ecf20Sopenharmony_ci	__u8 vpm;		/* verified path mask */
1068c2ecf20Sopenharmony_ci	__u8 lpm;		/* logical path mask */
1078c2ecf20Sopenharmony_ci	__u8 opm;               /* operational path mask */
1088c2ecf20Sopenharmony_ci	struct schib schib;	/* subchannel information block */
1098c2ecf20Sopenharmony_ci	int isc; /* desired interruption subclass */
1108c2ecf20Sopenharmony_ci	struct chsc_ssd_info ssd_info;	/* subchannel description */
1118c2ecf20Sopenharmony_ci	struct device dev;	/* entry in device tree */
1128c2ecf20Sopenharmony_ci	struct css_driver *driver;
1138c2ecf20Sopenharmony_ci	enum sch_todo todo;
1148c2ecf20Sopenharmony_ci	struct work_struct todo_work;
1158c2ecf20Sopenharmony_ci	struct schib_config config;
1168c2ecf20Sopenharmony_ci	u64 dma_mask;
1178c2ecf20Sopenharmony_ci	char *driver_override; /* Driver name to force a match */
1188c2ecf20Sopenharmony_ci} __attribute__ ((aligned(8)));
1198c2ecf20Sopenharmony_ci
1208c2ecf20Sopenharmony_ciDECLARE_PER_CPU_ALIGNED(struct irb, cio_irb);
1218c2ecf20Sopenharmony_ci
1228c2ecf20Sopenharmony_ci#define to_subchannel(n) container_of(n, struct subchannel, dev)
1238c2ecf20Sopenharmony_ci
1248c2ecf20Sopenharmony_ciextern int cio_enable_subchannel(struct subchannel *, u32);
1258c2ecf20Sopenharmony_ciextern int cio_disable_subchannel (struct subchannel *);
1268c2ecf20Sopenharmony_ciextern int cio_cancel (struct subchannel *);
1278c2ecf20Sopenharmony_ciextern int cio_clear (struct subchannel *);
1288c2ecf20Sopenharmony_ciextern int cio_cancel_halt_clear(struct subchannel *, int *);
1298c2ecf20Sopenharmony_ciextern int cio_resume (struct subchannel *);
1308c2ecf20Sopenharmony_ciextern int cio_halt (struct subchannel *);
1318c2ecf20Sopenharmony_ciextern int cio_start (struct subchannel *, struct ccw1 *, __u8);
1328c2ecf20Sopenharmony_ciextern int cio_start_key (struct subchannel *, struct ccw1 *, __u8, __u8);
1338c2ecf20Sopenharmony_ciextern int cio_set_options (struct subchannel *, int);
1348c2ecf20Sopenharmony_ciextern int cio_update_schib(struct subchannel *sch);
1358c2ecf20Sopenharmony_ciextern int cio_commit_config(struct subchannel *sch);
1368c2ecf20Sopenharmony_ci
1378c2ecf20Sopenharmony_ciint cio_tm_start_key(struct subchannel *sch, struct tcw *tcw, u8 lpm, u8 key);
1388c2ecf20Sopenharmony_ciint cio_tm_intrg(struct subchannel *sch);
1398c2ecf20Sopenharmony_ci
1408c2ecf20Sopenharmony_ciextern int __init airq_init(void);
1418c2ecf20Sopenharmony_ci
1428c2ecf20Sopenharmony_ci/* Use with care. */
1438c2ecf20Sopenharmony_ci#ifdef CONFIG_CCW_CONSOLE
1448c2ecf20Sopenharmony_ciextern struct subchannel *cio_probe_console(void);
1458c2ecf20Sopenharmony_ciextern int cio_is_console(struct subchannel_id);
1468c2ecf20Sopenharmony_ciextern void cio_register_early_subchannels(void);
1478c2ecf20Sopenharmony_ciextern void cio_tsch(struct subchannel *sch);
1488c2ecf20Sopenharmony_ci#else
1498c2ecf20Sopenharmony_ci#define cio_is_console(schid) 0
1508c2ecf20Sopenharmony_cistatic inline void cio_register_early_subchannels(void) {}
1518c2ecf20Sopenharmony_ci#endif
1528c2ecf20Sopenharmony_ci
1538c2ecf20Sopenharmony_ci#endif
154