fs/cachefiles/daemon.c

Source file repositories/reference/linux-study-clean/fs/cachefiles/daemon.c

File Facts

System
Linux kernel
Corpus path
fs/cachefiles/daemon.c
Extension
.c
Size
19012 bytes
Lines
828
Domain
Core OS
Bucket
VFS And Filesystem Core
Inferred role
Core OS: operation-table or driver-model contract
Status
pattern 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

const struct file_operations cachefiles_daemon_fops = {
	.owner		= THIS_MODULE,
	.open		= cachefiles_daemon_open,
	.release	= cachefiles_daemon_release,
	.read		= cachefiles_daemon_read,
	.write		= cachefiles_daemon_write,
	.poll		= cachefiles_daemon_poll,
	.llseek		= noop_llseek,
};

struct cachefiles_daemon_cmd {
	char name[8];
	int (*handler)(struct cachefiles_cache *cache, char *args);
};

static const struct cachefiles_daemon_cmd cachefiles_daemon_cmds[] = {
	{ "bind",	cachefiles_daemon_bind		},
	{ "brun",	cachefiles_daemon_brun		},
	{ "bcull",	cachefiles_daemon_bcull		},
	{ "bstop",	cachefiles_daemon_bstop		},
	{ "cull",	cachefiles_daemon_cull		},
	{ "debug",	cachefiles_daemon_debug		},
	{ "dir",	cachefiles_daemon_dir		},
	{ "frun",	cachefiles_daemon_frun		},
	{ "fcull",	cachefiles_daemon_fcull		},
	{ "fstop",	cachefiles_daemon_fstop		},
	{ "inuse",	cachefiles_daemon_inuse		},
	{ "secctx",	cachefiles_daemon_secctx	},
	{ "tag",	cachefiles_daemon_tag		},
#ifdef CONFIG_CACHEFILES_ONDEMAND
	{ "copen",	cachefiles_ondemand_copen	},
	{ "restore",	cachefiles_ondemand_restore	},
#endif
	{ "",		NULL				}
};


/*
 * Prepare a cache for caching.
 */
static int cachefiles_daemon_open(struct inode *inode, struct file *file)
{
	struct cachefiles_cache *cache;

	_enter("");

	/* only the superuser may do this */
	if (!capable(CAP_SYS_ADMIN))
		return -EPERM;

	/* the cachefiles device may only be open once at a time */
	if (xchg(&cachefiles_open, 1) == 1)
		return -EBUSY;

	/* allocate a cache record */
	cache = kzalloc_obj(struct cachefiles_cache);
	if (!cache) {
		cachefiles_open = 0;
		return -ENOMEM;
	}

	mutex_init(&cache->daemon_mutex);
	init_waitqueue_head(&cache->daemon_pollwq);
	INIT_LIST_HEAD(&cache->volumes);
	INIT_LIST_HEAD(&cache->object_list);
	spin_lock_init(&cache->object_list_lock);
	refcount_set(&cache->unbind_pincount, 1);
	xa_init_flags(&cache->reqs, XA_FLAGS_ALLOC);
	xa_init_flags(&cache->ondemand_ids, XA_FLAGS_ALLOC1);

	/* set default caching limits
	 * - limit at 1% free space and/or free files
	 * - cull below 5% free space and/or free files
	 * - cease culling above 7% free space and/or free files
	 */
	cache->frun_percent = 7;
	cache->fcull_percent = 5;
	cache->fstop_percent = 1;
	cache->brun_percent = 7;
	cache->bcull_percent = 5;
	cache->bstop_percent = 1;

	file->private_data = cache;
	cache->cachefilesd = file;
	return 0;
}

void cachefiles_flush_reqs(struct cachefiles_cache *cache)
{
	struct xarray *xa = &cache->reqs;

Annotation

Implementation Notes