]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
libmount: add functions to handle comments in fs tables
authorOndrej Oprala <ooprala@redhat.com>
Fri, 14 Jun 2013 10:41:30 +0000 (12:41 +0200)
committerKarel Zak <kzak@redhat.com>
Wed, 3 Jul 2013 08:17:37 +0000 (10:17 +0200)
Co-Author: Karel Zak <kzak@redhat.com>
Signed-off-by: Ondrej Oprala <ooprala@redhat.com>
Signed-off-by: Karel Zak <kzak@redhat.com>
libmount/src/fs.c
libmount/src/libmount.h.in
libmount/src/libmount.sym
libmount/src/mountP.h
libmount/src/tab.c
libmount/src/tab_parse.c
libmount/src/tab_update.c
tests/expected/libmount/tabfiles-parse-fstab-full [new file with mode: 0644]
tests/ts/libmount/files/fstab.comment [new file with mode: 0644]
tests/ts/libmount/tabfiles

index 75e3bbb26dc0a94cd32f5944cc30c6afaf3b18e4..bcf250597c0fbf13433fabfc19071d0bf4e93b61 100644 (file)
@@ -62,6 +62,7 @@ void mnt_free_fs(struct libmnt_fs *fs)
        free(fs->user_optstr);
        free(fs->attrs);
        free(fs->opt_fields);
+       free(fs->comment);
 
        free(fs);
 }
@@ -1280,6 +1281,60 @@ int mnt_fs_get_attribute(struct libmnt_fs *fs, const char *name,
        return rc;
 }
 
+/**
+ * mnt_fs_get_comment:
+ * @fs: fstab/mtab/mountinfo entry pointer
+ *
+ * Returns: 0 on success, 1 when not found the @name or negative number in case of error.
+ */
+const char *mnt_fs_get_comment(struct libmnt_fs *fs)
+{
+       assert(fs);
+       if (!fs)
+               return NULL;
+       return fs->comment;
+}
+
+/**
+ * mnt_fs_set_comment:
+ * @fs: fstab entry pointer
+ * @comm: comment string
+ *
+ * Returns: 0 on success or <0 in case of error.
+ */
+int mnt_fs_set_comment(struct libmnt_fs *fs, const char *comm)
+{
+       char *p = NULL;
+
+       assert(fs);
+       if (!fs)
+               return -EINVAL;
+       if (comm) {
+               p = strdup(comm);
+               if (!p)
+                       return -ENOMEM;
+       }
+
+       free(fs->comment);
+       fs->comment = p;
+       return 0;
+}
+
+/**
+ * mnt_fs_append_comment:
+ * @fs: fstab entry pointer
+ *
+ * Returns: 0 on success or <0 in case of error.
+ */
+int mnt_fs_append_comment(struct libmnt_fs *fs, const char *comm)
+{
+       assert(fs);
+       if (!fs)
+               return -EINVAL;
+
+       return append_string(&fs->comment, comm);
+}
+
 /**
  * mnt_fs_match_target:
  * @fs: filesystem
@@ -1496,6 +1551,8 @@ int mnt_fs_print_debug(struct libmnt_fs *fs, FILE *file)
                                                minor(mnt_fs_get_devno(fs)));
        if (mnt_fs_get_tid(fs))
                fprintf(file, "tid:    %d\n", mnt_fs_get_tid(fs));
+       if (mnt_fs_get_comment(fs))
+               fprintf(file, "comment: '%s'\n", mnt_fs_get_comment(fs));
 
        return 0;
 }
index db479e186543a6949ab94511664d767a084bcaeb..74d21c7c5b78b82237ba3036cf45bd8864eed385 100644 (file)
@@ -369,6 +369,10 @@ extern off_t mnt_fs_get_size(struct libmnt_fs *fs);
 extern off_t mnt_fs_get_usedsize(struct libmnt_fs *fs);
 extern int mnt_fs_get_priority(struct libmnt_fs *fs);
 
+extern const char *mnt_fs_get_comment(struct libmnt_fs *fs);
+extern int mnt_fs_set_comment(struct libmnt_fs *fs, const char *comm);
+extern int mnt_fs_append_comment(struct libmnt_fs *fs, const char *comm);
+
 extern int mnt_fs_match_target(struct libmnt_fs *fs, const char *target,
                               struct libmnt_cache *cache);
 extern int mnt_fs_match_source(struct libmnt_fs *fs, const char *source,
@@ -408,6 +412,15 @@ extern void mnt_free_table(struct libmnt_table *tb);
 
 extern int mnt_reset_table(struct libmnt_table *tb);
 extern int mnt_table_get_nents(struct libmnt_table *tb);
+
+extern void mnt_table_enable_comments(struct libmnt_table *tb, int enable);
+extern const char *mnt_table_get_intro_comment(struct libmnt_table *tb);
+extern int mnt_table_set_intro_comment(struct libmnt_table *tb, const char *comm);
+extern int mnt_table_append_intro_comment(struct libmnt_table *tb, const char *comm);
+extern int mnt_table_set_tailing_comment(struct libmnt_table *tb, const char *comm);
+extern const char *mnt_table_get_tailing_comment(struct libmnt_table *tb);
+extern int mnt_table_append_tailing_comment(struct libmnt_table *tb, const char *comm);
+
 extern int mnt_table_set_cache(struct libmnt_table *tb, struct libmnt_cache *mpc);
 extern struct libmnt_cache *mnt_table_get_cache(struct libmnt_table *tb);
 extern int mnt_table_add_fs(struct libmnt_table *tb, struct libmnt_fs *fs);
index 2ea48398948d4af324daa1bbba0a320207843e51..f72a8f83694f2a8b6e2bc85a7c2b8110f2f96750 100644 (file)
@@ -256,3 +256,17 @@ global:
        mnt_context_find_umount_fs;
        mnt_table_find_mountpoint;
 } MOUNT_2.22;
+
+MOUNT_2.24 {
+global:
+       mnt_fs_append_comment;
+       mnt_fs_get_comment;
+       mnt_fs_set_comment;
+       mnt_table_append_intro_comment;
+       mnt_table_append_tailing_comment;
+       mnt_table_enable_comments;
+       mnt_table_get_intro_comment;
+       mnt_table_get_tailing_comment;
+       mnt_table_set_intro_comment;
+       mnt_table_set_tailing_comment;
+} MOUNT_2.23;
index c6b70e29f3b02323ea9eccf5da6ecb537a2da994..28b77d0c31aee44e2b584884a81d3519fe4a398c 100644 (file)
@@ -243,6 +243,8 @@ struct libmnt_fs {
        int             flags;          /* MNT_FS_* flags */
        pid_t           tid;            /* /proc/<tid>/mountinfo otherwise zero */
 
+       char            *comment;       /* fstab comment */
+
        void            *userdata;      /* library independent data */
 };
 
@@ -265,6 +267,9 @@ struct libmnt_fs {
 struct libmnt_table {
        int             fmt;            /* MNT_FMT_* file format */
        int             nents;          /* number of valid entries */
+       int             comms;          /* enable/disable comment parsing */
+       char            *comm_intro;    /* First comment in file */
+       char            *comm_tail;     /* Last comment in file */
 
        struct libmnt_cache *cache;             /* canonicalized paths/tags cache */
 
index b3e47bd6e791005a3f511c980c6443cb2abea4e1..5ac252ce1994ff898e869b59dcd03961e56c2d4f 100644 (file)
@@ -110,6 +110,8 @@ void mnt_free_table(struct libmnt_table *tb)
        mnt_reset_table(tb);
 
        DBG(TAB, mnt_debug_h(tb, "free"));
+       free(tb->comm_intro);
+       free(tb->comm_tail);
        free(tb);
 }
 
@@ -125,6 +127,148 @@ int mnt_table_get_nents(struct libmnt_table *tb)
        return tb ? tb->nents : 0;
 }
 
+/**
+ * mnt_table_enable_comments:
+ * @tb: pointer to tab
+ *
+ * Enables parsing of comments.
+ *
+ * The initial (intro) file comment is accessible by
+ * mnt_table_get_intro_comment(). The intro and the comment of the first fstab
+ * entry has to be separated by blank line.  The filesystem comments are
+ * accessible by mnt_fs_get_comment(). The tailing fstab comment is accessible
+ * by mnt_table_get_tailing_comment().
+ *
+ * <informalexample>
+ *  <programlisting>
+ *     #
+ *     # Intro comment
+ *     #
+ *
+ *     # this comments belongs to the first fs
+ *     LABEL=foo /mnt/foo auto defaults 1 2
+ *     # this comments belongs to the second fs
+ *     LABEL=bar /mnt/bar auto defaults 1 2 
+ *     # tailing comment
+ *  </programlisting>
+ * </informalexample>
+ */
+void mnt_table_enable_comments(struct libmnt_table *tb, int enable)
+{
+       assert(tb);
+       if (tb)
+               tb->comms = enable;
+}
+
+/**
+ * mnt_table_get_intro_comment:
+ * @tb: pointer to tab
+ *
+ * Returns: initial comment in tb
+ */
+const char *mnt_table_get_intro_comment(struct libmnt_table *tb)
+{
+       assert(tb);
+       return tb ? tb->comm_intro : NULL;
+}
+
+/**
+ * mnt_table_set_into_comment:
+ * @tb: pointer to tab
+ * @comm: comment or NULL
+ *
+ * Sets initial comment in tb.
+ *
+ * Returns: 0 on success or negative number in case of error.
+ */
+int mnt_table_set_intro_comment(struct libmnt_table *tb, const char *comm)
+{
+       char *p = NULL;
+
+       assert(tb);
+       if (!tb)
+               return -EINVAL;
+       if (comm) {
+               p = strdup(comm);
+               if (!p)
+                       return -ENOMEM;
+       }
+       free(tb->comm_intro);
+       tb->comm_intro = p;
+       return 0;
+}
+
+/**
+ * mnt_table_append_into_comment:
+ * @tb: pointer to tab
+ * @comm: comment of NULL
+ *
+ * Appends the initial comment in tb.
+ *
+ * Returns: 0 on success or negative number in case of error.
+ */
+int mnt_table_append_intro_comment(struct libmnt_table *tb, const char *comm)
+{
+       assert(tb);
+       if (!tb)
+               return -EINVAL;
+       return append_string(&tb->comm_intro, comm);
+}
+
+/**
+ * mnt_table_get_tailing_comment:
+ * @tb: pointer to tab
+ *
+ * Returns: table tailing comment
+ */
+const char *mnt_table_get_tailing_comment(struct libmnt_table *tb)
+{
+       assert(tb);
+       return tb ? tb->comm_tail : NULL;
+}
+
+/**
+ * mnt_table_set_tailing_comment
+ * @tb: pointer to tab
+ *
+ * Sets tailing comment in table.
+ *
+ * Returns: 0 on success or negative number in case of error.
+ */
+int mnt_table_set_tailing_comment(struct libmnt_table *tb, const char *comm)
+{
+       char *p = NULL;
+
+       assert(tb);
+       if (!tb)
+               return -EINVAL;
+       if (comm) {
+               p = strdup(comm);
+               if (!p)
+                       return -ENOMEM;
+       }
+       free(tb->comm_tail);
+       tb->comm_tail = p;
+       return 0;
+}
+
+/**
+ * mnt_table_append_tailing_comment:
+ * @tb: pointer to tab
+ * @comm: comment of NULL
+ *
+ * Appends to the tailing table comment.
+ *
+ * Returns: 0 on success or negative number in case of error.
+ */
+int mnt_table_append_tailing_comment(struct libmnt_table *tb, const char *comm)
+{
+       assert(tb);
+       if (!tb)
+               return -EINVAL;
+       return append_string(&tb->comm_tail, comm);
+}
+
 /**
  * mnt_table_set_cache:
  * @tb: pointer to tab
@@ -1079,7 +1223,7 @@ static int parser_errcb(struct libmnt_table *tb, const char *filename, int line)
        return 1;       /* all errors are recoverable -- this is default */
 }
 
-struct libmnt_table *create_table(const char *file)
+struct libmnt_table *create_table(const char *file, int comments)
 {
        struct libmnt_table *tb;
 
@@ -1089,6 +1233,7 @@ struct libmnt_table *create_table(const char *file)
        if (!tb)
                goto err;
 
+       mnt_table_enable_comments(tb, comments);
        mnt_table_set_parser_errcb(tb, parser_errcb);
 
        if (mnt_table_parse_file(tb, file) != 0)
@@ -1106,7 +1251,7 @@ int test_copy_fs(struct libmnt_test *ts, int argc, char *argv[])
        struct libmnt_fs *fs;
        int rc = -1;
 
-       tb = create_table(argv[1]);
+       tb = create_table(argv[1], FALSE);
        if (!tb)
                return -1;
 
@@ -1136,8 +1281,12 @@ int test_parse(struct libmnt_test *ts, int argc, char *argv[])
        struct libmnt_iter *itr = NULL;
        struct libmnt_fs *fs;
        int rc = -1;
+       int parse_comments = FALSE;
+
+       if (argc == 3 && !strcmp(argv[2], "--comments"))
+               parse_comments = TRUE;
 
-       tb = create_table(argv[1]);
+       tb = create_table(argv[1], parse_comments);
        if (!tb)
                return -1;
 
@@ -1145,8 +1294,16 @@ int test_parse(struct libmnt_test *ts, int argc, char *argv[])
        if (!itr)
                goto done;
 
+       if (mnt_table_get_intro_comment(tb))
+               fprintf(stdout, "Initial comment:\n\"%s\"\n",
+                               mnt_table_get_intro_comment(tb));
+
        while(mnt_table_next_fs(tb, itr, &fs) == 0)
                mnt_fs_print_debug(fs, stdout);
+
+       if (mnt_table_get_tailing_comment(tb))
+               fprintf(stdout, "Trailing comment:\n\"%s\"\n",
+                               mnt_table_get_tailing_comment(tb));
        rc = 0;
 done:
        mnt_free_iter(itr);
@@ -1169,7 +1326,7 @@ int test_find(struct libmnt_test *ts, int argc, char *argv[], int dr)
 
        file = argv[1], find = argv[2], what = argv[3];
 
-       tb = create_table(file);
+       tb = create_table(file, FALSE);
        if (!tb)
                goto done;
 
@@ -1213,7 +1370,7 @@ int test_find_pair(struct libmnt_test *ts, int argc, char *argv[])
        struct libmnt_cache *mpc = NULL;
        int rc = -1;
 
-       tb = create_table(argv[1]);
+       tb = create_table(argv[1], FALSE);
        if (!tb)
                return -1;
        mpc = mnt_new_cache();
@@ -1274,7 +1431,7 @@ static int test_is_mounted(struct libmnt_test *ts, int argc, char *argv[])
                return -1;
        }
 
-       fstab = create_table(argv[1]);
+       fstab = create_table(argv[1], FALSE);
        if (!fstab)
                goto done;
 
@@ -1310,7 +1467,7 @@ done:
 int main(int argc, char *argv[])
 {
        struct libmnt_test tss[] = {
-       { "--parse",    test_parse,        "<file>  parse and print tab" },
+       { "--parse",    test_parse,        "<file> [--comments] parse and print tab" },
        { "--find-forward",  test_find_fw, "<file> <source|target> <string>" },
        { "--find-backward", test_find_bw, "<file> <source|target> <string>" },
        { "--find-pair",     test_find_pair, "<file> <source> <target>" },
index e930fd841747cd584bfa0328d08b8e82e8580333..527e14ee2440b901b2fcf0a21498da19aba6d9c9 100644 (file)
@@ -344,10 +344,82 @@ static int guess_table_format(char *line)
        return MNT_FMT_FSTAB;           /* fstab, mtab or /proc/mounts */
 }
 
+static int is_comment_line(char *line)
+{
+       char *p = skip_spaces(line);
+
+       if (p && (*p == '#' || *p == '\n'))
+               return 1;
+       return 0;
+}
+
+/* returns 1 if the last line in the @str is blank */
+static int is_terminated_by_blank(const char *str)
+{
+       size_t sz = str ? strlen(str) : 0;
+       const char *p = sz ? str + (sz - 1) : NULL;
+
+       if (!sz || !p || *p != '\n')
+               return 0;               /* empty or not terminated by '\n' */
+       if (p == str)
+               return 1;               /* only '\n' */
+       p--;
+       while (p >= str && (*p == ' ' || *p == '\t'))
+               p--;
+       return *p == '\n' ? 1 : 0;
+}
+
+/*
+ * Reads the next line from the file.
+ *
+ * Returns 0 if the line is comment
+ *         1 if the line is not comment
+ *        <0 on error
+ */
+static int next_comment_line(char *buf, size_t bufsz,
+                            FILE *f, char **last, int *nlines)
+{
+       if (fgets(buf, bufsz, f) == NULL)
+               return feof(f) ? 1 : -EINVAL;
+
+       ++*nlines;
+       *last = strchr(buf, '\n');
+
+       return is_comment_line(buf) ? 0 : 1;
+}
+
+static int append_comment(struct libmnt_table *tb,
+                         struct libmnt_fs *fs,
+                         const char *comm,
+                         int eof)
+{
+       int rc, intro = mnt_table_get_nents(tb) == 0;
+
+       if (intro && is_terminated_by_blank(mnt_table_get_intro_comment(tb)))
+               intro = 0;
+
+       DBG(TAB, mnt_debug_h(tb, "appending %s comment",
+                       intro ? "intro" :
+                       eof ? "tailing" : "fs"));
+       if (intro)
+               rc = mnt_table_append_intro_comment(tb, comm);
+       else if (eof) {
+               rc = mnt_table_set_tailing_comment(tb,
+                               mnt_fs_get_comment(fs));
+               if (!rc)
+                       rc = mnt_table_append_tailing_comment(tb, comm);
+               if (!rc)
+                       rc = mnt_fs_set_comment(fs, NULL);
+       } else
+               rc = mnt_fs_append_comment(fs, comm);
+       return rc;
+}
+
 /*
  * Read and parse the next line from {fs,m}tab or mountinfo
  */
-static int mnt_table_parse_next(struct libmnt_table *tb, FILE *f, struct libmnt_fs *fs,
+static int mnt_table_parse_next(struct libmnt_table *tb, FILE *f,
+                               struct libmnt_fs *fs,
                                const char *filename, int *nlines)
 {
        char buf[BUFSIZ];
@@ -379,6 +451,26 @@ next_line:
                                goto err;
                        }
                }
+
+               /* comments parser */
+               if (tb->comms
+                   && (tb->fmt == MNT_FMT_GUESS || tb->fmt == MNT_FMT_FSTAB)
+                   && is_comment_line(buf)) {
+                       do {
+                               rc = append_comment(tb, fs, buf, feof(f));
+                               if (!rc)
+                                       rc = next_comment_line(buf,
+                                                       sizeof(buf),
+                                                       f, &s, nlines);
+                       } while (rc == 0);
+
+                       if (rc == 1 && feof(f))
+                               rc = append_comment(tb, fs, NULL, 1);
+                       if (rc < 0)
+                               return rc;
+
+               }
+
                *s = '\0';
                if (--s >= buf && *s == '\r')
                        *s = '\0';
index 1e7f32be0d567eb7a1792cac508c876346a0e3e1..b83c1dd37abc64a0318cdf581033c46714298aab 100644 (file)
@@ -408,13 +408,14 @@ err:
  */
 static int fprintf_mtab_fs(FILE *f, struct libmnt_fs *fs)
 {
-       const char *o, *src, *fstype;
+       const char *o, *src, *fstype, *comm;
        char *m1, *m2, *m3, *m4;
        int rc;
 
        assert(fs);
        assert(f);
 
+       comm = mnt_fs_get_comment(fs);
        src = mnt_fs_get_source(fs);
        fstype = mnt_fs_get_fstype(fs);
        o = mnt_fs_get_options(fs);
@@ -425,6 +426,8 @@ static int fprintf_mtab_fs(FILE *f, struct libmnt_fs *fs)
        m4 = o ? mangle(o) : "rw";
 
        if (m1 && m2 && m3 && m4) {
+               if (comm)
+                       fputs(comm, f);
                rc = fprintf(f, "%s %s %s %s %d %d\n",
                                m1, m2, m3, m4,
                                mnt_fs_get_freq(fs),
@@ -527,6 +530,10 @@ static int update_table(struct libmnt_update *upd, struct libmnt_table *tb)
                struct libmnt_fs *fs;
 
                mnt_reset_iter(&itr, MNT_ITER_FORWARD);
+
+               if (tb->comms && mnt_table_get_intro_comment(tb))
+                       fputs(mnt_table_get_intro_comment(tb), f);
+
                while(mnt_table_next_fs(tb, &itr, &fs) == 0) {
                        if (upd->userspace_only)
                                rc = fprintf_utab_fs(f, fs);
@@ -538,6 +545,8 @@ static int update_table(struct libmnt_update *upd, struct libmnt_table *tb)
                                goto leave;
                        }
                }
+               if (tb->comms && mnt_table_get_tailing_comment(tb))
+                       fputs(mnt_table_get_tailing_comment(tb), f);
 
                if (fflush(f) != 0) {
                        rc = -errno;
diff --git a/tests/expected/libmount/tabfiles-parse-fstab-full b/tests/expected/libmount/tabfiles-parse-fstab-full
new file mode 100644 (file)
index 0000000..d46416d
--- /dev/null
@@ -0,0 +1,77 @@
+Initial comment:
+"# this is a leading comment
+
+"
+------ fs:
+source: UUID=d3a8f783-df75-4dc8-9163-975a891052c0
+target: /
+fstype: ext3
+Non-data:
+"# this comments belongs to the first fs
+"
+------ fs:
+source: UUID=fef7ccb3-821c-4de8-88dc-71472be5946f
+target: /boot
+fstype: ext3
+optstr: noatime,defaults
+VFS-optstr: noatime
+freq:   1
+pass:   2
+------ fs:
+source: UUID=1f2aa318-9c34-462e-8d29-260819ffd657
+target: swap
+fstype: swap
+Non-data:
+"
+# 3rd fs comment + newline padding
+
+"
+------ fs:
+source: tmpfs
+target: /dev/shm
+fstype: tmpfs
+optstr: defaults
+------ fs:
+source: devpts
+target: /dev/pts
+fstype: devpts
+optstr: gid=5,mode=620
+FS-opstr: gid=5,mode=620
+------ fs:
+source: sysfs
+target: /sys
+fstype: sysfs
+optstr: defaults
+------ fs:
+source: proc
+target: /proc
+fstype: proc
+optstr: defaults
+------ fs:
+source: /dev/mapper/foo
+target: /home/foo
+fstype: ext4
+Non-data:
+"# this is comment
+"
+------ fs:
+source: foo.com:/mnt/share
+target: /mnt/remote
+fstype: nfs
+optstr: noauto
+user-optstr: noauto
+------ fs:
+source: //bar.com/gogogo
+target: /mnt/gogogo
+fstype: cifs
+optstr: user=SRGROUP/baby,noauto
+user-optstr: user=SRGROUP/baby,noauto
+------ fs:
+source: /dev/foo
+target: /any/foo/
+fstype: auto
+optstr: defaults
+Trailing comment:
+"
+#this is a trailing comment
+"
diff --git a/tests/ts/libmount/files/fstab.comment b/tests/ts/libmount/files/fstab.comment
new file mode 100644 (file)
index 0000000..656e663
--- /dev/null
@@ -0,0 +1,22 @@
+#
+ # this is a leading comment
+#
+
+# this comments belongs to the first fs
+UUID=d3a8f783-df75-4dc8-9163-975a891052c0 /     ext3    noatime,defaults 1 1
+UUID=fef7ccb3-821c-4de8-88dc-71472be5946f /boot ext3    noatime,defaults 1 2
+
+# 3rd fs comment + newline padding
+
+UUID=1f2aa318-9c34-462e-8d29-260819ffd657 swap  swap    defaults        0 0
+tmpfs                   /dev/shm                tmpfs   defaults        0 0
+devpts                  /dev/pts                devpts  gid=5,mode=620  0 0
+sysfs                   /sys                    sysfs   defaults        0 0
+proc                    /proc                   proc    defaults        0 0
+# this is comment
+/dev/mapper/foo                /home/foo              ext4     noatime,defaults 0 0
+foo.com:/mnt/share     /mnt/remote             nfs     noauto
+//bar.com/gogogo        /mnt/gogogo             cifs    user=SRGROUP/baby,noauto
+/dev/foo               /any/foo/               auto    defaults 0 0
+
+#this is a trailing comment
index 671c649bbece55f569d6421c160c8619f01f2fa0..c6fa360b3fdccf68cacce839be34062a57332051 100755 (executable)
@@ -17,6 +17,11 @@ ts_valgrind $TESTPROG --parse "$TS_SELF/files/fstab" &> $TS_OUTPUT
 sed -i -e 's/fs: 0x.*/fs:/g' $TS_OUTPUT
 ts_finalize_subtest
 
+ts_init_subtest "parse-fstab-full"
+ts_valgrind $TESTPROG --parse "$TS_SELF/files/fstab.comment" --comments &> $TS_OUTPUT
+sed -i -e 's/fs: 0x.*/fs:/g' $TS_OUTPUT
+ts_finalize_subtest
+
 ts_init_subtest "parse-mtab"
 ts_valgrind $TESTPROG --parse "$TS_SELF/files/mtab" &> $TS_OUTPUT
 sed -i -e 's/fs: 0x.*/fs:/g' $TS_OUTPUT