39
39
@protocol DDLogFormatter;
40
40
41
41
/* *
42
- * Define our big multiline macros so all the other macros will be easy to read.
42
+ * This is the single macro that all other macros below compile into.
43
+ * This big multiline macro makes all the other macros easier to read.
43
44
**/
44
45
45
- #define LOG_MACRO (isAsynchronous, lvl, flg, ctx, fnct, frmt, ...) \
46
- [DDLog log: isAsynchronous \
47
- level: lvl \
48
- flag: flg \
49
- context: ctx \
50
- file: __FILE__ \
51
- function: fnct \
52
- line: __LINE__ \
53
- tag: nil \
46
+ #define LOG_MACRO (isAsynchronous, lvl, flg, ctx, atag, fnct, frmt, ...) \
47
+ [DDLog log: isAsynchronous \
48
+ level: lvl \
49
+ flag: flg \
50
+ context: ctx \
51
+ file: __FILE__ \
52
+ function: fnct \
53
+ line: __LINE__ \
54
+ tag: atag \
54
55
format: (frmt), ##__VA_ARGS__]
55
56
57
+ /* *
58
+ * Define the Objective-C and C versions of the macro.
59
+ * These automatically inject the proper function name for either an objective-c method or c function.
60
+ *
61
+ * We also define shorthand versions for asynchronous and synchronous logging.
62
+ **/
56
63
57
64
#define LOG_OBJC_MACRO (async, lvl, flg, ctx, frmt, ...) \
58
- LOG_MACRO (async, lvl, flg, ctx, sel_getName (_cmd), frmt, ##__VA_ARGS__)
65
+ LOG_MACRO (async, lvl, flg, ctx, nil , sel_getName (_cmd), frmt, ##__VA_ARGS__)
59
66
60
67
#define LOG_C_MACRO (async, lvl, flg, ctx, frmt, ...) \
61
- LOG_MACRO (async, lvl, flg, ctx, __FUNCTION__, frmt, ##__VA_ARGS__)
68
+ LOG_MACRO (async, lvl, flg, ctx, nil , __FUNCTION__, frmt, ##__VA_ARGS__)
62
69
63
70
#define SYNC_LOG_OBJC_MACRO (lvl, flg, ctx, frmt, ...) \
64
71
LOG_OBJC_MACRO ( NO , lvl, flg, ctx, frmt, ##__VA_ARGS__)
72
79
#define ASYNC_LOG_C_MACRO (lvl, flg, ctx, frmt, ...) \
73
80
LOG_C_MACRO (YES , lvl, flg, ctx, frmt, ##__VA_ARGS__)
74
81
82
+ /* *
83
+ * Define version of the macro that only execute if the logLevel is above the threshold.
84
+ * The compiled versions essentially look like this:
85
+ *
86
+ * if (logFlagForThisLogMsg & ddLogLevel) { execute log message }
87
+ *
88
+ * As shown further below, Lumberjack actually uses a bitmask as opposed to primitive log levels.
89
+ * This allows for a great amount of flexibility and some pretty advanced fine grained logging techniques.
90
+ *
91
+ * Note that when compiler optimizations are enabled (as they are for your release builds),
92
+ * the log messages above your logging threshold will automatically be compiled out.
93
+ *
94
+ * (If the compiler sees ddLogLevel declared as a constant, the compiler simply checks to see if the 'if' statement
95
+ * would execute, and if not it strips it from the binary.)
96
+ *
97
+ * We also define shorthand versions for asynchronous and synchronous logging.
98
+ **/
75
99
76
100
#define LOG_MAYBE (async, lvl, flg, ctx, fnct, frmt, ...) \
77
- do { if (lvl & flg) LOG_MACRO (async, lvl, flg, ctx, fnct, frmt, ##__VA_ARGS__); } while (0 )
101
+ do { if (lvl & flg) LOG_MACRO (async, lvl, flg, ctx, nil , fnct, frmt, ##__VA_ARGS__); } while (0 )
78
102
79
103
#define LOG_OBJC_MAYBE (async, lvl, flg, ctx, frmt, ...) \
80
104
LOG_MAYBE (async, lvl, flg, ctx, sel_getName (_cmd), frmt, ##__VA_ARGS__)
94
118
#define ASYNC_LOG_C_MAYBE (lvl, flg, ctx, frmt, ...) \
95
119
LOG_C_MAYBE (YES , lvl, flg, ctx, frmt, ##__VA_ARGS__)
96
120
121
+ /* *
122
+ * Define versions of the macros that also accept tags.
123
+ *
124
+ * The DDLogMessage object includes a 'tag' ivar that may be used for a variety of purposes.
125
+ * It may be used to pass custom information to loggers or formatters.
126
+ * Or it may be used by 3rd party extensions to the framework.
127
+ *
128
+ * Thes macros just make it a little easier to extend logging functionality.
129
+ **/
130
+
131
+ #define LOG_OBJC_TAG_MACRO (async, lvl, flg, ctx, tag, frmt, ...) \
132
+ LOG_MACRO (async, lvl, flg, ctx, tag, sel_getName (_cmd), frmt, ##__VA_ARGS__)
133
+
134
+ #define LOG_C_TAG_MACRO (async, lvl, flg, ctx, tag, frmt, ...) \
135
+ LOG_MACRO (async, lvl, flg, ctx, tag, __FUNCTION__, frmt, ##__VA_ARGS__)
136
+
137
+ #define LOG_TAG_MAYBE (async, lvl, flg, ctx, tag, fnct, frmt, ...) \
138
+ do { if (lvl & flg) LOG_MACRO (async, lvl, flg, ctx, tag, fnct, frmt, ##__VA_ARGS__); } while (0 )
139
+
140
+ #define LOG_OBJC_TAG_MAYBE (async, lvl, flg, ctx, tag, frmt, ...) \
141
+ LOG_TAG_MAYBE (async, lvl, flg, ctx, tag, sel_getName (_cmd), frmt, ##__VA_ARGS__)
142
+
143
+ #define LOG_C_TAG_MAYBE (async, lvl, flg, ctx, tag, frmt, ...) \
144
+ LOG_TAG_MAYBE (async, lvl, flg, ctx, tag, __FUNCTION__, frmt, ##__VA_ARGS__)
145
+
97
146
/* *
98
147
* Define the standard options.
99
148
*
@@ -246,7 +295,8 @@ NSString *DDExtractFileNameWithoutExtension(const char *filePath, BOOL copy);
246
295
* Logging Primitive.
247
296
*
248
297
* This method can be used if you have a prepared va_list.
249
- */
298
+ **/
299
+
250
300
+ (void )log : (BOOL )asynchronous
251
301
level : (int )level
252
302
flag : (int )flag
@@ -307,8 +357,9 @@ NSString *DDExtractFileNameWithoutExtension(const char *filePath, BOOL copy);
307
357
308
358
/* *
309
359
* Formatters may optionally be added to any logger.
310
- * If no formatter is set, the logger simply logs the message as it is given in logMessage.
311
- * Or it may use its own built in formatting style.
360
+ *
361
+ * If no formatter is set, the logger simply logs the message as it is given in logMessage,
362
+ * or it may use its own built in formatting style.
312
363
**/
313
364
- (id <DDLogFormatter>)logFormatter ;
314
365
- (void )setLogFormatter : (id <DDLogFormatter>)formatter ;
@@ -423,6 +474,12 @@ NSString *DDExtractFileNameWithoutExtension(const char *filePath, BOOL copy);
423
474
* If you write custom loggers or formatters, you will be dealing with objects of this class.
424
475
**/
425
476
477
+ enum {
478
+ DDLogMessageCopyFile = 1 << 0 ,
479
+ DDLogMessageCopyFunction = 1 << 1 ,
480
+ };
481
+ typedef int DDLogMessageOptions;
482
+
426
483
@interface DDLogMessage : NSObject
427
484
{
428
485
@@ -435,23 +492,34 @@ NSString *DDExtractFileNameWithoutExtension(const char *filePath, BOOL copy);
435
492
int logContext;
436
493
NSString *logMsg;
437
494
NSDate *timestamp;
438
- const char *file;
439
- const char *function;
495
+ char *file;
496
+ char *function;
440
497
int lineNumber;
441
498
mach_port_t machThreadID;
442
499
char *queueLabel;
443
500
NSString *threadName;
444
- id tag; // For 3rd party extensions to the framework, where flags and contexts aren't enough.
501
+
502
+ // For 3rd party extensions to the framework, where flags and contexts aren't enough.
503
+ id tag;
504
+
505
+ // For 3rd party extensions that manually create DDLogMessage instances.
506
+ DDLogMessageOptions options;
445
507
}
446
508
447
509
/* *
448
- * The initializer is somewhat reserved for internal use.
449
- * However, if you find need to manually create logMessage objects, there is one thing you should be aware of:
510
+ * Standard init method for a log message object.
511
+ * Used by the logging primitives. (And the macros use the logging primitives.)
512
+ *
513
+ * If you find need to manually create logMessage objects, there is one thing you should be aware of:
450
514
*
451
- * The initializer expects the file and function parameters to be string literals.
515
+ * If no flags are passed, the method expects the file and function parameters to be string literals.
452
516
* That is, it expects the given strings to exist for the duration of the object's lifetime,
453
517
* and it expects the given strings to be immutable.
454
518
* In other words, it does not copy these strings, it simply points to them.
519
+ * This is due to the fact that __FILE__ and __FUNCTION__ are usually used to specify these parameters,
520
+ * so it makes sense to optimize and skip the unnecessary allocations.
521
+ * However, if you need them to be copied you may use the options parameter to specify this.
522
+ * Options is a bitmask which supports DDLogMessageCopyFile and DDLogMessageCopyFunction.
455
523
**/
456
524
- (id )initWithLogMsg : (NSString *)logMsg
457
525
level : (int )logLevel
@@ -460,7 +528,8 @@ NSString *DDExtractFileNameWithoutExtension(const char *filePath, BOOL copy);
460
528
file : (const char *)file
461
529
function : (const char *)function
462
530
line : (int )line
463
- tag : (id )tag ;
531
+ tag : (id )tag
532
+ options : (DDLogMessageOptions)optionsMask ;
464
533
465
534
/* *
466
535
* Returns the threadID as it appears in NSLog.
0 commit comments