]> git.ipfire.org Git - thirdparty/mdadm.git/blobdiff - monitor.c
Create.c: fix uclibc build
[thirdparty/mdadm.git] / monitor.c
index 820a93d0ceaf6aa6fc44618a14da3d3e136107c1..be0bec785080351412f4a1fcd07e031e1d356b68 100644 (file)
--- a/monitor.c
+++ b/monitor.c
@@ -81,15 +81,15 @@ static int read_attr(char *buf, int len, int fd)
 
 static void read_resync_start(int fd, unsigned long long *v)
 {
-       char buf[30];
+       char buf[SYSFS_MAX_BUF_SIZE];
        int n;
 
-       n = read_attr(buf, 30, fd);
+       n = read_attr(buf, sizeof(buf), fd);
        if (n <= 0) {
                dprintf("Failed to read resync_start (%d)\n", fd);
                return;
        }
-       if (strncmp(buf, "none", 4) == 0)
+       if (str_is_none(buf) == true)
                *v = MaxSector;
        else
                *v = strtoull(buf, NULL, 10);
@@ -98,11 +98,11 @@ static void read_resync_start(int fd, unsigned long long *v)
 static unsigned long long read_sync_completed(int fd)
 {
        unsigned long long val;
-       char buf[50];
+       char buf[SYSFS_MAX_BUF_SIZE];
        int n;
        char *ep;
 
-       n = read_attr(buf, 50, fd);
+       n = read_attr(buf, sizeof(buf), fd);
 
        if (n <= 0)
                return 0;
@@ -115,8 +115,8 @@ static unsigned long long read_sync_completed(int fd)
 
 static enum array_state read_state(int fd)
 {
-       char buf[20];
-       int n = read_attr(buf, 20, fd);
+       char buf[SYSFS_MAX_BUF_SIZE];
+       int n = read_attr(buf, sizeof(buf), fd);
 
        if (n <= 0)
                return bad_word;
@@ -125,8 +125,8 @@ static enum array_state read_state(int fd)
 
 static enum sync_action read_action( int fd)
 {
-       char buf[20];
-       int n = read_attr(buf, 20, fd);
+       char buf[SYSFS_MAX_BUF_SIZE];
+       int n = read_attr(buf, sizeof(buf), fd);
 
        if (n <= 0)
                return bad_action;
@@ -135,7 +135,7 @@ static enum sync_action read_action( int fd)
 
 int read_dev_state(int fd)
 {
-       char buf[100];
+       char buf[SYSFS_MAX_BUF_SIZE];
        int n = read_attr(buf, sizeof(buf), fd);
        char *cp;
        int rv = 0;
@@ -412,6 +412,7 @@ static int read_and_act(struct active_array *a, fd_set *fds)
        int ret = 0;
        int count = 0;
        struct timeval tv;
+       bool write_checkpoint = false;
 
        a->next_state = bad_word;
        a->next_action = bad_action;
@@ -564,52 +565,40 @@ static int read_and_act(struct active_array *a, fd_set *fds)
                }
        }
 
-       /* Check for recovery checkpoint notifications.  We need to be a
-        * minimum distance away from the last checkpoint to prevent
-        * over checkpointing.  Note reshape checkpointing is handled
-        * in the second branch.
-        */
-       if (sync_completed > a->last_checkpoint &&
-           sync_completed - a->last_checkpoint > a->info.component_size >> 4 &&
-           a->curr_action > reshape) {
-               /* A (non-reshape) sync_action has reached a checkpoint.
-                * Record the updated position in the metadata
-                */
-               a->last_checkpoint = sync_completed;
-               a->container->ss->set_array_state(a, a->curr_state <= clean);
-       } else if ((a->curr_action == idle && a->prev_action == reshape) ||
-                  (a->curr_action == reshape &&
-                   sync_completed > a->last_checkpoint)) {
-               /* Reshape has progressed or completed so we need to
-                * update the array state - and possibly the array size
-                */
+       /* Update reshape checkpoint, depending if it finished or progressed */
+       if (a->curr_action == idle && a->prev_action == reshape) {
+               char buf[SYSFS_MAX_BUF_SIZE];
+
                if (sync_completed != 0)
                        a->last_checkpoint = sync_completed;
-               /* We might need to update last_checkpoint depending on
-                * the reason that reshape finished.
-                * if array reshape is really finished:
-                *        set check point to the end, this allows
-                *        set_array_state() to finalize reshape in metadata
-                * if reshape if broken: do not set checkpoint to the end
-                *        this allows for reshape restart from checkpoint
+
+               /*
+                * If reshape really finished, set checkpoint to the end to finalize it.
+                * Do not set checkpoint if reshape is broken.
+                * Reshape will restart from last checkpoint.
                 */
-               if ((a->curr_action != reshape) &&
-                   (a->prev_action == reshape)) {
-                       char buf[40];
-                       if ((sysfs_get_str(&a->info, NULL,
-                                         "reshape_position",
-                                         buf,
-                                         sizeof(buf)) >= 0) &&
-                            strncmp(buf, "none", 4) == 0)
+               if (sysfs_get_str(&a->info, NULL, "reshape_position", buf, sizeof(buf)) >= 0)
+                       if (str_is_none(buf) == true)
                                a->last_checkpoint = a->info.component_size;
-               }
-               a->container->ss->set_array_state(a, a->curr_state <= clean);
-               a->last_checkpoint = sync_completed;
+
+               write_checkpoint = true;
        }
 
-       if (sync_completed > a->last_checkpoint)
+       if (a->curr_action >= reshape && sync_completed > a->last_checkpoint) {
+               /* Update checkpoint if neither reshape nor idle action */
                a->last_checkpoint = sync_completed;
 
+               write_checkpoint = true;
+       }
+
+       /* Save checkpoint */
+       if (write_checkpoint) {
+               a->container->ss->set_array_state(a, a->curr_state <= clean);
+
+               if (a->curr_action <= reshape)
+                       a->last_checkpoint = sync_completed;
+       }
+
        if (sync_completed >= a->info.component_size)
                a->last_checkpoint = 0;