diff options
author | Michael Brown <mcb30@ipxe.org> | 2017-03-04 18:43:07 +0000 |
---|---|---|
committer | Michael Brown <mcb30@ipxe.org> | 2017-03-07 13:40:35 +0000 |
commit | 4adc7b029013bf93c0e5f79eddb9231ba2b50292 (patch) | |
tree | 2290eacb2fa965e4b8d1b2aa1857c8be998461fb /src/include/ipxe/sanboot.h | |
parent | 530ec8301180de6c094e6f99369450d9a70b91af (diff) | |
download | ipxe-4adc7b029013bf93c0e5f79eddb9231ba2b50292.tar.gz |
[block] Centralise SAN device abstraction
Create a central SAN device abstraction to be shared between BIOS and
UEFI.
Signed-off-by: Michael Brown <mcb30@ipxe.org>
Diffstat (limited to 'src/include/ipxe/sanboot.h')
-rw-r--r-- | src/include/ipxe/sanboot.h | 124 |
1 files changed, 123 insertions, 1 deletions
diff --git a/src/include/ipxe/sanboot.h b/src/include/ipxe/sanboot.h index 1c68a58ca..420d4dbed 100644 --- a/src/include/ipxe/sanboot.h +++ b/src/include/ipxe/sanboot.h @@ -12,9 +12,52 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL ); #include <ipxe/api.h> +#include <ipxe/refcnt.h> +#include <ipxe/list.h> +#include <ipxe/uri.h> +#include <ipxe/retry.h> +#include <ipxe/blockdev.h> #include <config/sanboot.h> -struct uri; +/** A SAN device */ +struct san_device { + /** Reference count */ + struct refcnt refcnt; + /** List of SAN devices */ + struct list_head list; + + /** SAN device URI */ + struct uri *uri; + /** Drive number */ + unsigned int drive; + + /** Underlying block device interface */ + struct interface block; + /** Current device status */ + int block_rc; + + /** Command interface */ + struct interface command; + /** Command timeout timer */ + struct retry_timer timer; + /** Command status */ + int command_rc; + + /** Raw block device capacity */ + struct block_device_capacity capacity; + /** Block size shift + * + * To allow for emulation of CD-ROM access, this represents + * the left-shift required to translate from exposed logical + * I/O blocks to underlying blocks. + */ + unsigned int blksize_shift; + /** Drive is a CD-ROM */ + int is_cdrom; + + /** Driver private data */ + void *priv; +}; /** * Calculate static inline sanboot API function name @@ -91,4 +134,83 @@ int san_boot ( unsigned int drive ); */ int san_describe ( unsigned int drive ); +extern struct list_head san_devices; + +/** Iterate over all SAN devices */ +#define for_each_sandev( sandev ) \ + list_for_each_entry ( (sandev), &san_devices, list ) + +/** There exist some SAN devices + * + * @ret existence Existence of SAN devices + */ +static inline int have_sandevs ( void ) { + return ( ! list_empty ( &san_devices ) ); +} + +/** + * Get reference to SAN device + * + * @v sandev SAN device + * @ret sandev SAN device + */ +static inline __attribute__ (( always_inline )) struct san_device * +sandev_get ( struct san_device *sandev ) { + ref_get ( &sandev->refcnt ); + return sandev; +} + +/** + * Drop reference to SAN device + * + * @v sandev SAN device + */ +static inline __attribute__ (( always_inline )) void +sandev_put ( struct san_device *sandev ) { + ref_put ( &sandev->refcnt ); +} + +/** + * Calculate SAN device block size + * + * @v sandev SAN device + * @ret blksize Sector size + */ +static inline size_t sandev_blksize ( struct san_device *sandev ) { + return ( sandev->capacity.blksize << sandev->blksize_shift ); +} + +/** + * Calculate SAN device capacity + * + * @v sandev SAN device + * @ret blocks Number of blocks + */ +static inline uint64_t sandev_capacity ( struct san_device *sandev ) { + return ( sandev->capacity.blocks >> sandev->blksize_shift ); +} + +/** + * Check if SAN device needs to be reopened + * + * @v sandev SAN device + * @ret needs_reopen SAN device needs to be reopened + */ +static inline int sandev_needs_reopen ( struct san_device *sandev ) { + return ( sandev->block_rc != 0 ); +} + +extern struct san_device * sandev_find ( unsigned int drive ); +extern int sandev_reopen ( struct san_device *sandev ); +extern int sandev_reset ( struct san_device *sandev ); +extern int sandev_rw ( struct san_device *sandev, uint64_t lba, + unsigned int count, userptr_t buffer, + int ( * block_rw ) ( struct interface *control, + struct interface *data, + uint64_t lba, unsigned int count, + userptr_t buffer, size_t len ) ); +extern struct san_device * alloc_sandev ( struct uri *uri, size_t priv_size ); +extern int register_sandev ( struct san_device *sandev ); +extern void unregister_sandev ( struct san_device *sandev ); + #endif /* _IPXE_SANBOOT_H */ |