/* @(#)src/unix/pagecache/sol/common/kernel/base/vxio.h	3.9 07/19/02 01:51:23 */
/* #ident "@(#)vxfs:src/unix/pagecache/sol/common/kernel/base/vxio.h	3.9" */

/*
 * (c) Copyright 1991-2004 VERITAS Software Corporation. All rights reserved.
 */

#ifndef _VXVM_VXIO_H
#define	_VXVM_VXIO_H

/*
 * vxio.h - public definitions and structures for VERITAS enhanced I/O API.
 */

/*
 * The following ioctl value is shared between fs and vm. As such, both
 * subsystems need to have the same values for this ioctl.
 */
#define VXVIOC		(('V' << 24) | ('X' << 16) | ('I' << 8))

#define	VX_GET_IOPARAMETERS	(VXVIOC | 1)	/* get volume I/O paramters */

#define	VXVI_DEF_IO	(65536 / NBPSCTR)	/* default I/O size */
#define	VXVI_PREF_LOW		10	/* low level for vi_pref_strength */
#define	VXVI_PREF_MEDIUM	20	/* medium level for vi_pref_strength */
#define	VXVI_PREF_HIGH		30	/* high level for vi_pref_strength */

/*
 * I/O sizes desired by the volume manager or file system.  These sizes
 * represent hints to enable applications to issue more efficient I/O
 * requests.
 *
 * For reading, the ideal application will issue groups of vi_read_nstream
 * requests of vi_read_preferred_io bytes.  If the application can't issue
 * streaming I/O requests, then it should try for individual requests that
 * are the product of (vi_read_nstream * vi_read_preferred_io).  If the
 * desired amount of data is too large or too small for the application,
 * as a general rule the next best sizes are multiples or factors of the
 * product of (vi_read_nstream * vi_read_preferred_io).  If no reasonable
 * size can be used based on vi_read_preferred_io, then vi_read_unit_io
 * provides a slightly less desirable size for I/O requests.
 *
 * For writes, apply the same rules used for reads but using the vi_write_*
 * parameters.
 *
 * The vi_pref_strength provides an indication of how hard the application
 * should try to build preferred size I/O requests.  The higher the value
 * of vi_pref_strength the greater the benefit of issuing correct size I/O
 * requests.
 *
 * The vi_breakup_size indicates the size where I/O requests will get broken
 * up into multiple operations at the driver level.  In general, unless the
 * preferred I/O request indicates a value larger than vi_breakup_size then
 * issuing I/O requests larger than vi_breakup_size can hurt performance.
 *
 * In the future, if we support volumes that are build on top of other
 * volumes, the start of the top level volume might not correspond to the
 * geometry of the storage.  The value vi_align_offset should be subtracted
 * from sector offsets when trying to decide if a request is aligned to
 * a preferred boundary.
 *
 * If the VX_GET_IOPARAMETERS ioctl is issued against a character device,
 * then vi_block_device contains the device number of the corresponding
 * block device.  This functions as a sanity check when converting from
 * character devices to block devices.
 */

struct vx_ioparameters {
	unsigned	vi_read_preferred_io;	/* pref read size in bytes */
	unsigned	vi_read_nstream;	/* # of pref reads to stream */
	unsigned	vi_read_unit_io;	/* less pref read size (bytes)*/
	unsigned	vi_write_preferred_io;	/* pref write size in bytes */
	unsigned	vi_write_nstream;	/* # of pref writes to stream */
	unsigned	vi_write_unit_io;	/* less pref write size(bytes)*/
	unsigned	vi_pref_strength;	/* strength of preferences */
	unsigned	vi_breakup_size;	/* I/O breakup size in bytes */
	unsigned	vi_align_offset;	/* adj for alignment calcs */
	dev_t		vi_block_device;	/* bdev number for this cdev */
};

/*
 * VIOC is a platfrom dependent value and hence it is defined in this
 * file. this is used in vxfsvol.h to define various volume manager
 * related ioctl.
 */

#ifndef VIOC
#define VIOC		(('V' << 24) | ('O' << 16) | ('L' << 8))
#endif	/* VIOC */

#endif	/* _VXVM_VXIO_H */
