[systemd-devel] [PATCH v2, ping?] tmpfiles, man: Add xattr support to tmpfiles
Lennart Poettering
lennart at poettering.net
Mon Jul 15 15:31:58 PDT 2013
On Mon, 15.07.13 15:22, Maciej Wereski (m.wereski at partner.samsung.com) wrote:
> + <varlistentry>
> + <term><varname>t</varname></term>
> + <listitem><para>Set extended
> + attributes on item. It should be
> + used with conjunction with
> other
Well, I'd use the wording "may be used", not "should be used" here...
> + if (!i->xattrs)
> + return 0;
We usually use strv_isempty() for that, which checks a bit more, but
this doesn't really matter in this case...
> + STRV_FOREACH(x, i->xattrs) {
> + value = *x;
> + name = strsep(&value, "=");
I'd really prefer if we didn't corrupt the string here. Maybe use
strv_split_quoted() here? That handles all the values for you anyway...
> + n = strlen(value);
> + if (i->type == CREATE_SYMLINK) {
> + if (lsetxattr(path, name, value, n+1, 0) < 0) {
> + log_error("Setting extended attribute %s=%s on symlink %s failed: %m", name, value, path);
> + free(value);
> + return -errno;
> + }
> + }
> + else if (setxattr(path, name, value, n+1, 0) < 0) {
> + log_error("Setting extended attribute %s=%s on %s failed: %m", name, value, path);
> + free(value);
> + return -errno;
> + }
> + free(value);
Hmm, the two if branches look like something you could combine further:
if (i->type == CREATE_SYMLINK)
r = lsetxattr(...);
else
r = setxattr(...);
And note that log_error() guarantees that errno stays untouched.
> + if (i->xattrs) {
> + r = item_set_xattrs(i, i->path);
> + if (r < 0)
> + return r;
> + }
Checking i->xattrs outside and inside the function is redundand, no?
> + for (n = 0; n < strv_length(tmp); ++n) {
> + len = strlen(tmp[n]);
> + strncpy(xattr, tmp[n], len+1);
> + p = strchr(xattr, '=');
> + if (!p) {
> + log_error("%s: Attribute has incorrect format.", i->path);
> + return -EBADMSG;
> + }
> + if (p[1] == '\"') {
> + while (true) {
> + if (!p)
> + p = tmp[n];
> + else
> + p += 2;
> + p = strchr(p, '\"');
> + if (p && xattr[p-xattr-1] != '\\')
> + break;
> + p = NULL;
> + ++n;
> + if (n == strv_length(tmp))
> + break;
> + len += strlen(tmp[n]) + 1;
> + strncat(xattr, " ", 1);
> + strncat(xattr, tmp[n], len);
> + }
> + }
> + strstrip(xattr);
> + f = i->xattrs;
> + i->xattrs = strv_append(i->xattrs, xattr);
> + if (!i->xattrs){
> + strv_free(f);
> + return log_oom();
> + }
For this stuf I'd really prefer using one of our already existing
quoting APIs, like strv_spit_quoted() or FOREACH_WORD_QUOTED or so.
> int r = 0, k;
> _cleanup_globfree_ glob_t g = {};
> @@ -674,6 +799,12 @@ static int create_item(Item *i) {
> if (r < 0)
> return r;
>
> + if (i->xattrs) {
> + r = item_set_xattrs(i, i->path);
> + if (r < 0)
> + return r;
> + }
> +
item_set_xattrs already checks i->xattrs for empty anyway, so this could
be shortened quite a bit (as above and a couple of more times)
> +static int copy_item_contents(Item *dest, const Item *src) {
Hmm, not following why you need to copy any items ever. Either you add a
new item, or you patch the existing one, but why ever copy one?
Lennart
--
Lennart Poettering - Red Hat, Inc.
More information about the systemd-devel
mailing list