18c2ecf20Sopenharmony_ci/* SPDX-License-Identifier: GPL-2.0-or-later */ 28c2ecf20Sopenharmony_ci/* General netfs cache on cache files internal defs 38c2ecf20Sopenharmony_ci * 48c2ecf20Sopenharmony_ci * Copyright (C) 2007 Red Hat, Inc. All Rights Reserved. 58c2ecf20Sopenharmony_ci * Written by David Howells (dhowells@redhat.com) 68c2ecf20Sopenharmony_ci */ 78c2ecf20Sopenharmony_ci 88c2ecf20Sopenharmony_ci#ifdef pr_fmt 98c2ecf20Sopenharmony_ci#undef pr_fmt 108c2ecf20Sopenharmony_ci#endif 118c2ecf20Sopenharmony_ci 128c2ecf20Sopenharmony_ci#define pr_fmt(fmt) "CacheFiles: " fmt 138c2ecf20Sopenharmony_ci 148c2ecf20Sopenharmony_ci 158c2ecf20Sopenharmony_ci#include <linux/fscache-cache.h> 168c2ecf20Sopenharmony_ci#include <linux/timer.h> 178c2ecf20Sopenharmony_ci#include <linux/wait_bit.h> 188c2ecf20Sopenharmony_ci#include <linux/cred.h> 198c2ecf20Sopenharmony_ci#include <linux/workqueue.h> 208c2ecf20Sopenharmony_ci#include <linux/security.h> 218c2ecf20Sopenharmony_ci 228c2ecf20Sopenharmony_cistruct cachefiles_cache; 238c2ecf20Sopenharmony_cistruct cachefiles_object; 248c2ecf20Sopenharmony_ci 258c2ecf20Sopenharmony_ciextern unsigned cachefiles_debug; 268c2ecf20Sopenharmony_ci#define CACHEFILES_DEBUG_KENTER 1 278c2ecf20Sopenharmony_ci#define CACHEFILES_DEBUG_KLEAVE 2 288c2ecf20Sopenharmony_ci#define CACHEFILES_DEBUG_KDEBUG 4 298c2ecf20Sopenharmony_ci 308c2ecf20Sopenharmony_ci#define cachefiles_gfp (__GFP_RECLAIM | __GFP_NORETRY | __GFP_NOMEMALLOC) 318c2ecf20Sopenharmony_ci 328c2ecf20Sopenharmony_ci/* 338c2ecf20Sopenharmony_ci * node records 348c2ecf20Sopenharmony_ci */ 358c2ecf20Sopenharmony_cistruct cachefiles_object { 368c2ecf20Sopenharmony_ci struct fscache_object fscache; /* fscache handle */ 378c2ecf20Sopenharmony_ci struct cachefiles_lookup_data *lookup_data; /* cached lookup data */ 388c2ecf20Sopenharmony_ci struct dentry *dentry; /* the file/dir representing this object */ 398c2ecf20Sopenharmony_ci struct dentry *backer; /* backing file */ 408c2ecf20Sopenharmony_ci loff_t i_size; /* object size */ 418c2ecf20Sopenharmony_ci unsigned long flags; 428c2ecf20Sopenharmony_ci#define CACHEFILES_OBJECT_ACTIVE 0 /* T if marked active */ 438c2ecf20Sopenharmony_ci atomic_t usage; /* object usage count */ 448c2ecf20Sopenharmony_ci uint8_t type; /* object type */ 458c2ecf20Sopenharmony_ci uint8_t new; /* T if object new */ 468c2ecf20Sopenharmony_ci spinlock_t work_lock; 478c2ecf20Sopenharmony_ci struct rb_node active_node; /* link in active tree (dentry is key) */ 488c2ecf20Sopenharmony_ci}; 498c2ecf20Sopenharmony_ci 508c2ecf20Sopenharmony_ciextern struct kmem_cache *cachefiles_object_jar; 518c2ecf20Sopenharmony_ci 528c2ecf20Sopenharmony_ci/* 538c2ecf20Sopenharmony_ci * Cache files cache definition 548c2ecf20Sopenharmony_ci */ 558c2ecf20Sopenharmony_cistruct cachefiles_cache { 568c2ecf20Sopenharmony_ci struct fscache_cache cache; /* FS-Cache record */ 578c2ecf20Sopenharmony_ci struct vfsmount *mnt; /* mountpoint holding the cache */ 588c2ecf20Sopenharmony_ci struct dentry *graveyard; /* directory into which dead objects go */ 598c2ecf20Sopenharmony_ci struct file *cachefilesd; /* manager daemon handle */ 608c2ecf20Sopenharmony_ci const struct cred *cache_cred; /* security override for accessing cache */ 618c2ecf20Sopenharmony_ci struct mutex daemon_mutex; /* command serialisation mutex */ 628c2ecf20Sopenharmony_ci wait_queue_head_t daemon_pollwq; /* poll waitqueue for daemon */ 638c2ecf20Sopenharmony_ci struct rb_root active_nodes; /* active nodes (can't be culled) */ 648c2ecf20Sopenharmony_ci rwlock_t active_lock; /* lock for active_nodes */ 658c2ecf20Sopenharmony_ci atomic_t gravecounter; /* graveyard uniquifier */ 668c2ecf20Sopenharmony_ci atomic_t f_released; /* number of objects released lately */ 678c2ecf20Sopenharmony_ci atomic_long_t b_released; /* number of blocks released lately */ 688c2ecf20Sopenharmony_ci unsigned frun_percent; /* when to stop culling (% files) */ 698c2ecf20Sopenharmony_ci unsigned fcull_percent; /* when to start culling (% files) */ 708c2ecf20Sopenharmony_ci unsigned fstop_percent; /* when to stop allocating (% files) */ 718c2ecf20Sopenharmony_ci unsigned brun_percent; /* when to stop culling (% blocks) */ 728c2ecf20Sopenharmony_ci unsigned bcull_percent; /* when to start culling (% blocks) */ 738c2ecf20Sopenharmony_ci unsigned bstop_percent; /* when to stop allocating (% blocks) */ 748c2ecf20Sopenharmony_ci unsigned bsize; /* cache's block size */ 758c2ecf20Sopenharmony_ci unsigned bshift; /* min(ilog2(PAGE_SIZE / bsize), 0) */ 768c2ecf20Sopenharmony_ci uint64_t frun; /* when to stop culling */ 778c2ecf20Sopenharmony_ci uint64_t fcull; /* when to start culling */ 788c2ecf20Sopenharmony_ci uint64_t fstop; /* when to stop allocating */ 798c2ecf20Sopenharmony_ci sector_t brun; /* when to stop culling */ 808c2ecf20Sopenharmony_ci sector_t bcull; /* when to start culling */ 818c2ecf20Sopenharmony_ci sector_t bstop; /* when to stop allocating */ 828c2ecf20Sopenharmony_ci unsigned long flags; 838c2ecf20Sopenharmony_ci#define CACHEFILES_READY 0 /* T if cache prepared */ 848c2ecf20Sopenharmony_ci#define CACHEFILES_DEAD 1 /* T if cache dead */ 858c2ecf20Sopenharmony_ci#define CACHEFILES_CULLING 2 /* T if cull engaged */ 868c2ecf20Sopenharmony_ci#define CACHEFILES_STATE_CHANGED 3 /* T if state changed (poll trigger) */ 878c2ecf20Sopenharmony_ci char *rootdirname; /* name of cache root directory */ 888c2ecf20Sopenharmony_ci char *secctx; /* LSM security context */ 898c2ecf20Sopenharmony_ci char *tag; /* cache binding tag */ 908c2ecf20Sopenharmony_ci}; 918c2ecf20Sopenharmony_ci 928c2ecf20Sopenharmony_ci/* 938c2ecf20Sopenharmony_ci * backing file read tracking 948c2ecf20Sopenharmony_ci */ 958c2ecf20Sopenharmony_cistruct cachefiles_one_read { 968c2ecf20Sopenharmony_ci wait_queue_entry_t monitor; /* link into monitored waitqueue */ 978c2ecf20Sopenharmony_ci struct page *back_page; /* backing file page we're waiting for */ 988c2ecf20Sopenharmony_ci struct page *netfs_page; /* netfs page we're going to fill */ 998c2ecf20Sopenharmony_ci struct fscache_retrieval *op; /* retrieval op covering this */ 1008c2ecf20Sopenharmony_ci struct list_head op_link; /* link in op's todo list */ 1018c2ecf20Sopenharmony_ci}; 1028c2ecf20Sopenharmony_ci 1038c2ecf20Sopenharmony_ci/* 1048c2ecf20Sopenharmony_ci * backing file write tracking 1058c2ecf20Sopenharmony_ci */ 1068c2ecf20Sopenharmony_cistruct cachefiles_one_write { 1078c2ecf20Sopenharmony_ci struct page *netfs_page; /* netfs page to copy */ 1088c2ecf20Sopenharmony_ci struct cachefiles_object *object; 1098c2ecf20Sopenharmony_ci struct list_head obj_link; /* link in object's lists */ 1108c2ecf20Sopenharmony_ci fscache_rw_complete_t end_io_func; 1118c2ecf20Sopenharmony_ci void *context; 1128c2ecf20Sopenharmony_ci}; 1138c2ecf20Sopenharmony_ci 1148c2ecf20Sopenharmony_ci/* 1158c2ecf20Sopenharmony_ci * auxiliary data xattr buffer 1168c2ecf20Sopenharmony_ci */ 1178c2ecf20Sopenharmony_cistruct cachefiles_xattr { 1188c2ecf20Sopenharmony_ci uint16_t len; 1198c2ecf20Sopenharmony_ci uint8_t type; 1208c2ecf20Sopenharmony_ci uint8_t data[]; 1218c2ecf20Sopenharmony_ci}; 1228c2ecf20Sopenharmony_ci 1238c2ecf20Sopenharmony_ci#include <trace/events/cachefiles.h> 1248c2ecf20Sopenharmony_ci 1258c2ecf20Sopenharmony_ci/* 1268c2ecf20Sopenharmony_ci * note change of state for daemon 1278c2ecf20Sopenharmony_ci */ 1288c2ecf20Sopenharmony_cistatic inline void cachefiles_state_changed(struct cachefiles_cache *cache) 1298c2ecf20Sopenharmony_ci{ 1308c2ecf20Sopenharmony_ci set_bit(CACHEFILES_STATE_CHANGED, &cache->flags); 1318c2ecf20Sopenharmony_ci wake_up_all(&cache->daemon_pollwq); 1328c2ecf20Sopenharmony_ci} 1338c2ecf20Sopenharmony_ci 1348c2ecf20Sopenharmony_ci/* 1358c2ecf20Sopenharmony_ci * bind.c 1368c2ecf20Sopenharmony_ci */ 1378c2ecf20Sopenharmony_ciextern int cachefiles_daemon_bind(struct cachefiles_cache *cache, char *args); 1388c2ecf20Sopenharmony_ciextern void cachefiles_daemon_unbind(struct cachefiles_cache *cache); 1398c2ecf20Sopenharmony_ci 1408c2ecf20Sopenharmony_ci/* 1418c2ecf20Sopenharmony_ci * daemon.c 1428c2ecf20Sopenharmony_ci */ 1438c2ecf20Sopenharmony_ciextern const struct file_operations cachefiles_daemon_fops; 1448c2ecf20Sopenharmony_ci 1458c2ecf20Sopenharmony_ciextern int cachefiles_has_space(struct cachefiles_cache *cache, 1468c2ecf20Sopenharmony_ci unsigned fnr, unsigned bnr); 1478c2ecf20Sopenharmony_ci 1488c2ecf20Sopenharmony_ci/* 1498c2ecf20Sopenharmony_ci * interface.c 1508c2ecf20Sopenharmony_ci */ 1518c2ecf20Sopenharmony_ciextern const struct fscache_cache_ops cachefiles_cache_ops; 1528c2ecf20Sopenharmony_ci 1538c2ecf20Sopenharmony_ci/* 1548c2ecf20Sopenharmony_ci * key.c 1558c2ecf20Sopenharmony_ci */ 1568c2ecf20Sopenharmony_ciextern char *cachefiles_cook_key(const u8 *raw, int keylen, uint8_t type); 1578c2ecf20Sopenharmony_ci 1588c2ecf20Sopenharmony_ci/* 1598c2ecf20Sopenharmony_ci * namei.c 1608c2ecf20Sopenharmony_ci */ 1618c2ecf20Sopenharmony_ciextern void cachefiles_mark_object_inactive(struct cachefiles_cache *cache, 1628c2ecf20Sopenharmony_ci struct cachefiles_object *object, 1638c2ecf20Sopenharmony_ci blkcnt_t i_blocks); 1648c2ecf20Sopenharmony_ciextern int cachefiles_delete_object(struct cachefiles_cache *cache, 1658c2ecf20Sopenharmony_ci struct cachefiles_object *object); 1668c2ecf20Sopenharmony_ciextern int cachefiles_walk_to_object(struct cachefiles_object *parent, 1678c2ecf20Sopenharmony_ci struct cachefiles_object *object, 1688c2ecf20Sopenharmony_ci const char *key, 1698c2ecf20Sopenharmony_ci struct cachefiles_xattr *auxdata); 1708c2ecf20Sopenharmony_ciextern struct dentry *cachefiles_get_directory(struct cachefiles_cache *cache, 1718c2ecf20Sopenharmony_ci struct dentry *dir, 1728c2ecf20Sopenharmony_ci const char *name); 1738c2ecf20Sopenharmony_ci 1748c2ecf20Sopenharmony_ciextern int cachefiles_cull(struct cachefiles_cache *cache, struct dentry *dir, 1758c2ecf20Sopenharmony_ci char *filename); 1768c2ecf20Sopenharmony_ci 1778c2ecf20Sopenharmony_ciextern int cachefiles_check_in_use(struct cachefiles_cache *cache, 1788c2ecf20Sopenharmony_ci struct dentry *dir, char *filename); 1798c2ecf20Sopenharmony_ci 1808c2ecf20Sopenharmony_ci/* 1818c2ecf20Sopenharmony_ci * proc.c 1828c2ecf20Sopenharmony_ci */ 1838c2ecf20Sopenharmony_ci#ifdef CONFIG_CACHEFILES_HISTOGRAM 1848c2ecf20Sopenharmony_ciextern atomic_t cachefiles_lookup_histogram[HZ]; 1858c2ecf20Sopenharmony_ciextern atomic_t cachefiles_mkdir_histogram[HZ]; 1868c2ecf20Sopenharmony_ciextern atomic_t cachefiles_create_histogram[HZ]; 1878c2ecf20Sopenharmony_ci 1888c2ecf20Sopenharmony_ciextern int __init cachefiles_proc_init(void); 1898c2ecf20Sopenharmony_ciextern void cachefiles_proc_cleanup(void); 1908c2ecf20Sopenharmony_cistatic inline 1918c2ecf20Sopenharmony_civoid cachefiles_hist(atomic_t histogram[], unsigned long start_jif) 1928c2ecf20Sopenharmony_ci{ 1938c2ecf20Sopenharmony_ci unsigned long jif = jiffies - start_jif; 1948c2ecf20Sopenharmony_ci if (jif >= HZ) 1958c2ecf20Sopenharmony_ci jif = HZ - 1; 1968c2ecf20Sopenharmony_ci atomic_inc(&histogram[jif]); 1978c2ecf20Sopenharmony_ci} 1988c2ecf20Sopenharmony_ci 1998c2ecf20Sopenharmony_ci#else 2008c2ecf20Sopenharmony_ci#define cachefiles_proc_init() (0) 2018c2ecf20Sopenharmony_ci#define cachefiles_proc_cleanup() do {} while (0) 2028c2ecf20Sopenharmony_ci#define cachefiles_hist(hist, start_jif) do {} while (0) 2038c2ecf20Sopenharmony_ci#endif 2048c2ecf20Sopenharmony_ci 2058c2ecf20Sopenharmony_ci/* 2068c2ecf20Sopenharmony_ci * rdwr.c 2078c2ecf20Sopenharmony_ci */ 2088c2ecf20Sopenharmony_ciextern int cachefiles_read_or_alloc_page(struct fscache_retrieval *, 2098c2ecf20Sopenharmony_ci struct page *, gfp_t); 2108c2ecf20Sopenharmony_ciextern int cachefiles_read_or_alloc_pages(struct fscache_retrieval *, 2118c2ecf20Sopenharmony_ci struct list_head *, unsigned *, 2128c2ecf20Sopenharmony_ci gfp_t); 2138c2ecf20Sopenharmony_ciextern int cachefiles_allocate_page(struct fscache_retrieval *, struct page *, 2148c2ecf20Sopenharmony_ci gfp_t); 2158c2ecf20Sopenharmony_ciextern int cachefiles_allocate_pages(struct fscache_retrieval *, 2168c2ecf20Sopenharmony_ci struct list_head *, unsigned *, gfp_t); 2178c2ecf20Sopenharmony_ciextern int cachefiles_write_page(struct fscache_storage *, struct page *); 2188c2ecf20Sopenharmony_ciextern void cachefiles_uncache_page(struct fscache_object *, struct page *); 2198c2ecf20Sopenharmony_ci 2208c2ecf20Sopenharmony_ci/* 2218c2ecf20Sopenharmony_ci * security.c 2228c2ecf20Sopenharmony_ci */ 2238c2ecf20Sopenharmony_ciextern int cachefiles_get_security_ID(struct cachefiles_cache *cache); 2248c2ecf20Sopenharmony_ciextern int cachefiles_determine_cache_security(struct cachefiles_cache *cache, 2258c2ecf20Sopenharmony_ci struct dentry *root, 2268c2ecf20Sopenharmony_ci const struct cred **_saved_cred); 2278c2ecf20Sopenharmony_ci 2288c2ecf20Sopenharmony_cistatic inline void cachefiles_begin_secure(struct cachefiles_cache *cache, 2298c2ecf20Sopenharmony_ci const struct cred **_saved_cred) 2308c2ecf20Sopenharmony_ci{ 2318c2ecf20Sopenharmony_ci *_saved_cred = override_creds(cache->cache_cred); 2328c2ecf20Sopenharmony_ci} 2338c2ecf20Sopenharmony_ci 2348c2ecf20Sopenharmony_cistatic inline void cachefiles_end_secure(struct cachefiles_cache *cache, 2358c2ecf20Sopenharmony_ci const struct cred *saved_cred) 2368c2ecf20Sopenharmony_ci{ 2378c2ecf20Sopenharmony_ci revert_creds(saved_cred); 2388c2ecf20Sopenharmony_ci} 2398c2ecf20Sopenharmony_ci 2408c2ecf20Sopenharmony_ci/* 2418c2ecf20Sopenharmony_ci * xattr.c 2428c2ecf20Sopenharmony_ci */ 2438c2ecf20Sopenharmony_ciextern int cachefiles_check_object_type(struct cachefiles_object *object); 2448c2ecf20Sopenharmony_ciextern int cachefiles_set_object_xattr(struct cachefiles_object *object, 2458c2ecf20Sopenharmony_ci struct cachefiles_xattr *auxdata); 2468c2ecf20Sopenharmony_ciextern int cachefiles_update_object_xattr(struct cachefiles_object *object, 2478c2ecf20Sopenharmony_ci struct cachefiles_xattr *auxdata); 2488c2ecf20Sopenharmony_ciextern int cachefiles_check_auxdata(struct cachefiles_object *object); 2498c2ecf20Sopenharmony_ciextern int cachefiles_check_object_xattr(struct cachefiles_object *object, 2508c2ecf20Sopenharmony_ci struct cachefiles_xattr *auxdata); 2518c2ecf20Sopenharmony_ciextern int cachefiles_remove_object_xattr(struct cachefiles_cache *cache, 2528c2ecf20Sopenharmony_ci struct dentry *dentry); 2538c2ecf20Sopenharmony_ci 2548c2ecf20Sopenharmony_ci 2558c2ecf20Sopenharmony_ci/* 2568c2ecf20Sopenharmony_ci * error handling 2578c2ecf20Sopenharmony_ci */ 2588c2ecf20Sopenharmony_ci 2598c2ecf20Sopenharmony_ci#define cachefiles_io_error(___cache, FMT, ...) \ 2608c2ecf20Sopenharmony_cido { \ 2618c2ecf20Sopenharmony_ci pr_err("I/O Error: " FMT"\n", ##__VA_ARGS__); \ 2628c2ecf20Sopenharmony_ci fscache_io_error(&(___cache)->cache); \ 2638c2ecf20Sopenharmony_ci set_bit(CACHEFILES_DEAD, &(___cache)->flags); \ 2648c2ecf20Sopenharmony_ci} while (0) 2658c2ecf20Sopenharmony_ci 2668c2ecf20Sopenharmony_ci#define cachefiles_io_error_obj(object, FMT, ...) \ 2678c2ecf20Sopenharmony_cido { \ 2688c2ecf20Sopenharmony_ci struct cachefiles_cache *___cache; \ 2698c2ecf20Sopenharmony_ci \ 2708c2ecf20Sopenharmony_ci ___cache = container_of((object)->fscache.cache, \ 2718c2ecf20Sopenharmony_ci struct cachefiles_cache, cache); \ 2728c2ecf20Sopenharmony_ci cachefiles_io_error(___cache, FMT, ##__VA_ARGS__); \ 2738c2ecf20Sopenharmony_ci} while (0) 2748c2ecf20Sopenharmony_ci 2758c2ecf20Sopenharmony_ci 2768c2ecf20Sopenharmony_ci/* 2778c2ecf20Sopenharmony_ci * debug tracing 2788c2ecf20Sopenharmony_ci */ 2798c2ecf20Sopenharmony_ci#define dbgprintk(FMT, ...) \ 2808c2ecf20Sopenharmony_ci printk(KERN_DEBUG "[%-6.6s] "FMT"\n", current->comm, ##__VA_ARGS__) 2818c2ecf20Sopenharmony_ci 2828c2ecf20Sopenharmony_ci#define kenter(FMT, ...) dbgprintk("==> %s("FMT")", __func__, ##__VA_ARGS__) 2838c2ecf20Sopenharmony_ci#define kleave(FMT, ...) dbgprintk("<== %s()"FMT"", __func__, ##__VA_ARGS__) 2848c2ecf20Sopenharmony_ci#define kdebug(FMT, ...) dbgprintk(FMT, ##__VA_ARGS__) 2858c2ecf20Sopenharmony_ci 2868c2ecf20Sopenharmony_ci 2878c2ecf20Sopenharmony_ci#if defined(__KDEBUG) 2888c2ecf20Sopenharmony_ci#define _enter(FMT, ...) kenter(FMT, ##__VA_ARGS__) 2898c2ecf20Sopenharmony_ci#define _leave(FMT, ...) kleave(FMT, ##__VA_ARGS__) 2908c2ecf20Sopenharmony_ci#define _debug(FMT, ...) kdebug(FMT, ##__VA_ARGS__) 2918c2ecf20Sopenharmony_ci 2928c2ecf20Sopenharmony_ci#elif defined(CONFIG_CACHEFILES_DEBUG) 2938c2ecf20Sopenharmony_ci#define _enter(FMT, ...) \ 2948c2ecf20Sopenharmony_cido { \ 2958c2ecf20Sopenharmony_ci if (cachefiles_debug & CACHEFILES_DEBUG_KENTER) \ 2968c2ecf20Sopenharmony_ci kenter(FMT, ##__VA_ARGS__); \ 2978c2ecf20Sopenharmony_ci} while (0) 2988c2ecf20Sopenharmony_ci 2998c2ecf20Sopenharmony_ci#define _leave(FMT, ...) \ 3008c2ecf20Sopenharmony_cido { \ 3018c2ecf20Sopenharmony_ci if (cachefiles_debug & CACHEFILES_DEBUG_KLEAVE) \ 3028c2ecf20Sopenharmony_ci kleave(FMT, ##__VA_ARGS__); \ 3038c2ecf20Sopenharmony_ci} while (0) 3048c2ecf20Sopenharmony_ci 3058c2ecf20Sopenharmony_ci#define _debug(FMT, ...) \ 3068c2ecf20Sopenharmony_cido { \ 3078c2ecf20Sopenharmony_ci if (cachefiles_debug & CACHEFILES_DEBUG_KDEBUG) \ 3088c2ecf20Sopenharmony_ci kdebug(FMT, ##__VA_ARGS__); \ 3098c2ecf20Sopenharmony_ci} while (0) 3108c2ecf20Sopenharmony_ci 3118c2ecf20Sopenharmony_ci#else 3128c2ecf20Sopenharmony_ci#define _enter(FMT, ...) no_printk("==> %s("FMT")", __func__, ##__VA_ARGS__) 3138c2ecf20Sopenharmony_ci#define _leave(FMT, ...) no_printk("<== %s()"FMT"", __func__, ##__VA_ARGS__) 3148c2ecf20Sopenharmony_ci#define _debug(FMT, ...) no_printk(FMT, ##__VA_ARGS__) 3158c2ecf20Sopenharmony_ci#endif 3168c2ecf20Sopenharmony_ci 3178c2ecf20Sopenharmony_ci#if 1 /* defined(__KDEBUGALL) */ 3188c2ecf20Sopenharmony_ci 3198c2ecf20Sopenharmony_ci#define ASSERT(X) \ 3208c2ecf20Sopenharmony_cido { \ 3218c2ecf20Sopenharmony_ci if (unlikely(!(X))) { \ 3228c2ecf20Sopenharmony_ci pr_err("\n"); \ 3238c2ecf20Sopenharmony_ci pr_err("Assertion failed\n"); \ 3248c2ecf20Sopenharmony_ci BUG(); \ 3258c2ecf20Sopenharmony_ci } \ 3268c2ecf20Sopenharmony_ci} while (0) 3278c2ecf20Sopenharmony_ci 3288c2ecf20Sopenharmony_ci#define ASSERTCMP(X, OP, Y) \ 3298c2ecf20Sopenharmony_cido { \ 3308c2ecf20Sopenharmony_ci if (unlikely(!((X) OP (Y)))) { \ 3318c2ecf20Sopenharmony_ci pr_err("\n"); \ 3328c2ecf20Sopenharmony_ci pr_err("Assertion failed\n"); \ 3338c2ecf20Sopenharmony_ci pr_err("%lx " #OP " %lx is false\n", \ 3348c2ecf20Sopenharmony_ci (unsigned long)(X), (unsigned long)(Y)); \ 3358c2ecf20Sopenharmony_ci BUG(); \ 3368c2ecf20Sopenharmony_ci } \ 3378c2ecf20Sopenharmony_ci} while (0) 3388c2ecf20Sopenharmony_ci 3398c2ecf20Sopenharmony_ci#define ASSERTIF(C, X) \ 3408c2ecf20Sopenharmony_cido { \ 3418c2ecf20Sopenharmony_ci if (unlikely((C) && !(X))) { \ 3428c2ecf20Sopenharmony_ci pr_err("\n"); \ 3438c2ecf20Sopenharmony_ci pr_err("Assertion failed\n"); \ 3448c2ecf20Sopenharmony_ci BUG(); \ 3458c2ecf20Sopenharmony_ci } \ 3468c2ecf20Sopenharmony_ci} while (0) 3478c2ecf20Sopenharmony_ci 3488c2ecf20Sopenharmony_ci#define ASSERTIFCMP(C, X, OP, Y) \ 3498c2ecf20Sopenharmony_cido { \ 3508c2ecf20Sopenharmony_ci if (unlikely((C) && !((X) OP (Y)))) { \ 3518c2ecf20Sopenharmony_ci pr_err("\n"); \ 3528c2ecf20Sopenharmony_ci pr_err("Assertion failed\n"); \ 3538c2ecf20Sopenharmony_ci pr_err("%lx " #OP " %lx is false\n", \ 3548c2ecf20Sopenharmony_ci (unsigned long)(X), (unsigned long)(Y)); \ 3558c2ecf20Sopenharmony_ci BUG(); \ 3568c2ecf20Sopenharmony_ci } \ 3578c2ecf20Sopenharmony_ci} while (0) 3588c2ecf20Sopenharmony_ci 3598c2ecf20Sopenharmony_ci#else 3608c2ecf20Sopenharmony_ci 3618c2ecf20Sopenharmony_ci#define ASSERT(X) do {} while (0) 3628c2ecf20Sopenharmony_ci#define ASSERTCMP(X, OP, Y) do {} while (0) 3638c2ecf20Sopenharmony_ci#define ASSERTIF(C, X) do {} while (0) 3648c2ecf20Sopenharmony_ci#define ASSERTIFCMP(C, X, OP, Y) do {} while (0) 3658c2ecf20Sopenharmony_ci 3668c2ecf20Sopenharmony_ci#endif 367