fs/ceph/xattr.c

Source file repositories/reference/linux-study-clean/fs/ceph/xattr.c

File Facts

System
Linux kernel
Corpus path
fs/ceph/xattr.c
Extension
.c
Size
39353 bytes
Lines
1486
Domain
Core OS
Bucket
VFS And Filesystem Core
Inferred role
Core OS: implementation source
Status
source implementation candidate

Why This File Exists

Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.

Dependency Surface

Detected Declarations

Annotated Snippet

struct ceph_vxattr {
	char *name;
	size_t name_size;	/* strlen(name) + 1 (for '\0') */
	ssize_t (*getxattr_cb)(struct ceph_inode_info *ci, char *val,
			       size_t size);
	bool (*exists_cb)(struct ceph_inode_info *ci);
	unsigned int flags;
};

#define VXATTR_FLAG_READONLY		(1<<0)
#define VXATTR_FLAG_HIDDEN		(1<<1)
#define VXATTR_FLAG_RSTAT		(1<<2)
#define VXATTR_FLAG_DIRSTAT		(1<<3)

/* layouts */

static bool ceph_vxattrcb_layout_exists(struct ceph_inode_info *ci)
{
	struct ceph_file_layout *fl = &ci->i_layout;
	return (fl->stripe_unit > 0 || fl->stripe_count > 0 ||
		fl->object_size > 0 || fl->pool_id >= 0 ||
		rcu_dereference_raw(fl->pool_ns) != NULL);
}

static ssize_t ceph_vxattrcb_layout(struct ceph_inode_info *ci, char *val,
				    size_t size)
{
	struct ceph_fs_client *fsc = ceph_sb_to_fs_client(ci->netfs.inode.i_sb);
	struct ceph_client *cl = fsc->client;
	struct ceph_osd_client *osdc = &fsc->client->osdc;
	struct ceph_string *pool_ns;
	s64 pool = ci->i_layout.pool_id;
	const char *pool_name;
	const char *ns_field = " pool_namespace=";
	char buf[128];
	size_t len, total_len = 0;
	ssize_t ret;

	pool_ns = ceph_try_get_string(ci->i_layout.pool_ns);

	doutc(cl, "%p\n", &ci->netfs.inode);
	down_read(&osdc->lock);
	pool_name = ceph_pg_pool_name_by_id(osdc->osdmap, pool);
	if (pool_name) {
		len = snprintf(buf, sizeof(buf),
		"stripe_unit=%u stripe_count=%u object_size=%u pool=",
		ci->i_layout.stripe_unit, ci->i_layout.stripe_count,
	        ci->i_layout.object_size);
		total_len = len + strlen(pool_name);
	} else {
		len = snprintf(buf, sizeof(buf),
		"stripe_unit=%u stripe_count=%u object_size=%u pool=%lld",
		ci->i_layout.stripe_unit, ci->i_layout.stripe_count,
		ci->i_layout.object_size, pool);
		total_len = len;
	}

	if (pool_ns)
		total_len += strlen(ns_field) + pool_ns->len;

	ret = total_len;
	if (size >= total_len) {
		memcpy(val, buf, len);
		ret = len;
		if (pool_name) {
			len = strlen(pool_name);
			memcpy(val + ret, pool_name, len);
			ret += len;
		}
		if (pool_ns) {
			len = strlen(ns_field);
			memcpy(val + ret, ns_field, len);
			ret += len;
			memcpy(val + ret, pool_ns->str, pool_ns->len);
			ret += pool_ns->len;
		}
	}
	up_read(&osdc->lock);
	ceph_put_string(pool_ns);
	return ret;
}

/*
 * The convention with strings in xattrs is that they should not be NULL
 * terminated, since we're returning the length with them. snprintf always
 * NULL terminates however, so call it on a temporary buffer and then memcpy
 * the result into place.
 */
static __printf(3, 4)
int ceph_fmt_xattr(char *val, size_t size, const char *fmt, ...)

Annotation

Implementation Notes