2001-09-25 16:49:28 +04:00
/*
2004-03-30 23:35:44 +04:00
* Copyright ( C ) 2001 - 2004 Sistina Software , Inc . All rights reserved .
2007-07-18 19:38:58 +04:00
* Copyright ( C ) 2004 - 2007 Red Hat , Inc . All rights reserved .
2001-09-25 16:49:28 +04:00
*
2004-03-30 23:35:44 +04:00
* This file is part of LVM2 .
2001-09-25 16:49:28 +04:00
*
2004-03-30 23:35:44 +04:00
* This copyrighted material is made available to anyone wishing to use ,
* modify , copy , or redistribute it subject to the terms and conditions
2007-08-21 00:55:30 +04:00
* of the GNU Lesser General Public License v .2 .1 .
2004-03-30 23:35:44 +04:00
*
2007-08-21 00:55:30 +04:00
* You should have received a copy of the GNU Lesser General Public License
2004-03-30 23:35:44 +04:00
* along with this program ; if not , write to the Free Software Foundation ,
* Inc . , 59 Temple Place , Suite 330 , Boston , MA 02111 - 1307 USA
*/
/*
2001-10-02 02:12:10 +04:00
* This is the in core representation of a volume group and its
2001-09-28 17:15:30 +04:00
* associated physical and logical volumes .
2001-09-25 16:49:28 +04:00
*/
2001-10-01 19:14:39 +04:00
# ifndef _LVM_METADATA_H
# define _LVM_METADATA_H
2001-09-25 16:49:28 +04:00
2002-11-18 17:04:08 +03:00
# include "ctype.h"
2001-10-01 20:21:21 +04:00
# include "dev-cache.h"
2006-04-19 19:33:07 +04:00
# include "lvm-string.h"
2007-07-18 19:38:58 +04:00
# include "metadata-exported.h"
2002-12-20 02:25:55 +03:00
2007-07-18 19:38:58 +04:00
//#define MAX_STRIPES 128U
//#define SECTOR_SHIFT 9L
2002-11-18 17:04:08 +03:00
# define SECTOR_SIZE ( 1L << SECTOR_SHIFT )
2007-07-18 19:38:58 +04:00
//#define STRIPE_SIZE_MIN ( (unsigned) lvm_getpagesize() >> SECTOR_SHIFT) /* PAGESIZE in sectors */
//#define STRIPE_SIZE_MAX ( 512L * 1024L >> SECTOR_SHIFT) /* 512 KB in sectors */
//#define STRIPE_SIZE_LIMIT ((UINT_MAX >> 2) + 1)
//#define PV_MIN_SIZE ( 512L * 1024L >> SECTOR_SHIFT) /* 512 KB in sectors */
//#define MAX_RESTRICTED_LVS 255 /* Used by FMT_RESTRICTED_LVIDS */
2006-09-12 01:14:56 +04:00
# define MIRROR_LOG_SIZE 1 /* Extents */
2001-10-02 02:12:10 +04:00
/* Various flags */
/* Note that the bits no longer necessarily correspond to LVM1 disk format */
2007-07-18 19:38:58 +04:00
//#define PARTIAL_VG 0x00000001U /* VG */
//#define EXPORTED_VG 0x00000002U /* VG PV */
//#define RESIZEABLE_VG 0x00000004U /* VG */
2002-07-11 18:36:45 +04:00
2002-11-18 17:04:08 +03:00
/* May any free extents on this PV be used or must they be left free? */
2007-07-18 19:38:58 +04:00
//#define ALLOCATABLE_PV 0x00000008U /* PV */
2001-10-02 02:12:10 +04:00
2006-05-10 01:23:51 +04:00
# define SPINDOWN_LV 0x00000010U /* LV */
# define BADBLOCK_ON 0x00000020U /* LV */
2007-07-18 19:38:58 +04:00
//#define VISIBLE_LV 0x00000040U /* LV */
//#define FIXED_MINOR 0x00000080U /* LV */
2002-11-18 17:04:08 +03:00
/* FIXME Remove when metadata restructuring is completed */
2007-07-18 19:38:58 +04:00
//#define SNAPSHOT 0x00001000U /* LV - internal use only */
//#define PVMOVE 0x00002000U /* VG LV SEG */
//#define LOCKED 0x00004000U /* LV */
//#define MIRRORED 0x00008000U /* LV - internal use only */
2006-05-10 01:23:51 +04:00
# define VIRTUAL 0x00010000U /* LV - internal use only */
2007-07-18 19:38:58 +04:00
//#define MIRROR_LOG 0x00020000U /* LV */
//#define MIRROR_IMAGE 0x00040000U /* LV */
//#define MIRROR_NOTSYNCED 0x00080000U /* LV */
2006-05-12 00:03:40 +04:00
# define ACTIVATE_EXCL 0x00100000U /* LV - internal use only */
# define PRECOMMITTED 0x00200000U /* VG - internal use only */
2006-05-10 01:23:51 +04:00
2007-07-18 19:38:58 +04:00
//#define LVM_READ 0x00000100U /* LV VG */
//#define LVM_WRITE 0x00000200U /* LV VG */
//#define CLUSTERED 0x00000400U /* VG */
2006-05-10 01:23:51 +04:00
# define SHARED 0x00000800U /* VG */
2001-10-02 02:12:10 +04:00
2002-11-18 17:04:08 +03:00
/* Format features flags */
2007-07-18 19:38:58 +04:00
//#define FMT_SEGMENTS 0x00000001U /* Arbitrary segment params? */
//#define FMT_MDAS 0x00000002U /* Proper metadata areas? */
//#define FMT_TAGS 0x00000004U /* Tagging? */
//#define FMT_UNLIMITED_VOLS 0x00000008U /* Unlimited PVs/LVs? */
//#define FMT_RESTRICTED_LVIDS 0x00000010U /* LVID <= 255 */
//#define FMT_ORPHAN_ALLOCATABLE 0x00000020U /* Orphan PV allocatable? */
2006-05-10 01:23:51 +04:00
# define FMT_PRECOMMIT 0x00000040U /* Supports pre-commit? */
2007-07-18 19:38:58 +04:00
//#define FMT_RESIZE_PV 0x00000080U /* Supports pvresize? */
//#define FMT_UNLIMITED_STRIPESIZE 0x00000100U /* Unlimited stripe size? */
2002-11-18 17:04:08 +03:00
struct metadata_area ;
/* Per-format per-metadata area operations */
struct metadata_area_ops {
struct volume_group * ( * vg_read ) ( struct format_instance * fi ,
const char * vg_name ,
struct metadata_area * mda ) ;
2005-04-06 22:59:55 +04:00
struct volume_group * ( * vg_read_precommit ) ( struct format_instance * fi ,
const char * vg_name ,
struct metadata_area * mda ) ;
2002-11-18 17:04:08 +03:00
/*
* Write out complete VG metadata . You must ensure internal
* consistency before calling . eg . PEs can ' t refer to PVs not
* part of the VG .
*
* It is also the responsibility of the caller to ensure external
* consistency , eg by calling pv_write ( ) if removing PVs from
* a VG or calling vg_write ( ) a second time if splitting a VG
* into two .
*
* vg_write ( ) should not read or write from any PVs not included
* in the volume_group structure it is handed .
* ( format1 currently breaks this rule . )
*/
int ( * vg_write ) ( struct format_instance * fid , struct volume_group * vg ,
struct metadata_area * mda ) ;
2005-04-06 22:59:55 +04:00
int ( * vg_precommit ) ( struct format_instance * fid ,
struct volume_group * vg ,
struct metadata_area * mda ) ;
2002-11-18 17:04:08 +03:00
int ( * vg_commit ) ( struct format_instance * fid ,
struct volume_group * vg , struct metadata_area * mda ) ;
2003-07-05 02:34:56 +04:00
int ( * vg_revert ) ( struct format_instance * fid ,
struct volume_group * vg , struct metadata_area * mda ) ;
2002-11-18 17:04:08 +03:00
int ( * vg_remove ) ( struct format_instance * fi , struct volume_group * vg ,
struct metadata_area * mda ) ;
2007-11-05 20:17:55 +03:00
/*
* Returns number of free sectors in given metadata area .
*/
uint64_t ( * mda_free_sectors ) ( struct metadata_area * mda ) ;
2007-03-23 15:43:17 +03:00
/*
* Check if metadata area belongs to vg
*/
int ( * mda_in_vg ) ( struct format_instance * fi ,
struct volume_group * vg , struct metadata_area * mda ) ;
2007-04-26 01:10:55 +04:00
/*
* Analyze a metadata area on a PV .
*/
int ( * pv_analyze_mda ) ( const struct format_type * fmt ,
struct metadata_area * mda ) ;
2002-11-18 17:04:08 +03:00
} ;
2002-04-24 22:20:51 +04:00
struct metadata_area {
struct list list ;
2002-11-18 17:04:08 +03:00
struct metadata_area_ops * ops ;
2002-04-24 22:20:51 +04:00
void * metadata_locn ;
} ;
2005-10-18 17:43:40 +04:00
# define seg_pvseg(seg, s) (seg)->areas[(s)].u.pv.pvseg
# define seg_dev(seg, s) (seg)->areas[(s)].u.pv.pvseg->pv->dev
# define seg_pe(seg, s) (seg)->areas[(s)].u.pv.pvseg->pe
# define seg_le(seg, s) (seg)->areas[(s)].u.lv.le
2005-06-01 20:51:55 +04:00
2001-10-05 02:53:37 +04:00
struct name_list {
2001-10-31 15:47:01 +03:00
struct list list ;
2001-10-08 20:08:16 +04:00
char * name ;
2001-10-02 21:09:05 +04:00
} ;
2002-11-18 17:04:08 +03:00
struct mda_list {
struct list list ;
struct device_area mda ;
} ;
2001-11-12 15:16:57 +03:00
2005-04-20 00:52:35 +04:00
struct peg_list {
struct list list ;
struct pv_segment * peg ;
} ;
2008-01-16 22:00:59 +03:00
struct seg_list {
struct list list ;
unsigned count ;
struct lv_segment * seg ;
} ;
2001-10-10 13:25:04 +04:00
/*
* Ownership of objects passes to caller .
*/
2001-11-12 15:16:57 +03:00
struct format_handler {
2001-10-10 13:25:04 +04:00
/*
2002-11-18 17:04:08 +03:00
* Scan any metadata areas that aren ' t referenced in PV labels
2001-10-10 13:25:04 +04:00
*/
2002-12-20 02:25:55 +03:00
int ( * scan ) ( const struct format_type * fmt ) ;
2001-09-25 16:49:28 +04:00
2001-10-10 13:25:04 +04:00
/*
* Return PV with given path .
*/
2002-12-20 02:25:55 +03:00
int ( * pv_read ) ( const struct format_type * fmt , const char * pv_name ,
2002-11-18 17:04:08 +03:00
struct physical_volume * pv , struct list * mdas ) ;
2001-10-05 02:53:37 +04:00
2001-10-10 13:25:04 +04:00
/*
2001-11-12 15:16:57 +03:00
* Tweak an already filled out a pv ready for importing into a
* vg . eg . pe_count is format specific .
2001-10-10 13:25:04 +04:00
*/
2002-12-20 02:25:55 +03:00
int ( * pv_setup ) ( const struct format_type * fmt ,
2002-11-18 17:04:08 +03:00
uint64_t pe_start , uint32_t extent_count ,
uint32_t extent_size ,
int pvmetadatacopies ,
uint64_t pvmetadatasize , struct list * mdas ,
struct physical_volume * pv , struct volume_group * vg ) ;
2001-10-10 13:25:04 +04:00
/*
2001-11-12 15:16:57 +03:00
* Write a PV structure to disk . Fails if the PV is in a VG ie
2007-11-02 16:06:42 +03:00
* pv - > vg_name must be a valid orphan VG name
2001-10-10 13:25:04 +04:00
*/
2002-12-20 02:25:55 +03:00
int ( * pv_write ) ( const struct format_type * fmt ,
struct physical_volume * pv , struct list * mdas ,
int64_t label_sector ) ;
2001-09-25 16:49:28 +04:00
2002-01-24 20:15:49 +03:00
/*
* Tweak an already filled out a lv eg , check there
* aren ' t too many extents .
*/
2002-11-18 17:04:08 +03:00
int ( * lv_setup ) ( struct format_instance * fi ,
struct logical_volume * lv ) ;
2002-01-24 20:15:49 +03:00
2001-10-12 18:25:53 +04:00
/*
2001-11-12 15:16:57 +03:00
* Tweak an already filled out vg . eg , max_pv is format
* specific .
2001-10-12 18:25:53 +04:00
*/
2002-11-18 17:04:08 +03:00
int ( * vg_setup ) ( struct format_instance * fi , struct volume_group * vg ) ;
2001-10-05 02:53:37 +04:00
2004-09-14 17:56:18 +04:00
/*
* Check whether particular segment type is supported .
*/
int ( * segtype_supported ) ( struct format_instance * fid ,
2006-05-10 01:23:51 +04:00
const struct segment_type * segtype ) ;
2004-09-14 17:56:18 +04:00
2002-04-24 22:20:51 +04:00
/*
* Create format instance with a particular metadata area
*/
2002-12-20 02:25:55 +03:00
struct format_instance * ( * create_instance ) ( const struct format_type *
fmt , const char * vgname ,
2006-04-13 01:23:04 +04:00
const char * vgid ,
2002-11-18 17:04:08 +03:00
void * context ) ;
2002-04-24 22:20:51 +04:00
/*
* Destructor for format instance
*/
2002-11-18 17:04:08 +03:00
void ( * destroy_instance ) ( struct format_instance * fid ) ;
2001-10-05 02:53:37 +04:00
2001-10-10 13:25:04 +04:00
/*
2002-04-24 22:20:51 +04:00
* Destructor for format type
2001-10-10 13:25:04 +04:00
*/
2002-12-20 02:25:55 +03:00
void ( * destroy ) ( const struct format_type * fmt ) ;
2001-09-28 17:15:30 +04:00
} ;
2001-09-25 16:49:28 +04:00
2001-10-12 14:32:06 +04:00
/*
* Utility functions
*/
2006-08-17 23:30:59 +04:00
unsigned long pe_align ( void ) ;
2005-07-12 23:40:59 +04:00
int vg_validate ( struct volume_group * vg ) ;
2007-07-18 19:38:58 +04:00
2007-02-07 16:29:52 +03:00
int pv_write_orphan ( struct cmd_context * cmd , struct physical_volume * pv ) ;
2001-11-12 22:28:50 +03:00
2001-10-05 02:53:37 +04:00
/* Manipulate PV structures */
2001-10-02 02:12:10 +04:00
int pv_add ( struct volume_group * vg , struct physical_volume * pv ) ;
2001-10-03 16:34:08 +04:00
int pv_remove ( struct volume_group * vg , struct physical_volume * pv ) ;
2002-11-18 17:04:08 +03:00
struct physical_volume * pv_find ( struct volume_group * vg , const char * pv_name ) ;
2001-10-05 02:53:37 +04:00
2001-10-29 16:52:23 +03:00
/* Find a PV within a given VG */
2005-04-18 03:57:44 +04:00
int get_pv_from_vg_by_id ( const struct format_type * fmt , const char * vg_name ,
2006-04-13 01:23:04 +04:00
const char * vgid , const char * pvid ,
struct physical_volume * pv ) ;
2001-10-05 02:53:37 +04:00
2002-11-18 17:04:08 +03:00
struct lv_list * find_lv_in_vg_by_lvid ( struct volume_group * vg ,
2002-12-20 02:25:55 +03:00
const union lvid * lvid ) ;
2001-10-29 16:52:23 +03:00
2008-03-28 22:08:23 +03:00
struct lv_list * find_lv_in_lv_list ( const struct list * ll ,
const struct logical_volume * lv ) ;
2001-10-29 16:52:23 +03:00
/* Return the VG that contains a given LV (based on path given in lv_name) */
/* or environment var */
struct volume_group * find_vg_with_lv ( const char * lv_name ) ;
2002-11-18 17:04:08 +03:00
/* Find LV with given lvid (used during activation) */
struct logical_volume * lv_from_lvid ( struct cmd_context * cmd ,
2005-10-31 23:15:28 +03:00
const char * lvid_s ,
2008-03-17 19:51:31 +03:00
unsigned precommitted ) ;
2001-10-29 16:52:23 +03:00
/* FIXME Merge these functions with ones above */
2001-11-27 19:37:33 +03:00
struct physical_volume * find_pv ( struct volume_group * vg , struct device * dev ) ;
2001-09-28 17:15:30 +04:00
2008-03-28 22:08:23 +03:00
struct pv_list * find_pv_in_pv_list ( const struct list * pl ,
const struct physical_volume * pv ) ;
2003-04-25 02:23:24 +04:00
/* Find LV segment containing given LE */
2007-12-20 21:55:46 +03:00
struct lv_segment * find_seg_by_le ( const struct logical_volume * lv , uint32_t le ) ;
2003-04-25 02:23:24 +04:00
2005-05-03 21:28:23 +04:00
/* Find PV segment containing given LE */
2007-12-20 21:55:46 +03:00
struct pv_segment * find_peg_by_pe ( const struct physical_volume * pv , uint32_t pe ) ;
2005-05-03 21:28:23 +04:00
2001-11-12 15:16:57 +03:00
/*
2001-11-14 16:52:38 +03:00
* Remove a dev_dir if present .
2001-11-12 15:16:57 +03:00
*/
const char * strip_dir ( const char * vg_name , const char * dir ) ;
2001-10-15 22:39:40 +04:00
2002-01-10 14:18:08 +03:00
/*
* Checks that an lv has no gaps or overlapping segments .
2005-10-28 01:51:28 +04:00
* Set complete_vg to perform additional VG level checks .
2002-01-10 14:18:08 +03:00
*/
2005-10-28 01:51:28 +04:00
int check_lv_segments ( struct logical_volume * lv , int complete_vg ) ;
2002-01-10 14:18:08 +03:00
/*
* Sometimes ( eg , after an lvextend ) , it is possible to merge two
* adjacent segments into a single segment . This function trys
* to merge as many segments as possible .
*/
int lv_merge_segments ( struct logical_volume * lv ) ;
2003-09-15 22:22:50 +04:00
/*
* Ensure there ' s a segment boundary at a given LE , splitting if necessary
*/
int lv_split_segment ( struct logical_volume * lv , uint32_t le ) ;
2008-01-16 22:00:59 +03:00
/*
* Add / remove upward link from underlying LV to the segment using it
* FIXME : ridiculously long name
*/
int add_seg_to_segs_using_this_lv ( struct logical_volume * lv , struct lv_segment * seg ) ;
int remove_seg_from_segs_using_this_lv ( struct logical_volume * lv , struct lv_segment * seg ) ;
struct lv_segment * get_only_segment_using_this_lv ( struct logical_volume * lv ) ;
2008-04-02 02:40:13 +04:00
/*
* For internal metadata caching .
*/
int export_vg_to_buffer ( struct volume_group * vg , char * * buf ) ;
struct volume_group * import_vg_from_buffer ( char * buf ,
struct format_instance * fid ) ;
2003-04-30 19:23:43 +04:00
/*
* Mirroring functions
*/
2005-11-29 21:20:23 +03:00
2005-10-27 23:58:22 +04:00
/*
* Given mirror image or mirror log segment , find corresponding mirror segment
*/
2005-10-28 01:51:28 +04:00
int fixup_imported_mirrors ( struct volume_group * vg ) ;
2005-06-14 22:22:31 +04:00
2007-06-13 01:20:20 +04:00
/*
2007-07-12 03:33:12 +04:00
* Begin skeleton for external LVM library
2007-06-13 01:20:20 +04:00
*/
2007-10-12 18:08:10 +04:00
struct id pv_id ( const pv_t * pv ) ;
const struct format_type * pv_format_type ( const pv_t * pv ) ;
struct id pv_vgid ( const pv_t * pv ) ;
2007-06-19 08:23:32 +04:00
2007-07-12 19:38:53 +04:00
pv_t * pv_by_path ( struct cmd_context * cmd , const char * pv_name ) ;
2007-07-12 09:04:42 +04:00
int add_pv_to_vg ( struct volume_group * vg , const char * pv_name ,
struct physical_volume * pv ) ;
2007-07-12 03:33:12 +04:00
2001-09-28 17:15:30 +04:00
# endif