]> git.ipfire.org Git - thirdparty/mdadm.git/blobdiff - mdadm.h
mdadm: Move pr_vrb define to mdadm.h
[thirdparty/mdadm.git] / mdadm.h
diff --git a/mdadm.h b/mdadm.h
index 23ffe97748ab147602a068f8ba671c312a143cf7..fbb161ba4dc2bfa5ced6326ccc7b125655f3ed5a 100644 (file)
--- a/mdadm.h
+++ b/mdadm.h
@@ -100,6 +100,22 @@ struct dlm_lksb {
 #define DEFAULT_BITMAP_DELAY 5
 #define DEFAULT_MAX_WRITE_BEHIND 256
 
+/* DEV_NUM_PREF is a subpath to numbered MD devices, e.g. /dev/md1 or directory name.
+ * DEV_NUM_PREF_LEN is a length with Null byte excluded.
+ */
+#ifndef DEV_NUM_PREF
+#define DEV_NUM_PREF "/dev/md"
+#define DEV_NUM_PREF_LEN (sizeof(DEV_NUM_PREF) - 1)
+#endif /* DEV_NUM_PREF */
+
+/* DEV_MD_DIR points to named MD devices directory.
+ * DEV_MD_DIR_LEN is a length with Null byte excluded.
+ */
+#ifndef DEV_MD_DIR
+#define DEV_MD_DIR "/dev/md/"
+#define DEV_MD_DIR_LEN (sizeof(DEV_MD_DIR) - 1)
+#endif /* DEV_MD_DIR */
+
 /* MAP_DIR should be somewhere that persists across the pivotroot
  * from early boot to late boot.
  * /run  seems to have emerged as the best standard.
@@ -275,6 +291,14 @@ static inline void __put_unaligned32(__u32 val, void *p)
 
 #define ARRAY_SIZE(x) (sizeof(x)/sizeof(x[0]))
 
+#define KIB_TO_BYTES(x)        ((x) << 10)
+#define SEC_TO_BYTES(x)        ((x) << 9)
+
+/**
+ * This is true for native and DDF, IMSM allows 16.
+ */
+#define MD_NAME_MAX 32
+
 extern const char Name[];
 
 struct md_bb_entry {
@@ -353,9 +377,13 @@ struct mdinfo {
        int container_member; /* for assembling external-metatdata arrays
                               * This is to be used internally by metadata
                               * handler only */
-       int container_enough; /* flag external handlers can set to
-                              * indicate that subarrays have not enough (-1),
-                              * enough to start (0), or all expected disks (1) */
+       /**
+        * flag external handlers can set to indicate that subarrays have:
+        * - not enough disks to start (-1),
+        * - enough disks to start (0),
+        * - all expected disks (1).
+        */
+       int container_enough;
        char            sys_name[32];
        struct mdinfo *devs;
        struct mdinfo *next;
@@ -402,10 +430,18 @@ struct createinfo {
 };
 
 struct spare_criteria {
+       bool criteria_set;
        unsigned long long min_size;
        unsigned int sector_size;
+       struct dev_policy *pols;
 };
 
+typedef enum mdadm_status {
+       MDADM_STATUS_SUCCESS = 0,
+       MDADM_STATUS_ERROR,
+       MDADM_STATUS_UNDEF,
+} mdadm_status_t;
+
 enum mode {
        ASSEMBLE=1,
        BUILD,
@@ -435,6 +471,7 @@ extern char Version[], Usage[], Help[], OptionHelp[],
  */
 enum special_options {
        AssumeClean = 300,
+       WriteZeroes,
        BitmapChunk,
        WriteBehind,
        ReAdd,
@@ -497,6 +534,51 @@ enum special_options {
        ConsistencyPolicy,
 };
 
+enum update_opt {
+       UOPT_NAME = 1,
+       UOPT_PPL,
+       UOPT_NO_PPL,
+       UOPT_BITMAP,
+       UOPT_NO_BITMAP,
+       UOPT_SUBARRAY_ONLY,
+       UOPT_SPARC22,
+       UOPT_SUPER_MINOR,
+       UOPT_SUMMARIES,
+       UOPT_RESYNC,
+       UOPT_UUID,
+       UOPT_HOMEHOST,
+       UOPT_HOME_CLUSTER,
+       UOPT_NODES,
+       UOPT_DEVICESIZE,
+       UOPT_BBL,
+       UOPT_NO_BBL,
+       UOPT_FORCE_NO_BBL,
+       UOPT_METADATA,
+       UOPT_REVERT_RESHAPE,
+       UOPT_LAYOUT_ORIGINAL,
+       UOPT_LAYOUT_ALTERNATE,
+       UOPT_LAYOUT_UNSPECIFIED,
+       UOPT_BYTEORDER,
+       UOPT_HELP,
+       UOPT_USER_ONLY,
+       /*
+        * Code specific options, cannot be set by the user
+        */
+       UOPT_SPEC_FORCE_ONE,
+       UOPT_SPEC_FORCE_ARRAY,
+       UOPT_SPEC_ASSEMBLE,
+       UOPT_SPEC_LINEAR_GROW_NEW,
+       UOPT_SPEC_LINEAR_GROW_UPDATE,
+       UOPT_SPEC__RESHAPE_PROGRESS,
+       UOPT_SPEC_WRITEMOSTLY,
+       UOPT_SPEC_READWRITE,
+       UOPT_SPEC_FAILFAST,
+       UOPT_SPEC_NOFAILFAST,
+       UOPT_SPEC_REVERT_RESHAPE_NOBACKUP,
+       UOPT_UNDEFINED
+};
+extern void fprint_update_options(FILE *outf, enum update_opt update_mode);
+
 enum prefix_standard {
        JEDEC,
        IEC
@@ -528,7 +610,7 @@ struct mddev_ident {
 
        int     uuid_set;
        int     uuid[4];
-       char    name[33];
+       char    name[MD_NAME_MAX + 1];
 
        int super_minor;
 
@@ -571,7 +653,7 @@ struct context {
        int     export;
        int     test;
        char    *subarray;
-       char    *update;
+       enum    update_opt update;
        int     scan;
        int     SparcAdjust;
        int     autof;
@@ -595,6 +677,7 @@ struct shape {
        int     bitmap_chunk;
        char    *bitmap_file;
        int     assume_clean;
+       bool    write_zeroes;
        int     write_behind;
        unsigned long long size;
        unsigned long long data_offset;
@@ -693,6 +776,10 @@ enum sysfs_read_flags {
        GET_DEVS_ALL    = (1 << 27),
 };
 
+#define SYSFS_MAX_BUF_SIZE 64
+
+extern void sysfs_get_container_devnm(struct mdinfo *mdi, char *buf);
+
 /* If fd >= 0, get the array it is open on,
  * else use devnm.
  */
@@ -724,7 +811,7 @@ extern int sysfs_attribute_available(struct mdinfo *sra, struct mdinfo *dev,
 extern int sysfs_get_str(struct mdinfo *sra, struct mdinfo *dev,
                         char *name, char *val, int size);
 extern int sysfs_set_safemode(struct mdinfo *sra, unsigned long ms);
-extern int sysfs_set_array(struct mdinfo *info, int vers);
+extern int sysfs_set_array(struct mdinfo *info);
 extern int sysfs_add_disk(struct mdinfo *sra, struct mdinfo *sd, int resume);
 extern int sysfs_disk_to_scsi_id(int fd, __u32 *id);
 extern int sysfs_unique_holder(char *devnm, long rdev);
@@ -777,7 +864,7 @@ extern char *map_num(mapping_t *map, int num);
 extern int map_name(mapping_t *map, char *name);
 extern mapping_t r0layout[], r5layout[], r6layout[],
        pers[], modes[], faultylayout[];
-extern mapping_t consistency_policies[], sysfs_array_states[];
+extern mapping_t consistency_policies[], sysfs_array_states[], update_options[];
 
 extern char *map_dev_preferred(int major, int minor, int create,
                               char *prefer);
@@ -854,6 +941,23 @@ struct reshape {
        unsigned long long new_size; /* New size of array in sectors */
 };
 
+/**
+ * struct dev_policy - Data structure for policy management.
+ * @next: pointer to next dev_policy.
+ * @name: policy name, category.
+ * @metadata: the metadata type it affects.
+ * @value: value of the policy.
+ *
+ * The functions to manipulate dev_policy lists do not free elements, so they must be statically
+ * allocated. @name and @metadata can be compared by address.
+ */
+typedef struct dev_policy {
+       struct dev_policy *next;
+       char *name;
+       const char *metadata;
+       const char *value;
+} dev_policy_t;
+
 /* A superswitch provides entry point to a metadata handler.
  *
  * The superswitch primarily operates on some "metadata" that
@@ -966,7 +1070,7 @@ extern struct superswitch {
         *                    it will resume going in the opposite direction.
         */
        int (*update_super)(struct supertype *st, struct mdinfo *info,
-                           char *update,
+                           enum update_opt update,
                            char *devname, int verbose,
                            int uuid_set, char *homehost);
 
@@ -1032,10 +1136,9 @@ extern struct superswitch {
         * Return spare criteria for array:
         * - minimum disk size can be used in array;
         * - sector size can be used in array.
-        * Return values: 0 - for success and -EINVAL on error.
         */
-       int (*get_spare_criteria)(struct supertype *st,
-                                 struct spare_criteria *sc);
+       mdadm_status_t (*get_spare_criteria)(struct supertype *st, char *mddev_path,
+                                            struct spare_criteria *sc);
        /* Find somewhere to put a bitmap - possibly auto-size it - and
         * update the metadata to record this.  The array may be newly
         * created, in which case data_size may be updated, or it might
@@ -1083,6 +1186,25 @@ extern struct superswitch {
                                 char *subdev, unsigned long long *freesize,
                                 int consistency_policy, int verbose);
 
+       /**
+        * test_and_add_drive_policies() - test new and add custom policies from metadata handler.
+        * @pols: list of currently recorded policies.
+        * @disk_fd: file descriptor of the device to check.
+        * @verbose: verbose flag.
+        *
+        * Used by IMSM to verify all drives in container/array, against requirements not recored
+        * in superblock, like controller type for IMSM. It should check all drives even if
+        * they are not actually used, because mdmon or kernel are free to use any drive assigned to
+        * container automatically.
+        *
+        * Generating and comparison methods belong to metadata handler. It is not mandatory to be
+        * implemented.
+        *
+        * Return: MDADM_STATUS_SUCCESS is expected on success.
+        */
+       mdadm_status_t (*test_and_add_drive_policies)(dev_policy_t **pols, int disk_fd,
+                                                     const int verbose);
+
        /* Return a linked list of 'mdinfo' structures for all arrays
         * in the container.  For non-containers, it is like
         * getinfo_super with an allocated mdinfo.*/
@@ -1092,9 +1214,15 @@ extern struct superswitch {
        /* Permit subarray's to be deleted from inactive containers */
        int (*kill_subarray)(struct supertype *st,
                             char *subarray_id); /* optional */
-       /* Permit subarray's to be modified */
+       /**
+        * update_subarray() - Permit subarray to be modified.
+        * @st: Supertype.
+        * @subarray: Subarray name.
+        * @update: Update option.
+        * @ident: Optional identifiers.
+        */
        int (*update_subarray)(struct supertype *st, char *subarray,
-                              char *update, struct mddev_ident *ident); /* optional */
+                              enum update_opt update, struct mddev_ident *ident);
        /* Check if reshape is supported for this external format.
         * st is obtained from super_by_fd() where st->subarray[0] is
         * initialized to indicate if reshape is being performed at the
@@ -1158,21 +1286,6 @@ extern struct superswitch {
         */
        struct mdinfo *(*activate_spare)(struct active_array *a,
                                         struct metadata_update **updates);
-       /*
-        * Return statically allocated string that represents metadata specific
-        * controller domain of the disk. The domain is used in disk domain
-        * matching functions. Disks belong to the same domain if the they have
-        * the same domain from mdadm.conf and belong the same metadata domain.
-        * Returning NULL or not providing this handler means that metadata
-        * does not distinguish the differences between disks that belong to
-        * different controllers. They are in the domain specified by
-        * configuration file (mdadm.conf).
-        * In case when the metadata has the notion of domains based on disk
-        * it shall return NULL for disks that do not belong to the controller
-        * the supported domains. Such disks will form another domain and won't
-        * be mixed with supported ones.
-        */
-       const char *(*get_disk_controller_domain)(const char *path);
 
        /* for external backup area */
        int (*recover_backup)(struct supertype *st, struct mdinfo *info);
@@ -1207,6 +1320,8 @@ extern struct superswitch super0, super1;
 extern struct superswitch super_imsm, super_ddf;
 extern struct superswitch mbr, gpt;
 
+void imsm_set_no_platform(int v);
+
 struct metadata_update {
        int     len;
        char    *buf;
@@ -1277,27 +1392,8 @@ extern struct supertype *dup_super(struct supertype *st);
 extern int get_dev_size(int fd, char *dname, unsigned long long *sizep);
 extern int get_dev_sector_size(int fd, char *dname, unsigned int *sectsizep);
 extern int must_be_container(int fd);
-extern int dev_size_from_id(dev_t id, unsigned long long *size);
-extern int dev_sector_size_from_id(dev_t id, unsigned int *size);
 void wait_for(char *dev, int fd);
 
-/*
- * Data structures for policy management.
- * Each device can have a policy structure that lists
- * various name/value pairs each possibly with a metadata associated.
- * The policy list is sorted by name/value/metadata
- */
-struct dev_policy {
-       struct dev_policy *next;
-       char *name;     /* None of these strings are allocated.  They are
-                        * all just references to strings which are known
-                        * to exist elsewhere.
-                        * name and metadata can be compared by address equality.
-                        */
-       const char *metadata;
-       const char *value;
-};
-
 extern char pol_act[], pol_domain[], pol_metadata[], pol_auto[];
 
 /* iterate over the sublist starting at list, having the same
@@ -1339,10 +1435,16 @@ extern struct dev_policy *disk_policy(struct mdinfo *disk);
 extern struct dev_policy *devid_policy(int devid);
 extern void dev_policy_free(struct dev_policy *p);
 
-//extern void pol_new(struct dev_policy **pol, char *name, char *val, char *metadata);
 extern void pol_add(struct dev_policy **pol, char *name, char *val, char *metadata);
 extern struct dev_policy *pol_find(struct dev_policy *pol, char *name);
 
+extern mdadm_status_t drive_test_and_add_policies(struct supertype *st, dev_policy_t **pols,
+                                                 int fd, const int verbose);
+extern mdadm_status_t sysfs_test_and_add_drive_policies(struct supertype *st, dev_policy_t **pols,
+                                                       struct mdinfo *mdi, const int verbose);
+extern mdadm_status_t mddev_test_and_add_drive_policies(struct supertype *st, dev_policy_t **pols,
+                                                       int array_fd, const int verbose);
+
 enum policy_action {
        act_default,
        act_include,
@@ -1427,7 +1529,7 @@ extern int Manage_stop(char *devname, int fd, int quiet,
                       int will_retry);
 extern int Manage_subdevs(char *devname, int fd,
                          struct mddev_dev *devlist, int verbose, int test,
-                         char *update, int force);
+                         enum update_opt update, int force);
 extern int autodetect(void);
 extern int Grow_Add_device(char *devname, int fd, char *newdev);
 extern int Grow_addbitmap(char *devname, int fd,
@@ -1457,14 +1559,11 @@ extern int Assemble(struct supertype *st, char *mddev,
                    struct mddev_dev *devlist,
                    struct context *c);
 
-extern int Build(char *mddev, struct mddev_dev *devlist,
-                struct shape *s, struct context *c);
+extern int Build(struct mddev_ident *ident, struct mddev_dev *devlist, struct shape *s,
+                struct context *c);
 
-extern int Create(struct supertype *st, char *mddev,
-                 char *name, int *uuid,
-                 int subdevs, struct mddev_dev *devlist,
-                 struct shape *s,
-                 struct context *c);
+extern int Create(struct supertype *st, struct mddev_ident *ident, int subdevs,
+                 struct mddev_dev *devlist, struct shape *s, struct context *c);
 
 extern int Detail(char *dev, struct context *c);
 extern int Detail_Platform(struct superswitch *ss, int scan, int verbose, int export, char *controller_path);
@@ -1481,7 +1580,7 @@ extern int Monitor(struct mddev_dev *devlist,
 
 extern int Kill(char *dev, struct supertype *st, int force, int verbose, int noexcl);
 extern int Kill_subarray(char *dev, char *subarray, int verbose);
-extern int Update_subarray(char *dev, char *subarray, char *update, struct mddev_ident *ident, int quiet);
+extern int Update_subarray(char *dev, char *subarray, enum update_opt update, struct mddev_ident *ident, int quiet);
 extern int Wait(char *dev);
 extern int WaitClean(char *dev, int verbose);
 extern int SetAction(char *dev, char *action);
@@ -1527,7 +1626,7 @@ int default_layout(struct supertype *st, int level, int verbose);
 extern int is_near_layout_10(int layout);
 extern int parse_layout_10(char *layout);
 extern int parse_layout_faulty(char *layout);
-extern int parse_num(int *dest, char *num);
+extern int parse_num(int *dest, const char *num);
 extern int parse_cluster_confirm_arg(char *inp, char **devname, int *slot);
 extern int check_ext2(int fd, char *name);
 extern int check_reiser(int fd, char *name);
@@ -1535,9 +1634,11 @@ extern int check_raid(int fd, char *name);
 extern int check_partitions(int fd, char *dname,
                            unsigned long long freesize,
                            unsigned long long size);
+extern bool is_name_posix_compatible(const char *path);
 extern int fstat_is_blkdev(int fd, char *devname, dev_t *rdev);
 extern int stat_is_blkdev(char *devname, dev_t *rdev);
 
+extern bool is_string_lq(const char * const str, size_t max_len);
 extern bool is_dev_alive(char *path);
 extern int get_mdp_major(void);
 extern int get_maj_min(char *dev, int *major, int *minor);
@@ -1552,9 +1653,11 @@ extern int same_dev(char *one, char *two);
 extern int compare_paths (char* path1,char* path2);
 extern void enable_fds(int devices);
 extern void manage_fork_fds(int close_all);
-extern int continue_via_systemd(char *devnm, char *service_name);
+extern int continue_via_systemd(char *devnm, char *service_name, char *prefix);
 
 extern void ident_init(struct mddev_ident *ident);
+extern mdadm_status_t ident_set_devname(struct mddev_ident *ident, const char *devname);
+extern mdadm_status_t ident_set_name(struct mddev_ident *ident, const char *name);
 
 extern int parse_auto(char *str, char *msg, int config);
 extern struct mddev_ident *conf_get_ident(char *dev);
@@ -1572,10 +1675,13 @@ extern int conf_get_monitor_delay(void);
 extern char *conf_line(FILE *file);
 extern char *conf_word(FILE *file, int allow_key);
 extern void print_quoted(char *str);
-extern void print_escape(char *str);
 extern int use_udev(void);
+extern void print_escape(char *str);
 extern unsigned long GCD(unsigned long a, unsigned long b);
 extern int conf_name_is_free(char *name);
+extern bool is_devname_ignore(const char *devname);
+extern bool is_devname_md_numbered(const char *devname);
+extern bool is_devname_md_d_numbered(const char *devname);
 extern int conf_verify_devnames(struct mddev_ident *array_list);
 extern int devname_matches(char *name, char *match);
 extern struct mddev_ident *conf_match(struct supertype *st,
@@ -1590,8 +1696,7 @@ extern const int uuid_zero[4];
 extern int same_uuid(int a[4], int b[4], int swapuuid);
 extern void copy_uuid(void *a, int b[4], int swapuuid);
 extern char *__fname_from_uuid(int id[4], int swap, char *buf, char sep);
-extern char *fname_from_uuid(struct supertype *st,
-                            struct mdinfo *info, char *buf, char sep);
+extern char *fname_from_uuid(struct mdinfo *info, char *buf);
 extern unsigned long calc_csum(void *super, int bytes);
 extern int enough(int level, int raid_disks, int layout, int clean,
                   char *avail);
@@ -1613,6 +1718,9 @@ extern int assemble_container_content(struct supertype *st, int mdfd,
 #define        INCR_UNSAFE     2
 #define        INCR_ALREADY    4
 #define        INCR_YES        8
+
+extern bool devid_matches_criteria(struct supertype *st, dev_t devid, struct spare_criteria *sc);
+extern bool disk_fd_matches_criteria(struct supertype *st, int disk_fd, struct spare_criteria *sc);
 extern struct mdinfo *container_choose_spares(struct supertype *st,
                                              struct spare_criteria *criteria,
                                              struct domainlist *domlist,
@@ -1679,8 +1787,6 @@ extern char *fd2kname(int fd);
 extern char *stat2devnm(struct stat *st);
 bool stat_is_md_dev(struct stat *st);
 extern char *fd2devnm(int fd);
-extern void udev_block(char *devnm);
-extern void udev_unblock(void);
 
 extern int in_initrd(void);
 
@@ -1726,6 +1832,9 @@ extern void set_dlm_hooks(void);
 #define MSEC_TO_NSEC(msec) ((msec) * 1000000)
 #define USEC_TO_NSEC(usec) ((usec) * 1000)
 extern void sleep_for(unsigned int sec, long nsec, bool wake_after_interrupt);
+extern bool is_directory(const char *path);
+extern bool is_file(const char *path);
+extern int s_gethostname(char *buf, int buf_len);
 
 #define _ROUND_UP(val, base)   (((val) + (base) - 1) & ~(base - 1))
 #define ROUND_UP(val, base)    _ROUND_UP(val, (typeof(val))(base))
@@ -1760,11 +1869,10 @@ static inline char *to_subarray(struct mdstat_ent *ent, char *container)
  */
 static inline sighandler_t signal_s(int sig, sighandler_t handler)
 {
-       struct sigaction new_act;
-       struct sigaction old_act;
+       struct sigaction new_act = {0};
+       struct sigaction old_act = {0};
 
        new_act.sa_handler = handler;
-       new_act.sa_flags = 0;
 
        if (sigaction(sig, &new_act, &old_act) == 0)
                return old_act.sa_handler;
@@ -1801,6 +1909,10 @@ static inline int xasprintf(char **strp, const char *fmt, ...) {
 #endif
 #define cont_err(fmt ...) fprintf(stderr, "       " fmt)
 
+#define pr_info(fmt, args...) printf("%s: "fmt, Name, ##args)
+
+#define pr_vrb(fmt, arg...) ((void)(verbose && pr_err(fmt, ##arg)))
+
 void *xmalloc(size_t len);
 void *xrealloc(void *ptr, size_t len);
 void *xcalloc(size_t num, size_t size);
@@ -1923,11 +2035,6 @@ enum r0layout {
 /* And another special number needed for --data_offset=variable */
 #define VARIABLE_OFFSET 3
 
-/**
- * This is true for native and DDF, IMSM allows 16.
- */
-#define MD_NAME_MAX 32
-
 /**
  * is_container() - check if @level is &LEVEL_CONTAINER
  * @level: level value
@@ -1941,3 +2048,19 @@ static inline int is_container(const int level)
                return 1;
        return 0;
 }
+
+#define STR_COMMON_NONE "none"
+
+/**
+ * str_is_none() - check if @str starts with "none".
+ * @str: string
+ *
+ * return:
+ * true if string starts with "none", false otherwise.
+ */
+static inline bool str_is_none(char *str)
+{
+       if (strncmp(str, STR_COMMON_NONE, sizeof(STR_COMMON_NONE) - 1) == 0)
+               return true;
+       return false;
+}