xref: /openbmc/linux/fs/cachefiles/internal.h (revision ecf5a6ce)
177443f61SDavid Howells /* SPDX-License-Identifier: GPL-2.0-or-later */
277443f61SDavid Howells /* General netfs cache on cache files internal defs
377443f61SDavid Howells  *
477443f61SDavid Howells  * Copyright (C) 2021 Red Hat, Inc. All Rights Reserved.
577443f61SDavid Howells  * Written by David Howells (dhowells@redhat.com)
677443f61SDavid Howells  */
777443f61SDavid Howells 
877443f61SDavid Howells #ifdef pr_fmt
977443f61SDavid Howells #undef pr_fmt
1077443f61SDavid Howells #endif
1177443f61SDavid Howells 
1277443f61SDavid Howells #define pr_fmt(fmt) "CacheFiles: " fmt
1377443f61SDavid Howells 
1477443f61SDavid Howells 
1577443f61SDavid Howells #include <linux/fscache-cache.h>
1677443f61SDavid Howells #include <linux/cred.h>
1777443f61SDavid Howells #include <linux/security.h>
1877443f61SDavid Howells 
198390fbc4SDavid Howells struct cachefiles_cache;
208390fbc4SDavid Howells struct cachefiles_object;
218390fbc4SDavid Howells 
228390fbc4SDavid Howells /*
238390fbc4SDavid Howells  * Data file records.
248390fbc4SDavid Howells  */
258390fbc4SDavid Howells struct cachefiles_object {
268390fbc4SDavid Howells 	int				debug_id;	/* debugging ID */
278390fbc4SDavid Howells };
288390fbc4SDavid Howells 
298390fbc4SDavid Howells /*
308390fbc4SDavid Howells  * Cache files cache definition
318390fbc4SDavid Howells  */
328390fbc4SDavid Howells struct cachefiles_cache {
338390fbc4SDavid Howells 	struct vfsmount			*mnt;		/* mountpoint holding the cache */
348390fbc4SDavid Howells 	struct file			*cachefilesd;	/* manager daemon handle */
358390fbc4SDavid Howells 	const struct cred		*cache_cred;	/* security override for accessing cache */
368390fbc4SDavid Howells 	struct mutex			daemon_mutex;	/* command serialisation mutex */
378390fbc4SDavid Howells 	wait_queue_head_t		daemon_pollwq;	/* poll waitqueue for daemon */
388390fbc4SDavid Howells 	atomic_t			gravecounter;	/* graveyard uniquifier */
398390fbc4SDavid Howells 	atomic_t			f_released;	/* number of objects released lately */
408390fbc4SDavid Howells 	atomic_long_t			b_released;	/* number of blocks released lately */
418390fbc4SDavid Howells 	unsigned			frun_percent;	/* when to stop culling (% files) */
428390fbc4SDavid Howells 	unsigned			fcull_percent;	/* when to start culling (% files) */
438390fbc4SDavid Howells 	unsigned			fstop_percent;	/* when to stop allocating (% files) */
448390fbc4SDavid Howells 	unsigned			brun_percent;	/* when to stop culling (% blocks) */
458390fbc4SDavid Howells 	unsigned			bcull_percent;	/* when to start culling (% blocks) */
468390fbc4SDavid Howells 	unsigned			bstop_percent;	/* when to stop allocating (% blocks) */
478390fbc4SDavid Howells 	unsigned			bsize;		/* cache's block size */
488390fbc4SDavid Howells 	unsigned			bshift;		/* min(ilog2(PAGE_SIZE / bsize), 0) */
498390fbc4SDavid Howells 	uint64_t			frun;		/* when to stop culling */
508390fbc4SDavid Howells 	uint64_t			fcull;		/* when to start culling */
518390fbc4SDavid Howells 	uint64_t			fstop;		/* when to stop allocating */
528390fbc4SDavid Howells 	sector_t			brun;		/* when to stop culling */
538390fbc4SDavid Howells 	sector_t			bcull;		/* when to start culling */
548390fbc4SDavid Howells 	sector_t			bstop;		/* when to stop allocating */
558390fbc4SDavid Howells 	unsigned long			flags;
568390fbc4SDavid Howells #define CACHEFILES_READY		0	/* T if cache prepared */
578390fbc4SDavid Howells #define CACHEFILES_DEAD			1	/* T if cache dead */
588390fbc4SDavid Howells #define CACHEFILES_CULLING		2	/* T if cull engaged */
598390fbc4SDavid Howells #define CACHEFILES_STATE_CHANGED	3	/* T if state changed (poll trigger) */
608390fbc4SDavid Howells 	char				*rootdirname;	/* name of cache root directory */
618390fbc4SDavid Howells 	char				*secctx;	/* LSM security context */
628390fbc4SDavid Howells 	char				*tag;		/* cache binding tag */
638390fbc4SDavid Howells };
648390fbc4SDavid Howells 
65*ecf5a6ceSDavid Howells #include <trace/events/cachefiles.h>
6677443f61SDavid Howells 
6777443f61SDavid Howells /*
68a70f6526SDavid Howells  * error_inject.c
69a70f6526SDavid Howells  */
70a70f6526SDavid Howells #ifdef CONFIG_CACHEFILES_ERROR_INJECTION
71a70f6526SDavid Howells extern unsigned int cachefiles_error_injection_state;
72a70f6526SDavid Howells extern int cachefiles_register_error_injection(void);
73a70f6526SDavid Howells extern void cachefiles_unregister_error_injection(void);
74a70f6526SDavid Howells 
75a70f6526SDavid Howells #else
76a70f6526SDavid Howells #define cachefiles_error_injection_state 0
77a70f6526SDavid Howells 
78a70f6526SDavid Howells static inline int cachefiles_register_error_injection(void)
79a70f6526SDavid Howells {
80a70f6526SDavid Howells 	return 0;
81a70f6526SDavid Howells }
82a70f6526SDavid Howells 
83a70f6526SDavid Howells static inline void cachefiles_unregister_error_injection(void)
84a70f6526SDavid Howells {
85a70f6526SDavid Howells }
86a70f6526SDavid Howells #endif
87a70f6526SDavid Howells 
88a70f6526SDavid Howells 
89a70f6526SDavid Howells static inline int cachefiles_inject_read_error(void)
90a70f6526SDavid Howells {
91a70f6526SDavid Howells 	return cachefiles_error_injection_state & 2 ? -EIO : 0;
92a70f6526SDavid Howells }
93a70f6526SDavid Howells 
94a70f6526SDavid Howells static inline int cachefiles_inject_write_error(void)
95a70f6526SDavid Howells {
96a70f6526SDavid Howells 	return cachefiles_error_injection_state & 2 ? -EIO :
97a70f6526SDavid Howells 		cachefiles_error_injection_state & 1 ? -ENOSPC :
98a70f6526SDavid Howells 		0;
99a70f6526SDavid Howells }
100a70f6526SDavid Howells 
101a70f6526SDavid Howells static inline int cachefiles_inject_remove_error(void)
102a70f6526SDavid Howells {
103a70f6526SDavid Howells 	return cachefiles_error_injection_state & 2 ? -EIO : 0;
104a70f6526SDavid Howells }
105a70f6526SDavid Howells 
106a70f6526SDavid Howells 
107a70f6526SDavid Howells /*
108a70f6526SDavid Howells  * Debug tracing
10977443f61SDavid Howells  */
11077443f61SDavid Howells extern unsigned cachefiles_debug;
11177443f61SDavid Howells #define CACHEFILES_DEBUG_KENTER	1
11277443f61SDavid Howells #define CACHEFILES_DEBUG_KLEAVE	2
11377443f61SDavid Howells #define CACHEFILES_DEBUG_KDEBUG	4
11477443f61SDavid Howells 
11577443f61SDavid Howells #define dbgprintk(FMT, ...) \
11677443f61SDavid Howells 	printk(KERN_DEBUG "[%-6.6s] "FMT"\n", current->comm, ##__VA_ARGS__)
11777443f61SDavid Howells 
11877443f61SDavid Howells #define kenter(FMT, ...) dbgprintk("==> %s("FMT")", __func__, ##__VA_ARGS__)
11977443f61SDavid Howells #define kleave(FMT, ...) dbgprintk("<== %s()"FMT"", __func__, ##__VA_ARGS__)
12077443f61SDavid Howells #define kdebug(FMT, ...) dbgprintk(FMT, ##__VA_ARGS__)
12177443f61SDavid Howells 
12277443f61SDavid Howells 
12377443f61SDavid Howells #if defined(__KDEBUG)
12477443f61SDavid Howells #define _enter(FMT, ...) kenter(FMT, ##__VA_ARGS__)
12577443f61SDavid Howells #define _leave(FMT, ...) kleave(FMT, ##__VA_ARGS__)
12677443f61SDavid Howells #define _debug(FMT, ...) kdebug(FMT, ##__VA_ARGS__)
12777443f61SDavid Howells 
12877443f61SDavid Howells #elif defined(CONFIG_CACHEFILES_DEBUG)
12977443f61SDavid Howells #define _enter(FMT, ...)				\
13077443f61SDavid Howells do {							\
13177443f61SDavid Howells 	if (cachefiles_debug & CACHEFILES_DEBUG_KENTER)	\
13277443f61SDavid Howells 		kenter(FMT, ##__VA_ARGS__);		\
13377443f61SDavid Howells } while (0)
13477443f61SDavid Howells 
13577443f61SDavid Howells #define _leave(FMT, ...)				\
13677443f61SDavid Howells do {							\
13777443f61SDavid Howells 	if (cachefiles_debug & CACHEFILES_DEBUG_KLEAVE)	\
13877443f61SDavid Howells 		kleave(FMT, ##__VA_ARGS__);		\
13977443f61SDavid Howells } while (0)
14077443f61SDavid Howells 
14177443f61SDavid Howells #define _debug(FMT, ...)				\
14277443f61SDavid Howells do {							\
14377443f61SDavid Howells 	if (cachefiles_debug & CACHEFILES_DEBUG_KDEBUG)	\
14477443f61SDavid Howells 		kdebug(FMT, ##__VA_ARGS__);		\
14577443f61SDavid Howells } while (0)
14677443f61SDavid Howells 
14777443f61SDavid Howells #else
14877443f61SDavid Howells #define _enter(FMT, ...) no_printk("==> %s("FMT")", __func__, ##__VA_ARGS__)
14977443f61SDavid Howells #define _leave(FMT, ...) no_printk("<== %s()"FMT"", __func__, ##__VA_ARGS__)
15077443f61SDavid Howells #define _debug(FMT, ...) no_printk(FMT, ##__VA_ARGS__)
15177443f61SDavid Howells #endif
15277443f61SDavid Howells 
15377443f61SDavid Howells #if 1 /* defined(__KDEBUGALL) */
15477443f61SDavid Howells 
15577443f61SDavid Howells #define ASSERT(X)							\
15677443f61SDavid Howells do {									\
15777443f61SDavid Howells 	if (unlikely(!(X))) {						\
15877443f61SDavid Howells 		pr_err("\n");						\
15977443f61SDavid Howells 		pr_err("Assertion failed\n");		\
16077443f61SDavid Howells 		BUG();							\
16177443f61SDavid Howells 	}								\
16277443f61SDavid Howells } while (0)
16377443f61SDavid Howells 
16477443f61SDavid Howells #define ASSERTCMP(X, OP, Y)						\
16577443f61SDavid Howells do {									\
16677443f61SDavid Howells 	if (unlikely(!((X) OP (Y)))) {					\
16777443f61SDavid Howells 		pr_err("\n");						\
16877443f61SDavid Howells 		pr_err("Assertion failed\n");		\
16977443f61SDavid Howells 		pr_err("%lx " #OP " %lx is false\n",			\
17077443f61SDavid Howells 		       (unsigned long)(X), (unsigned long)(Y));		\
17177443f61SDavid Howells 		BUG();							\
17277443f61SDavid Howells 	}								\
17377443f61SDavid Howells } while (0)
17477443f61SDavid Howells 
17577443f61SDavid Howells #define ASSERTIF(C, X)							\
17677443f61SDavid Howells do {									\
17777443f61SDavid Howells 	if (unlikely((C) && !(X))) {					\
17877443f61SDavid Howells 		pr_err("\n");						\
17977443f61SDavid Howells 		pr_err("Assertion failed\n");		\
18077443f61SDavid Howells 		BUG();							\
18177443f61SDavid Howells 	}								\
18277443f61SDavid Howells } while (0)
18377443f61SDavid Howells 
18477443f61SDavid Howells #define ASSERTIFCMP(C, X, OP, Y)					\
18577443f61SDavid Howells do {									\
18677443f61SDavid Howells 	if (unlikely((C) && !((X) OP (Y)))) {				\
18777443f61SDavid Howells 		pr_err("\n");						\
18877443f61SDavid Howells 		pr_err("Assertion failed\n");		\
18977443f61SDavid Howells 		pr_err("%lx " #OP " %lx is false\n",			\
19077443f61SDavid Howells 		       (unsigned long)(X), (unsigned long)(Y));		\
19177443f61SDavid Howells 		BUG();							\
19277443f61SDavid Howells 	}								\
19377443f61SDavid Howells } while (0)
19477443f61SDavid Howells 
19577443f61SDavid Howells #else
19677443f61SDavid Howells 
19777443f61SDavid Howells #define ASSERT(X)			do {} while (0)
19877443f61SDavid Howells #define ASSERTCMP(X, OP, Y)		do {} while (0)
19977443f61SDavid Howells #define ASSERTIF(C, X)			do {} while (0)
20077443f61SDavid Howells #define ASSERTIFCMP(C, X, OP, Y)	do {} while (0)
20177443f61SDavid Howells 
20277443f61SDavid Howells #endif
203