From: Karel Zak Date: Thu, 19 Oct 2023 11:42:08 +0000 (+0200) Subject: findmnt: use zero to separate lines in multi-line cells X-Git-Tag: v2.40-rc1~184 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=295bbcf676ee958727970174e421618b9d473398;p=thirdparty%2Futil-linux.git findmnt: use zero to separate lines in multi-line cells Fixes: https://github.com/util-linux/util-linux/issues/2533 Signed-off-by: Karel Zak --- diff --git a/misc-utils/findmnt.8.adoc b/misc-utils/findmnt.8.adoc index 0cb7f0e6c0..72a1ecf2a2 100644 --- a/misc-utils/findmnt.8.adoc +++ b/misc-utils/findmnt.8.adoc @@ -105,6 +105,8 @@ Output almost all available columns. The columns that require *--poll* are not i *-P*, *--pairs*:: Produce output in the form of key="value" pairs. All potentially unsafe value characters are hex-escaped (\x). See also option *--shell*. ++ +Note that SOURCES column, use multi-line cells. In these cases, the column use an array-like formatting in the output, for example *name=("aaa" "bbb" "ccc")*. *-p*, *--poll*[_=list_]:: Monitor changes in the _/proc/self/mountinfo_ file. Supported actions are: mount, umount, remount and move. More than one action may be specified in a comma-separated list. All actions are monitored by default. @@ -131,6 +133,8 @@ Print recursively all submounts for the selected filesystems. The restrictions d *-r*, *--raw*:: Use raw output format. All potentially unsafe characters are hex-escaped (\x). ++ +Note that column SOURCES, use multi-line cells. In these cases, the column may produce more strings on the same line. *--real*:: Print only real filesystems. diff --git a/misc-utils/findmnt.c b/misc-utils/findmnt.c index cb091201b5..6865d96af1 100644 --- a/misc-utils/findmnt.c +++ b/misc-utils/findmnt.c @@ -511,7 +511,7 @@ static char *get_vfs_attr(struct libmnt_fs *fs, int sizetype) /* reads sources from libmount/libblkid */ -static char *get_data_col_sources(struct libmnt_fs *fs, int evaluate) +static char *get_data_col_sources(struct libmnt_fs *fs, int evaluate, size_t *datasiz) { const char *tag = NULL, *p = NULL; int i = 0; @@ -565,14 +565,14 @@ static char *get_data_col_sources(struct libmnt_fs *fs, int evaluate) if (!dev) continue; if (i != 0) - ul_buffer_append_data(&buf, "\n", 1); + ul_buffer_append_data(&buf, "\0", 1); ul_buffer_append_string(&buf, blkid_dev_devname(dev)); i++; } blkid_dev_iterate_end(iter); free(val); - return ul_buffer_get_data(&buf, NULL, NULL); + return ul_buffer_get_data(&buf, datasiz, NULL); nothing: free(val); @@ -581,7 +581,7 @@ nothing: /* reads FS data from libmount */ -static char *get_data(struct libmnt_fs *fs, int num) +static char *get_data(struct libmnt_fs *fs, int num, size_t *datasiz) { char *str = NULL; int col_id = get_column_id(num); @@ -589,7 +589,7 @@ static char *get_data(struct libmnt_fs *fs, int num) switch (col_id) { case COL_SOURCES: /* print all devices with the same tag (LABEL, UUID) */ - str = get_data_col_sources(fs, flags & FL_EVALUATE); + str = get_data_col_sources(fs, flags & FL_EVALUATE, datasiz); if (str) break; @@ -730,7 +730,8 @@ static char *get_data(struct libmnt_fs *fs, int num) static char *get_tabdiff_data(struct libmnt_fs *old_fs, struct libmnt_fs *new_fs, int change, - int num) + int num, + size_t *datasiz) { char *str = NULL; @@ -769,14 +770,30 @@ static char *get_tabdiff_data(struct libmnt_fs *old_fs, break; default: if (new_fs) - str = get_data(new_fs, num); + str = get_data(new_fs, num, datasiz); else - str = get_data(old_fs, num); + str = get_data(old_fs, num, datasiz); break; } return str; } +static void set_line_data(struct libscols_line *ln, size_t i, char *data, size_t datasiz) +{ + int rc; + struct libscols_cell *ce; + + ce = scols_line_get_cell(ln, i); + if (!ce) + return; + if (datasiz) + rc = scols_cell_refer_memory(ce, data, datasiz); + else + rc = scols_cell_refer_data(ce, data); + if (rc) + err(EXIT_FAILURE, _("failed to add output data")); +} + /* adds one line to the output @tab */ static struct libscols_line *add_line(struct libscols_table *table, struct libmnt_fs *fs, struct libscols_line *parent) @@ -788,8 +805,11 @@ static struct libscols_line *add_line(struct libscols_table *table, struct libmn err(EXIT_FAILURE, _("failed to allocate output line")); for (i = 0; i < ncolumns; i++) { - if (scols_line_refer_data(line, i, get_data(fs, i))) - err(EXIT_FAILURE, _("failed to add output data")); + size_t datasiz = 0; + char *data = get_data(fs, i, &datasiz); + + if (data) + set_line_data(line, i, data, datasiz); } scols_line_set_userdata(line, fs); @@ -806,9 +826,11 @@ static struct libscols_line *add_tabdiff_line(struct libscols_table *table, stru err(EXIT_FAILURE, _("failed to allocate output line")); for (i = 0; i < ncolumns; i++) { - if (scols_line_refer_data(line, i, - get_tabdiff_data(old_fs, new_fs, change, i))) - err(EXIT_FAILURE, _("failed to add output data")); + size_t datasiz = 0; + char *data = get_tabdiff_data(old_fs, new_fs, change, i, &datasiz); + + if (data) + set_line_data(line, i, data, datasiz); } return line; @@ -1793,13 +1815,11 @@ int main(int argc, char *argv[]) goto leave; } /* multi-line cells (now used for SOURCES) */ - if (fl & SCOLS_FL_WRAP) { + if (fl & SCOLS_FL_WRAP) scols_column_set_wrapfunc(cl, - scols_wrapnl_chunksize, - scols_wrapnl_nextchunk, + NULL, + scols_wrapzero_nextchunk, NULL); - scols_column_set_safechars(cl, "\n"); - } if (flags & FL_JSON) { switch (id) { case COL_SIZE: