18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0 */
28c2ecf20Sopenharmony_ci#ifndef S390_DEVICE_H
38c2ecf20Sopenharmony_ci#define S390_DEVICE_H
48c2ecf20Sopenharmony_ci
58c2ecf20Sopenharmony_ci#include <asm/ccwdev.h>
68c2ecf20Sopenharmony_ci#include <linux/atomic.h>
78c2ecf20Sopenharmony_ci#include <linux/timer.h>
88c2ecf20Sopenharmony_ci#include <linux/wait.h>
98c2ecf20Sopenharmony_ci#include <linux/notifier.h>
108c2ecf20Sopenharmony_ci#include <linux/kernel_stat.h>
118c2ecf20Sopenharmony_ci#include "io_sch.h"
128c2ecf20Sopenharmony_ci
138c2ecf20Sopenharmony_ci/*
148c2ecf20Sopenharmony_ci * states of the device statemachine
158c2ecf20Sopenharmony_ci */
168c2ecf20Sopenharmony_cienum dev_state {
178c2ecf20Sopenharmony_ci	DEV_STATE_NOT_OPER,
188c2ecf20Sopenharmony_ci	DEV_STATE_SENSE_ID,
198c2ecf20Sopenharmony_ci	DEV_STATE_OFFLINE,
208c2ecf20Sopenharmony_ci	DEV_STATE_VERIFY,
218c2ecf20Sopenharmony_ci	DEV_STATE_ONLINE,
228c2ecf20Sopenharmony_ci	DEV_STATE_W4SENSE,
238c2ecf20Sopenharmony_ci	DEV_STATE_DISBAND_PGID,
248c2ecf20Sopenharmony_ci	DEV_STATE_BOXED,
258c2ecf20Sopenharmony_ci	/* states to wait for i/o completion before doing something */
268c2ecf20Sopenharmony_ci	DEV_STATE_TIMEOUT_KILL,
278c2ecf20Sopenharmony_ci	DEV_STATE_QUIESCE,
288c2ecf20Sopenharmony_ci	/* special states for devices gone not operational */
298c2ecf20Sopenharmony_ci	DEV_STATE_DISCONNECTED,
308c2ecf20Sopenharmony_ci	DEV_STATE_DISCONNECTED_SENSE_ID,
318c2ecf20Sopenharmony_ci	DEV_STATE_CMFCHANGE,
328c2ecf20Sopenharmony_ci	DEV_STATE_CMFUPDATE,
338c2ecf20Sopenharmony_ci	DEV_STATE_STEAL_LOCK,
348c2ecf20Sopenharmony_ci	/* last element! */
358c2ecf20Sopenharmony_ci	NR_DEV_STATES
368c2ecf20Sopenharmony_ci};
378c2ecf20Sopenharmony_ci
388c2ecf20Sopenharmony_ci/*
398c2ecf20Sopenharmony_ci * asynchronous events of the device statemachine
408c2ecf20Sopenharmony_ci */
418c2ecf20Sopenharmony_cienum dev_event {
428c2ecf20Sopenharmony_ci	DEV_EVENT_NOTOPER,
438c2ecf20Sopenharmony_ci	DEV_EVENT_INTERRUPT,
448c2ecf20Sopenharmony_ci	DEV_EVENT_TIMEOUT,
458c2ecf20Sopenharmony_ci	DEV_EVENT_VERIFY,
468c2ecf20Sopenharmony_ci	/* last element! */
478c2ecf20Sopenharmony_ci	NR_DEV_EVENTS
488c2ecf20Sopenharmony_ci};
498c2ecf20Sopenharmony_ci
508c2ecf20Sopenharmony_cistruct ccw_device;
518c2ecf20Sopenharmony_ci
528c2ecf20Sopenharmony_ci/*
538c2ecf20Sopenharmony_ci * action called through jumptable
548c2ecf20Sopenharmony_ci */
558c2ecf20Sopenharmony_citypedef void (fsm_func_t)(struct ccw_device *, enum dev_event);
568c2ecf20Sopenharmony_ciextern fsm_func_t *dev_jumptable[NR_DEV_STATES][NR_DEV_EVENTS];
578c2ecf20Sopenharmony_ci
588c2ecf20Sopenharmony_cistatic inline void
598c2ecf20Sopenharmony_cidev_fsm_event(struct ccw_device *cdev, enum dev_event dev_event)
608c2ecf20Sopenharmony_ci{
618c2ecf20Sopenharmony_ci	int state = cdev->private->state;
628c2ecf20Sopenharmony_ci
638c2ecf20Sopenharmony_ci	if (dev_event == DEV_EVENT_INTERRUPT) {
648c2ecf20Sopenharmony_ci		if (state == DEV_STATE_ONLINE)
658c2ecf20Sopenharmony_ci			inc_irq_stat(cdev->private->int_class);
668c2ecf20Sopenharmony_ci		else if (state != DEV_STATE_CMFCHANGE &&
678c2ecf20Sopenharmony_ci			 state != DEV_STATE_CMFUPDATE)
688c2ecf20Sopenharmony_ci			inc_irq_stat(IRQIO_CIO);
698c2ecf20Sopenharmony_ci	}
708c2ecf20Sopenharmony_ci	dev_jumptable[state][dev_event](cdev, dev_event);
718c2ecf20Sopenharmony_ci}
728c2ecf20Sopenharmony_ci
738c2ecf20Sopenharmony_ci/*
748c2ecf20Sopenharmony_ci * Delivers 1 if the device state is final.
758c2ecf20Sopenharmony_ci */
768c2ecf20Sopenharmony_cistatic inline int
778c2ecf20Sopenharmony_cidev_fsm_final_state(struct ccw_device *cdev)
788c2ecf20Sopenharmony_ci{
798c2ecf20Sopenharmony_ci	return (cdev->private->state == DEV_STATE_NOT_OPER ||
808c2ecf20Sopenharmony_ci		cdev->private->state == DEV_STATE_OFFLINE ||
818c2ecf20Sopenharmony_ci		cdev->private->state == DEV_STATE_ONLINE ||
828c2ecf20Sopenharmony_ci		cdev->private->state == DEV_STATE_BOXED);
838c2ecf20Sopenharmony_ci}
848c2ecf20Sopenharmony_ci
858c2ecf20Sopenharmony_ciint __init io_subchannel_init(void);
868c2ecf20Sopenharmony_ci
878c2ecf20Sopenharmony_civoid io_subchannel_recog_done(struct ccw_device *cdev);
888c2ecf20Sopenharmony_civoid io_subchannel_init_config(struct subchannel *sch);
898c2ecf20Sopenharmony_ci
908c2ecf20Sopenharmony_ciint ccw_device_cancel_halt_clear(struct ccw_device *);
918c2ecf20Sopenharmony_ci
928c2ecf20Sopenharmony_ciint ccw_device_is_orphan(struct ccw_device *);
938c2ecf20Sopenharmony_ci
948c2ecf20Sopenharmony_civoid ccw_device_recognition(struct ccw_device *);
958c2ecf20Sopenharmony_ciint ccw_device_online(struct ccw_device *);
968c2ecf20Sopenharmony_ciint ccw_device_offline(struct ccw_device *);
978c2ecf20Sopenharmony_civoid ccw_device_update_sense_data(struct ccw_device *);
988c2ecf20Sopenharmony_ciint ccw_device_test_sense_data(struct ccw_device *);
998c2ecf20Sopenharmony_ciint ccw_purge_blacklisted(void);
1008c2ecf20Sopenharmony_civoid ccw_device_sched_todo(struct ccw_device *cdev, enum cdev_todo todo);
1018c2ecf20Sopenharmony_cistruct ccw_device *get_ccwdev_by_dev_id(struct ccw_dev_id *dev_id);
1028c2ecf20Sopenharmony_ci
1038c2ecf20Sopenharmony_ci/* Function prototypes for device status and basic sense stuff. */
1048c2ecf20Sopenharmony_civoid ccw_device_accumulate_irb(struct ccw_device *, struct irb *);
1058c2ecf20Sopenharmony_civoid ccw_device_accumulate_basic_sense(struct ccw_device *, struct irb *);
1068c2ecf20Sopenharmony_ciint ccw_device_accumulate_and_sense(struct ccw_device *, struct irb *);
1078c2ecf20Sopenharmony_ciint ccw_device_do_sense(struct ccw_device *, struct irb *);
1088c2ecf20Sopenharmony_ci
1098c2ecf20Sopenharmony_ci/* Function prototype for internal request handling. */
1108c2ecf20Sopenharmony_ciint lpm_adjust(int lpm, int mask);
1118c2ecf20Sopenharmony_civoid ccw_request_start(struct ccw_device *);
1128c2ecf20Sopenharmony_ciint ccw_request_cancel(struct ccw_device *cdev);
1138c2ecf20Sopenharmony_civoid ccw_request_handler(struct ccw_device *cdev);
1148c2ecf20Sopenharmony_civoid ccw_request_timeout(struct ccw_device *cdev);
1158c2ecf20Sopenharmony_civoid ccw_request_notoper(struct ccw_device *cdev);
1168c2ecf20Sopenharmony_ci
1178c2ecf20Sopenharmony_ci/* Function prototypes for sense id stuff. */
1188c2ecf20Sopenharmony_civoid ccw_device_sense_id_start(struct ccw_device *);
1198c2ecf20Sopenharmony_civoid ccw_device_sense_id_done(struct ccw_device *, int);
1208c2ecf20Sopenharmony_ci
1218c2ecf20Sopenharmony_ci/* Function prototypes for path grouping stuff. */
1228c2ecf20Sopenharmony_civoid ccw_device_verify_start(struct ccw_device *);
1238c2ecf20Sopenharmony_civoid ccw_device_verify_done(struct ccw_device *, int);
1248c2ecf20Sopenharmony_ci
1258c2ecf20Sopenharmony_civoid ccw_device_disband_start(struct ccw_device *);
1268c2ecf20Sopenharmony_civoid ccw_device_disband_done(struct ccw_device *, int);
1278c2ecf20Sopenharmony_ci
1288c2ecf20Sopenharmony_ciint ccw_device_stlck(struct ccw_device *);
1298c2ecf20Sopenharmony_ci
1308c2ecf20Sopenharmony_ci/* Helper function for machine check handling. */
1318c2ecf20Sopenharmony_civoid ccw_device_trigger_reprobe(struct ccw_device *);
1328c2ecf20Sopenharmony_civoid ccw_device_kill_io(struct ccw_device *);
1338c2ecf20Sopenharmony_ciint ccw_device_notify(struct ccw_device *, int);
1348c2ecf20Sopenharmony_civoid ccw_device_set_disconnected(struct ccw_device *cdev);
1358c2ecf20Sopenharmony_civoid ccw_device_set_notoper(struct ccw_device *cdev);
1368c2ecf20Sopenharmony_ci
1378c2ecf20Sopenharmony_civoid ccw_device_timeout(struct timer_list *t);
1388c2ecf20Sopenharmony_civoid ccw_device_set_timeout(struct ccw_device *, int);
1398c2ecf20Sopenharmony_civoid ccw_device_schedule_recovery(void);
1408c2ecf20Sopenharmony_ci
1418c2ecf20Sopenharmony_ci/* Channel measurement facility related */
1428c2ecf20Sopenharmony_civoid retry_set_schib(struct ccw_device *cdev);
1438c2ecf20Sopenharmony_civoid cmf_retry_copy_block(struct ccw_device *);
1448c2ecf20Sopenharmony_ciint cmf_reenable(struct ccw_device *);
1458c2ecf20Sopenharmony_civoid cmf_reactivate(void);
1468c2ecf20Sopenharmony_ciint ccw_set_cmf(struct ccw_device *cdev, int enable);
1478c2ecf20Sopenharmony_ciextern struct device_attribute dev_attr_cmb_enable;
1488c2ecf20Sopenharmony_ci#endif
149