1d8187177SRob Clark /* 2d8187177SRob Clark * Copyright (C) 2016 Red Hat 3d8187177SRob Clark * 4d8187177SRob Clark * Permission is hereby granted, free of charge, to any person obtaining a 5d8187177SRob Clark * copy of this software and associated documentation files (the "Software"), 6d8187177SRob Clark * to deal in the Software without restriction, including without limitation 7d8187177SRob Clark * the rights to use, copy, modify, merge, publish, distribute, sublicense, 8d8187177SRob Clark * and/or sell copies of the Software, and to permit persons to whom the 9d8187177SRob Clark * Software is furnished to do so, subject to the following conditions: 10d8187177SRob Clark * 11d8187177SRob Clark * The above copyright notice and this permission notice shall be included in 12d8187177SRob Clark * all copies or substantial portions of the Software. 13d8187177SRob Clark * 14d8187177SRob Clark * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 15d8187177SRob Clark * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 16d8187177SRob Clark * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 17d8187177SRob Clark * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR 18d8187177SRob Clark * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 19d8187177SRob Clark * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 20d8187177SRob Clark * OTHER DEALINGS IN THE SOFTWARE. 21d8187177SRob Clark * 22d8187177SRob Clark * Authors: 23d8187177SRob Clark * Rob Clark <robdclark@gmail.com> 24d8187177SRob Clark */ 25d8187177SRob Clark 26d8187177SRob Clark #ifndef DRM_PRINT_H_ 27d8187177SRob Clark #define DRM_PRINT_H_ 28d8187177SRob Clark 293c6d6e0fSJoe Perches #include <linux/compiler.h> 303c6d6e0fSJoe Perches #include <linux/printk.h> 31d8187177SRob Clark #include <linux/seq_file.h> 32d8187177SRob Clark #include <linux/device.h> 33d8187177SRob Clark 34d8187177SRob Clark /** 35d8187177SRob Clark * DOC: print 36d8187177SRob Clark * 37d8187177SRob Clark * A simple wrapper for dev_printk(), seq_printf(), etc. Allows same 38d8187177SRob Clark * debug code to be used for both debugfs and printk logging. 39d8187177SRob Clark * 40d8187177SRob Clark * For example:: 41d8187177SRob Clark * 42d8187177SRob Clark * void log_some_info(struct drm_printer *p) 43d8187177SRob Clark * { 44d8187177SRob Clark * drm_printf(p, "foo=%d\n", foo); 45d8187177SRob Clark * drm_printf(p, "bar=%d\n", bar); 46d8187177SRob Clark * } 47d8187177SRob Clark * 48d8187177SRob Clark * #ifdef CONFIG_DEBUG_FS 49d8187177SRob Clark * void debugfs_show(struct seq_file *f) 50d8187177SRob Clark * { 51d8187177SRob Clark * struct drm_printer p = drm_seq_file_printer(f); 52d8187177SRob Clark * log_some_info(&p); 53d8187177SRob Clark * } 54d8187177SRob Clark * #endif 55d8187177SRob Clark * 56d8187177SRob Clark * void some_other_function(...) 57d8187177SRob Clark * { 58d8187177SRob Clark * struct drm_printer p = drm_info_printer(drm->dev); 59d8187177SRob Clark * log_some_info(&p); 60d8187177SRob Clark * } 61d8187177SRob Clark */ 62d8187177SRob Clark 63d8187177SRob Clark /** 64d8187177SRob Clark * struct drm_printer - drm output "stream" 65d8187177SRob Clark * 66d8187177SRob Clark * Do not use struct members directly. Use drm_printer_seq_file(), 67d8187177SRob Clark * drm_printer_info(), etc to initialize. And drm_printf() for output. 68d8187177SRob Clark */ 69d8187177SRob Clark struct drm_printer { 703d387d92SDaniel Vetter /* private: */ 71d8187177SRob Clark void (*printfn)(struct drm_printer *p, struct va_format *vaf); 72d8187177SRob Clark void *arg; 733d387d92SDaniel Vetter const char *prefix; 74d8187177SRob Clark }; 75d8187177SRob Clark 76d8187177SRob Clark void __drm_printfn_seq_file(struct drm_printer *p, struct va_format *vaf); 77d8187177SRob Clark void __drm_printfn_info(struct drm_printer *p, struct va_format *vaf); 783d387d92SDaniel Vetter void __drm_printfn_debug(struct drm_printer *p, struct va_format *vaf); 79d8187177SRob Clark 803c6d6e0fSJoe Perches __printf(2, 3) 81d8187177SRob Clark void drm_printf(struct drm_printer *p, const char *f, ...); 82d8187177SRob Clark 83d8187177SRob Clark 84d8187177SRob Clark /** 85d8187177SRob Clark * drm_seq_file_printer - construct a &drm_printer that outputs to &seq_file 86ea0dd85aSDaniel Vetter * @f: the &struct seq_file to output to 87d8187177SRob Clark * 88d8187177SRob Clark * RETURNS: 89d8187177SRob Clark * The &drm_printer object 90d8187177SRob Clark */ 91d8187177SRob Clark static inline struct drm_printer drm_seq_file_printer(struct seq_file *f) 92d8187177SRob Clark { 93d8187177SRob Clark struct drm_printer p = { 94d8187177SRob Clark .printfn = __drm_printfn_seq_file, 95d8187177SRob Clark .arg = f, 96d8187177SRob Clark }; 97d8187177SRob Clark return p; 98d8187177SRob Clark } 99d8187177SRob Clark 100d8187177SRob Clark /** 101d8187177SRob Clark * drm_info_printer - construct a &drm_printer that outputs to dev_printk() 102ea0dd85aSDaniel Vetter * @dev: the &struct device pointer 103d8187177SRob Clark * 104d8187177SRob Clark * RETURNS: 105d8187177SRob Clark * The &drm_printer object 106d8187177SRob Clark */ 107d8187177SRob Clark static inline struct drm_printer drm_info_printer(struct device *dev) 108d8187177SRob Clark { 109d8187177SRob Clark struct drm_printer p = { 110d8187177SRob Clark .printfn = __drm_printfn_info, 111d8187177SRob Clark .arg = dev, 112d8187177SRob Clark }; 113d8187177SRob Clark return p; 114d8187177SRob Clark } 115d8187177SRob Clark 1163d387d92SDaniel Vetter /** 1173d387d92SDaniel Vetter * drm_debug_printer - construct a &drm_printer that outputs to pr_debug() 1183d387d92SDaniel Vetter * @prefix: debug output prefix 1193d387d92SDaniel Vetter * 1203d387d92SDaniel Vetter * RETURNS: 1213d387d92SDaniel Vetter * The &drm_printer object 1223d387d92SDaniel Vetter */ 1233d387d92SDaniel Vetter static inline struct drm_printer drm_debug_printer(const char *prefix) 1243d387d92SDaniel Vetter { 1253d387d92SDaniel Vetter struct drm_printer p = { 1263d387d92SDaniel Vetter .printfn = __drm_printfn_debug, 1273d387d92SDaniel Vetter .prefix = prefix 1283d387d92SDaniel Vetter }; 1293d387d92SDaniel Vetter return p; 1303d387d92SDaniel Vetter } 13102c9656bSHaneen Mohammed 13202c9656bSHaneen Mohammed /* 13302c9656bSHaneen Mohammed * The following categories are defined: 13402c9656bSHaneen Mohammed * 13502c9656bSHaneen Mohammed * CORE: Used in the generic drm code: drm_ioctl.c, drm_mm.c, drm_memory.c, ... 13602c9656bSHaneen Mohammed * This is the category used by the DRM_DEBUG() macro. 13702c9656bSHaneen Mohammed * 13802c9656bSHaneen Mohammed * DRIVER: Used in the vendor specific part of the driver: i915, radeon, ... 13902c9656bSHaneen Mohammed * This is the category used by the DRM_DEBUG_DRIVER() macro. 14002c9656bSHaneen Mohammed * 14102c9656bSHaneen Mohammed * KMS: used in the modesetting code. 14202c9656bSHaneen Mohammed * This is the category used by the DRM_DEBUG_KMS() macro. 14302c9656bSHaneen Mohammed * 14402c9656bSHaneen Mohammed * PRIME: used in the prime code. 14502c9656bSHaneen Mohammed * This is the category used by the DRM_DEBUG_PRIME() macro. 14602c9656bSHaneen Mohammed * 14702c9656bSHaneen Mohammed * ATOMIC: used in the atomic code. 14802c9656bSHaneen Mohammed * This is the category used by the DRM_DEBUG_ATOMIC() macro. 14902c9656bSHaneen Mohammed * 15002c9656bSHaneen Mohammed * VBL: used for verbose debug message in the vblank code 15102c9656bSHaneen Mohammed * This is the category used by the DRM_DEBUG_VBL() macro. 15202c9656bSHaneen Mohammed * 15302c9656bSHaneen Mohammed * Enabling verbose debug messages is done through the drm.debug parameter, 15402c9656bSHaneen Mohammed * each category being enabled by a bit. 15502c9656bSHaneen Mohammed * 15602c9656bSHaneen Mohammed * drm.debug=0x1 will enable CORE messages 15702c9656bSHaneen Mohammed * drm.debug=0x2 will enable DRIVER messages 15802c9656bSHaneen Mohammed * drm.debug=0x3 will enable CORE and DRIVER messages 15902c9656bSHaneen Mohammed * ... 16002c9656bSHaneen Mohammed * drm.debug=0x3f will enable all messages 16102c9656bSHaneen Mohammed * 16202c9656bSHaneen Mohammed * An interesting feature is that it's possible to enable verbose logging at 16302c9656bSHaneen Mohammed * run-time by echoing the debug value in its sysfs node: 16402c9656bSHaneen Mohammed * # echo 0xf > /sys/module/drm/parameters/debug 16502c9656bSHaneen Mohammed */ 16602c9656bSHaneen Mohammed #define DRM_UT_NONE 0x00 16702c9656bSHaneen Mohammed #define DRM_UT_CORE 0x01 16802c9656bSHaneen Mohammed #define DRM_UT_DRIVER 0x02 16902c9656bSHaneen Mohammed #define DRM_UT_KMS 0x04 17002c9656bSHaneen Mohammed #define DRM_UT_PRIME 0x08 17102c9656bSHaneen Mohammed #define DRM_UT_ATOMIC 0x10 17202c9656bSHaneen Mohammed #define DRM_UT_VBL 0x20 17302c9656bSHaneen Mohammed #define DRM_UT_STATE 0x40 17402c9656bSHaneen Mohammed 17502c9656bSHaneen Mohammed __printf(6, 7) 17602c9656bSHaneen Mohammed void drm_dev_printk(const struct device *dev, const char *level, 17702c9656bSHaneen Mohammed unsigned int category, const char *function_name, 17802c9656bSHaneen Mohammed const char *prefix, const char *format, ...); 17902c9656bSHaneen Mohammed __printf(3, 4) 18002c9656bSHaneen Mohammed void drm_printk(const char *level, unsigned int category, 18102c9656bSHaneen Mohammed const char *format, ...); 182091756bbSHaneen Mohammed 183091756bbSHaneen Mohammed /* Macros to make printk easier */ 18402c9656bSHaneen Mohammed 18502c9656bSHaneen Mohammed #define _DRM_PRINTK(once, level, fmt, ...) \ 18602c9656bSHaneen Mohammed do { \ 18702c9656bSHaneen Mohammed printk##once(KERN_##level "[" DRM_NAME "] " fmt, \ 18802c9656bSHaneen Mohammed ##__VA_ARGS__); \ 18902c9656bSHaneen Mohammed } while (0) 19002c9656bSHaneen Mohammed 19102c9656bSHaneen Mohammed #define DRM_INFO(fmt, ...) \ 19202c9656bSHaneen Mohammed _DRM_PRINTK(, INFO, fmt, ##__VA_ARGS__) 19302c9656bSHaneen Mohammed #define DRM_NOTE(fmt, ...) \ 19402c9656bSHaneen Mohammed _DRM_PRINTK(, NOTICE, fmt, ##__VA_ARGS__) 19502c9656bSHaneen Mohammed #define DRM_WARN(fmt, ...) \ 19602c9656bSHaneen Mohammed _DRM_PRINTK(, WARNING, fmt, ##__VA_ARGS__) 19702c9656bSHaneen Mohammed 19802c9656bSHaneen Mohammed #define DRM_INFO_ONCE(fmt, ...) \ 19902c9656bSHaneen Mohammed _DRM_PRINTK(_once, INFO, fmt, ##__VA_ARGS__) 20002c9656bSHaneen Mohammed #define DRM_NOTE_ONCE(fmt, ...) \ 20102c9656bSHaneen Mohammed _DRM_PRINTK(_once, NOTICE, fmt, ##__VA_ARGS__) 20202c9656bSHaneen Mohammed #define DRM_WARN_ONCE(fmt, ...) \ 20302c9656bSHaneen Mohammed _DRM_PRINTK(_once, WARNING, fmt, ##__VA_ARGS__) 20402c9656bSHaneen Mohammed 20502c9656bSHaneen Mohammed /** 20602c9656bSHaneen Mohammed * Error output. 20702c9656bSHaneen Mohammed * 208091756bbSHaneen Mohammed * @dev: device pointer 209091756bbSHaneen Mohammed * @fmt: printf() like format string. 21002c9656bSHaneen Mohammed */ 21102c9656bSHaneen Mohammed #define DRM_DEV_ERROR(dev, fmt, ...) \ 21202c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_ERR, DRM_UT_NONE, __func__, " *ERROR*",\ 21302c9656bSHaneen Mohammed fmt, ##__VA_ARGS__) 21402c9656bSHaneen Mohammed #define DRM_ERROR(fmt, ...) \ 21502c9656bSHaneen Mohammed drm_printk(KERN_ERR, DRM_UT_NONE, fmt, ##__VA_ARGS__) 21602c9656bSHaneen Mohammed 21702c9656bSHaneen Mohammed /** 21802c9656bSHaneen Mohammed * Rate limited error output. Like DRM_ERROR() but won't flood the log. 21902c9656bSHaneen Mohammed * 220091756bbSHaneen Mohammed * @dev: device pointer 221091756bbSHaneen Mohammed * @fmt: printf() like format string. 22202c9656bSHaneen Mohammed */ 22302c9656bSHaneen Mohammed #define DRM_DEV_ERROR_RATELIMITED(dev, fmt, ...) \ 22402c9656bSHaneen Mohammed ({ \ 22502c9656bSHaneen Mohammed static DEFINE_RATELIMIT_STATE(_rs, \ 22602c9656bSHaneen Mohammed DEFAULT_RATELIMIT_INTERVAL, \ 22702c9656bSHaneen Mohammed DEFAULT_RATELIMIT_BURST); \ 22802c9656bSHaneen Mohammed \ 22902c9656bSHaneen Mohammed if (__ratelimit(&_rs)) \ 23002c9656bSHaneen Mohammed DRM_DEV_ERROR(dev, fmt, ##__VA_ARGS__); \ 23102c9656bSHaneen Mohammed }) 23202c9656bSHaneen Mohammed #define DRM_ERROR_RATELIMITED(fmt, ...) \ 23302c9656bSHaneen Mohammed DRM_DEV_ERROR_RATELIMITED(NULL, fmt, ##__VA_ARGS__) 23402c9656bSHaneen Mohammed 23502c9656bSHaneen Mohammed #define DRM_DEV_INFO(dev, fmt, ...) \ 23602c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_INFO, DRM_UT_NONE, __func__, "", fmt, \ 23702c9656bSHaneen Mohammed ##__VA_ARGS__) 23802c9656bSHaneen Mohammed 23902c9656bSHaneen Mohammed #define DRM_DEV_INFO_ONCE(dev, fmt, ...) \ 24002c9656bSHaneen Mohammed ({ \ 24102c9656bSHaneen Mohammed static bool __print_once __read_mostly; \ 24202c9656bSHaneen Mohammed if (!__print_once) { \ 24302c9656bSHaneen Mohammed __print_once = true; \ 24402c9656bSHaneen Mohammed DRM_DEV_INFO(dev, fmt, ##__VA_ARGS__); \ 24502c9656bSHaneen Mohammed } \ 24602c9656bSHaneen Mohammed }) 24702c9656bSHaneen Mohammed 24802c9656bSHaneen Mohammed /** 24902c9656bSHaneen Mohammed * Debug output. 25002c9656bSHaneen Mohammed * 251091756bbSHaneen Mohammed * @dev: device pointer 252091756bbSHaneen Mohammed * @fmt: printf() like format string. 25302c9656bSHaneen Mohammed */ 25402c9656bSHaneen Mohammed #define DRM_DEV_DEBUG(dev, fmt, args...) \ 25502c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_DEBUG, DRM_UT_CORE, __func__, "", fmt, \ 25602c9656bSHaneen Mohammed ##args) 25702c9656bSHaneen Mohammed #define DRM_DEBUG(fmt, ...) \ 25802c9656bSHaneen Mohammed drm_printk(KERN_DEBUG, DRM_UT_CORE, fmt, ##__VA_ARGS__) 25902c9656bSHaneen Mohammed 26002c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_DRIVER(dev, fmt, args...) \ 26102c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_DEBUG, DRM_UT_DRIVER, __func__, "", \ 26202c9656bSHaneen Mohammed fmt, ##args) 26302c9656bSHaneen Mohammed #define DRM_DEBUG_DRIVER(fmt, ...) \ 26402c9656bSHaneen Mohammed drm_printk(KERN_DEBUG, DRM_UT_DRIVER, fmt, ##__VA_ARGS__) 26502c9656bSHaneen Mohammed 26602c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_KMS(dev, fmt, args...) \ 26702c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_DEBUG, DRM_UT_KMS, __func__, "", fmt, \ 26802c9656bSHaneen Mohammed ##args) 26902c9656bSHaneen Mohammed #define DRM_DEBUG_KMS(fmt, ...) \ 27002c9656bSHaneen Mohammed drm_printk(KERN_DEBUG, DRM_UT_KMS, fmt, ##__VA_ARGS__) 27102c9656bSHaneen Mohammed 27202c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_PRIME(dev, fmt, args...) \ 27302c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_DEBUG, DRM_UT_PRIME, __func__, "", \ 27402c9656bSHaneen Mohammed fmt, ##args) 27502c9656bSHaneen Mohammed #define DRM_DEBUG_PRIME(fmt, ...) \ 27602c9656bSHaneen Mohammed drm_printk(KERN_DEBUG, DRM_UT_PRIME, fmt, ##__VA_ARGS__) 27702c9656bSHaneen Mohammed 27802c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_ATOMIC(dev, fmt, args...) \ 27902c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_DEBUG, DRM_UT_ATOMIC, __func__, "", \ 28002c9656bSHaneen Mohammed fmt, ##args) 28102c9656bSHaneen Mohammed #define DRM_DEBUG_ATOMIC(fmt, ...) \ 28202c9656bSHaneen Mohammed drm_printk(KERN_DEBUG, DRM_UT_ATOMIC, fmt, ##__VA_ARGS__) 28302c9656bSHaneen Mohammed 28402c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_VBL(dev, fmt, args...) \ 28502c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_DEBUG, DRM_UT_VBL, __func__, "", fmt, \ 28602c9656bSHaneen Mohammed ##args) 28702c9656bSHaneen Mohammed #define DRM_DEBUG_VBL(fmt, ...) \ 28802c9656bSHaneen Mohammed drm_printk(KERN_DEBUG, DRM_UT_VBL, fmt, ##__VA_ARGS__) 28902c9656bSHaneen Mohammed 29002c9656bSHaneen Mohammed #define _DRM_DEV_DEFINE_DEBUG_RATELIMITED(dev, level, fmt, args...) \ 29102c9656bSHaneen Mohammed ({ \ 29202c9656bSHaneen Mohammed static DEFINE_RATELIMIT_STATE(_rs, \ 29302c9656bSHaneen Mohammed DEFAULT_RATELIMIT_INTERVAL, \ 29402c9656bSHaneen Mohammed DEFAULT_RATELIMIT_BURST); \ 29502c9656bSHaneen Mohammed if (__ratelimit(&_rs)) \ 29602c9656bSHaneen Mohammed drm_dev_printk(dev, KERN_DEBUG, DRM_UT_ ## level, \ 29702c9656bSHaneen Mohammed __func__, "", fmt, ##args); \ 29802c9656bSHaneen Mohammed }) 29902c9656bSHaneen Mohammed 30002c9656bSHaneen Mohammed /** 30102c9656bSHaneen Mohammed * Rate limited debug output. Like DRM_DEBUG() but won't flood the log. 30202c9656bSHaneen Mohammed * 303091756bbSHaneen Mohammed * @dev: device pointer 304091756bbSHaneen Mohammed * @fmt: printf() like format string. 30502c9656bSHaneen Mohammed */ 30602c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_RATELIMITED(dev, fmt, args...) \ 30702c9656bSHaneen Mohammed DEV__DRM_DEFINE_DEBUG_RATELIMITED(dev, CORE, fmt, ##args) 30802c9656bSHaneen Mohammed #define DRM_DEBUG_RATELIMITED(fmt, args...) \ 30902c9656bSHaneen Mohammed DRM_DEV_DEBUG_RATELIMITED(NULL, fmt, ##args) 31002c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_DRIVER_RATELIMITED(dev, fmt, args...) \ 31102c9656bSHaneen Mohammed _DRM_DEV_DEFINE_DEBUG_RATELIMITED(dev, DRIVER, fmt, ##args) 31202c9656bSHaneen Mohammed #define DRM_DEBUG_DRIVER_RATELIMITED(fmt, args...) \ 31302c9656bSHaneen Mohammed DRM_DEV_DEBUG_DRIVER_RATELIMITED(NULL, fmt, ##args) 31402c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_KMS_RATELIMITED(dev, fmt, args...) \ 31502c9656bSHaneen Mohammed _DRM_DEV_DEFINE_DEBUG_RATELIMITED(dev, KMS, fmt, ##args) 31602c9656bSHaneen Mohammed #define DRM_DEBUG_KMS_RATELIMITED(fmt, args...) \ 31702c9656bSHaneen Mohammed DRM_DEV_DEBUG_KMS_RATELIMITED(NULL, fmt, ##args) 31802c9656bSHaneen Mohammed #define DRM_DEV_DEBUG_PRIME_RATELIMITED(dev, fmt, args...) \ 31902c9656bSHaneen Mohammed _DRM_DEV_DEFINE_DEBUG_RATELIMITED(dev, PRIME, fmt, ##args) 32002c9656bSHaneen Mohammed #define DRM_DEBUG_PRIME_RATELIMITED(fmt, args...) \ 32102c9656bSHaneen Mohammed DRM_DEV_DEBUG_PRIME_RATELIMITED(NULL, fmt, ##args) 32202c9656bSHaneen Mohammed 323d8187177SRob Clark #endif /* DRM_PRINT_H_ */ 324