event_log.h 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424
  1. /*
  2. * EVENT_LOG system definitions
  3. *
  4. * Portions of this code are copyright (c) 2020 Cypress Semiconductor Corporation
  5. *
  6. * Copyright (C) 1999-2020, Broadcom Corporation
  7. *
  8. * Unless you and Broadcom execute a separate written software license
  9. * agreement governing use of this software, this software is licensed to you
  10. * under the terms of the GNU General Public License version 2 (the "GPL"),
  11. * available at http://www.broadcom.com/licenses/GPLv2.php, with the
  12. * following added to such license:
  13. *
  14. * As a special exception, the copyright holders of this software give you
  15. * permission to link this software with independent modules, and to copy and
  16. * distribute the resulting executable under terms of your choice, provided that
  17. * you also meet, for each linked independent module, the terms and conditions of
  18. * the license of that module. An independent module is a module which is not
  19. * derived from this software. The special exception does not apply to any
  20. * modifications of the software.
  21. *
  22. * Notwithstanding the above, under no circumstances may you combine this
  23. * software in any way with any other Broadcom software provided under a license
  24. * other than the GPL, without Broadcom's express prior written consent.
  25. *
  26. *
  27. * <<Broadcom-WL-IPTag/Open:>>
  28. *
  29. * $Id: event_log.h 692339 2017-03-27 17:04:27Z $
  30. */
  31. #ifndef _EVENT_LOG_H_
  32. #define _EVENT_LOG_H_
  33. #include <typedefs.h>
  34. #include <event_log_set.h>
  35. #include <event_log_tag.h>
  36. #include <event_log_payload.h>
  37. #include <osl_decl.h>
  38. /* logstrs header */
  39. #define LOGSTRS_MAGIC 0x4C4F4753
  40. #define LOGSTRS_VERSION 0x1
  41. /* We make sure that the block size will fit in a single packet
  42. * (allowing for a bit of overhead on each packet
  43. */
  44. #if defined(BCMPCIEDEV)
  45. #define EVENT_LOG_MAX_BLOCK_SIZE 1648
  46. #else
  47. #define EVENT_LOG_MAX_BLOCK_SIZE 1400
  48. #endif // endif
  49. #define EVENT_LOG_WL_BLOCK_SIZE 0x200
  50. #define EVENT_LOG_PSM_BLOCK_SIZE 0x200
  51. #define EVENT_LOG_BUS_BLOCK_SIZE 0x200
  52. #define EVENT_LOG_ERROR_BLOCK_SIZE 0x200
  53. /* Maximum event log record payload size = 1016 bytes or 254 words. */
  54. #define EVENT_LOG_MAX_RECORD_PAYLOAD_SIZE 254
  55. /*
  56. * There are multiple levels of objects define here:
  57. * event_log_set - a set of buffers
  58. * event log groups - every event log call is part of just one. All
  59. * event log calls in a group are handled the
  60. * same way. Each event log group is associated
  61. * with an event log set or is off.
  62. */
  63. #ifndef __ASSEMBLER__
  64. /* On the external system where the dumper is we need to make sure
  65. * that these types are the same size as they are on the ARM the
  66. * produced them
  67. */
  68. #ifdef EVENT_LOG_DUMPER
  69. #define _EL_BLOCK_PTR uint32
  70. #define _EL_TYPE_PTR uint32
  71. #define _EL_SET_PTR uint32
  72. #define _EL_TOP_PTR uint32
  73. #else
  74. #define _EL_BLOCK_PTR struct event_log_block *
  75. #define _EL_TYPE_PTR uint32 *
  76. #define _EL_SET_PTR struct event_log_set **
  77. #define _EL_TOP_PTR struct event_log_top *
  78. #endif /* EVENT_LOG_DUMPER */
  79. /* Event log sets (a logical circurlar buffer) consist of one or more
  80. * event_log_blocks. The blocks themselves form a logical circular
  81. * list. The log entries are placed in each event_log_block until it
  82. * is full. Logging continues with the next event_log_block in the
  83. * event_set until the last event_log_block is reached and then
  84. * logging starts over with the first event_log_block in the
  85. * event_set.
  86. */
  87. typedef struct event_log_block {
  88. _EL_BLOCK_PTR next_block;
  89. _EL_BLOCK_PTR prev_block;
  90. _EL_TYPE_PTR end_ptr;
  91. /* Start of packet sent for log tracing */
  92. uint16 pktlen; /* Size of rest of block */
  93. uint16 count; /* Logtrace counter */
  94. uint32 extra_hdr_info; /* LSB: 6 bits set id. MSB 24 bits reserved */
  95. uint32 event_logs;
  96. } event_log_block_t;
  97. #define EVENT_LOG_BLOCK_HDRLEN 8 /* pktlen 2 + count 2 + extra_hdr_info 4 */
  98. #define EVENT_LOG_BLOCK_LEN 12
  99. typedef enum {
  100. SET_DESTINATION_INVALID = -1,
  101. SET_DESTINATION_HOST = 0,
  102. SET_DESTINATION_NONE = 1,
  103. SET_DESTINATION_MAX
  104. } event_log_set_destination_t;
  105. /* There can be multiple event_sets with each logging a set of
  106. * associated events (i.e, "fast" and "slow" events).
  107. */
  108. typedef struct event_log_set {
  109. _EL_BLOCK_PTR first_block; /* Pointer to first event_log block */
  110. _EL_BLOCK_PTR last_block; /* Pointer to last event_log block */
  111. _EL_BLOCK_PTR logtrace_block; /* next block traced */
  112. _EL_BLOCK_PTR cur_block; /* Pointer to current event_log block */
  113. _EL_TYPE_PTR cur_ptr; /* Current event_log pointer */
  114. uint32 blockcount; /* Number of blocks */
  115. uint16 logtrace_count; /* Last count for logtrace */
  116. uint16 blockfill_count; /* Fill count for logtrace */
  117. uint32 timestamp; /* Last timestamp event */
  118. uint32 cyclecount; /* Cycles at last timestamp event */
  119. event_log_set_destination_t destination;
  120. uint16 size; /* same size for all buffers in one set */
  121. } event_log_set_t;
  122. /* logstr_hdr_flags */
  123. #define LOGSTRS_ENCRYPTED 0x1
  124. /* Top data structure for access to everything else */
  125. typedef struct event_log_top {
  126. uint32 magic;
  127. #define EVENT_LOG_TOP_MAGIC 0x474C8669 /* 'EVLG' */
  128. uint32 version;
  129. #define EVENT_LOG_VERSION 1
  130. uint32 num_sets;
  131. uint32 logstrs_size; /* Size of lognums + logstrs area */
  132. uint32 timestamp; /* Last timestamp event */
  133. uint32 cyclecount; /* Cycles at last timestamp event */
  134. _EL_SET_PTR sets; /* Ptr to array of <num_sets> set ptrs */
  135. } event_log_top_t;
  136. /* structure of the trailing 3 words in logstrs.bin */
  137. typedef struct {
  138. uint32 fw_id; /* FWID will be written by tool later */
  139. uint32 flags; /* 0th bit indicates whether encrypted or not */
  140. /* Keep version and magic last since "header" is appended to the end of logstrs file. */
  141. uint32 version; /* Header version */
  142. uint32 log_magic; /* MAGIC number for verification 'LOGS' */
  143. } logstr_trailer_t;
  144. /* Data structure of Keeping the Header from logstrs.bin */
  145. typedef struct {
  146. uint32 logstrs_size; /* Size of the file */
  147. uint32 rom_lognums_offset; /* Offset to the ROM lognum */
  148. uint32 ram_lognums_offset; /* Offset to the RAM lognum */
  149. uint32 rom_logstrs_offset; /* Offset to the ROM logstr */
  150. uint32 ram_logstrs_offset; /* Offset to the RAM logstr */
  151. logstr_trailer_t trailer;
  152. } logstr_header_t;
  153. /* Ver 1 Header from logstrs.bin */
  154. typedef struct {
  155. uint32 logstrs_size; /* Size of the file */
  156. uint32 rom_lognums_offset; /* Offset to the ROM lognum */
  157. uint32 ram_lognums_offset; /* Offset to the RAM lognum */
  158. uint32 rom_logstrs_offset; /* Offset to the ROM logstr */
  159. uint32 ram_logstrs_offset; /* Offset to the RAM logstr */
  160. /* Keep version and magic last since "header" is appended to the end of logstrs file. */
  161. uint32 version; /* Header version */
  162. uint32 log_magic; /* MAGIC number for verification 'LOGS' */
  163. } logstr_header_v1_t;
  164. /*
  165. * Use the following macros for generating log events.
  166. *
  167. * The FAST versions check the enable of the tag before evaluating the arguments and calling the
  168. * event_log function. This adds 5 instructions. The COMPACT versions evaluate the arguments
  169. * and call the event_log function unconditionally. The event_log function will then skip logging
  170. * if this tag is disabled.
  171. *
  172. * To support easy usage of existing debugging (e.g. msglevel) via macro re-definition there are
  173. * two variants of these macros to help.
  174. *
  175. * First there are the CAST versions. The event_log function normally logs uint32 values or else
  176. * they have to be cast to uint32. The CAST versions blindly cast for you so you don't have to edit
  177. * any existing code.
  178. *
  179. * Second there are the PAREN_ARGS versions. These expect the logging format string and arguments
  180. * to be enclosed in parentheses. This allows us to make the following mapping of an existing
  181. * msglevel macro:
  182. * #define WL_ERROR(args) EVENT_LOG_CAST_PAREN_ARGS(EVENT_LOG_TAG_WL_ERROR, args)
  183. *
  184. * The versions of the macros without FAST or COMPACT in their name are just synonyms for the
  185. * COMPACT versions.
  186. *
  187. * You should use the COMPACT macro (or its synonym) in cases where there is some preceding logic
  188. * that prevents the execution of the macro, e.g. WL_ERROR by definition rarely gets executed.
  189. * Use the FAST macro in performance sensitive paths. The key concept here is that you should be
  190. * assuming that your macro usage is compiled into ROM and can't be changed ... so choose wisely.
  191. *
  192. */
  193. #if !defined(EVENT_LOG_DUMPER)
  194. #ifndef EVENT_LOG_COMPILE
  195. /* Null define if no tracing */
  196. #define EVENT_LOG(format, ...)
  197. #define EVENT_LOG_FAST(tag, fmt, ...)
  198. #define EVENT_LOG_COMPACT(tag, fmt, ...)
  199. #define EVENT_LOG_CAST(tag, fmt, ...)
  200. #define EVENT_LOG_FAST_CAST(tag, fmt, ...)
  201. #define EVENT_LOG_COMPACT_CAST(tag, fmt, ...)
  202. #define EVENT_LOG_CAST_PAREN_ARGS(tag, pargs)
  203. #define EVENT_LOG_FAST_CAST_PAREN_ARGS(tag, pargs)
  204. #define EVENT_LOG_COMPACT_CAST_PAREN_ARGS(tag, pargs)
  205. #define EVENT_LOG_IS_ON(tag) 0
  206. #define EVENT_LOG_IS_LOG_ON(tag) 0
  207. #define EVENT_LOG_BUFFER(tag, buf, size)
  208. #else /* EVENT_LOG_COMPILE */
  209. /* The first few are special because they can be done more efficiently
  210. * this way and they are the common case. Once there are too many
  211. * parameters the code size starts to be an issue and a loop is better
  212. */
  213. #define _EVENT_LOG0(tag, fmt_num) \
  214. event_log0(tag, fmt_num)
  215. #define _EVENT_LOG1(tag, fmt_num, t1) \
  216. event_log1(tag, fmt_num, t1)
  217. #define _EVENT_LOG2(tag, fmt_num, t1, t2) \
  218. event_log2(tag, fmt_num, t1, t2)
  219. #define _EVENT_LOG3(tag, fmt_num, t1, t2, t3) \
  220. event_log3(tag, fmt_num, t1, t2, t3)
  221. #define _EVENT_LOG4(tag, fmt_num, t1, t2, t3, t4) \
  222. event_log4(tag, fmt_num, t1, t2, t3, t4)
  223. /* The rest call the generic routine that takes a count */
  224. #define _EVENT_LOG5(tag, fmt_num, ...) event_logn(5, tag, fmt_num, __VA_ARGS__)
  225. #define _EVENT_LOG6(tag, fmt_num, ...) event_logn(6, tag, fmt_num, __VA_ARGS__)
  226. #define _EVENT_LOG7(tag, fmt_num, ...) event_logn(7, tag, fmt_num, __VA_ARGS__)
  227. #define _EVENT_LOG8(tag, fmt_num, ...) event_logn(8, tag, fmt_num, __VA_ARGS__)
  228. #define _EVENT_LOG9(tag, fmt_num, ...) event_logn(9, tag, fmt_num, __VA_ARGS__)
  229. #define _EVENT_LOGA(tag, fmt_num, ...) event_logn(10, tag, fmt_num, __VA_ARGS__)
  230. #define _EVENT_LOGB(tag, fmt_num, ...) event_logn(11, tag, fmt_num, __VA_ARGS__)
  231. #define _EVENT_LOGC(tag, fmt_num, ...) event_logn(12, tag, fmt_num, __VA_ARGS__)
  232. #define _EVENT_LOGD(tag, fmt_num, ...) event_logn(13, tag, fmt_num, __VA_ARGS__)
  233. #define _EVENT_LOGE(tag, fmt_num, ...) event_logn(14, tag, fmt_num, __VA_ARGS__)
  234. #define _EVENT_LOGF(tag, fmt_num, ...) event_logn(15, tag, fmt_num, __VA_ARGS__)
  235. /* Casting low level macros */
  236. #define _EVENT_LOG_CAST0(tag, fmt_num) \
  237. event_log0(tag, fmt_num)
  238. #define _EVENT_LOG_CAST1(tag, fmt_num, t1) \
  239. event_log1(tag, fmt_num, (uint32)(t1))
  240. #define _EVENT_LOG_CAST2(tag, fmt_num, t1, t2) \
  241. event_log2(tag, fmt_num, (uint32)(t1), (uint32)(t2))
  242. #define _EVENT_LOG_CAST3(tag, fmt_num, t1, t2, t3) \
  243. event_log3(tag, fmt_num, (uint32)(t1), (uint32)(t2), (uint32)(t3))
  244. #define _EVENT_LOG_CAST4(tag, fmt_num, t1, t2, t3, t4) \
  245. event_log4(tag, fmt_num, (uint32)(t1), (uint32)(t2), (uint32)(t3), (uint32)(t4))
  246. /* The rest call the generic routine that takes a count */
  247. #define _EVENT_LOG_CAST5(tag, fmt_num, ...) _EVENT_LOG5(tag, fmt_num, __VA_ARGS__)
  248. #define _EVENT_LOG_CAST6(tag, fmt_num, ...) _EVENT_LOG6(tag, fmt_num, __VA_ARGS__)
  249. #define _EVENT_LOG_CAST7(tag, fmt_num, ...) _EVENT_LOG7(tag, fmt_num, __VA_ARGS__)
  250. #define _EVENT_LOG_CAST8(tag, fmt_num, ...) _EVENT_LOG8(tag, fmt_num, __VA_ARGS__)
  251. #define _EVENT_LOG_CAST9(tag, fmt_num, ...) _EVENT_LOG9(tag, fmt_num, __VA_ARGS__)
  252. #define _EVENT_LOG_CASTA(tag, fmt_num, ...) _EVENT_LOGA(tag, fmt_num, __VA_ARGS__)
  253. #define _EVENT_LOG_CASTB(tag, fmt_num, ...) _EVENT_LOGB(tag, fmt_num, __VA_ARGS__)
  254. #define _EVENT_LOG_CASTC(tag, fmt_num, ...) _EVENT_LOGC(tag, fmt_num, __VA_ARGS__)
  255. #define _EVENT_LOG_CASTD(tag, fmt_num, ...) _EVENT_LOGD(tag, fmt_num, __VA_ARGS__)
  256. #define _EVENT_LOG_CASTE(tag, fmt_num, ...) _EVENT_LOGE(tag, fmt_num, __VA_ARGS__)
  257. #define _EVENT_LOG_CASTF(tag, fmt_num, ...) _EVENT_LOGF(tag, fmt_num, __VA_ARGS__)
  258. /* Hack to make the proper routine call when variadic macros get
  259. * passed. Note the max of 15 arguments. More than that can't be
  260. * handled by the event_log entries anyways so best to catch it at compile
  261. * time
  262. */
  263. #define _EVENT_LOG_VA_NUM_ARGS(F, _1, _2, _3, _4, _5, _6, _7, _8, _9, \
  264. _A, _B, _C, _D, _E, _F, N, ...) F ## N
  265. /* cast = _EVENT_LOG for no casting
  266. * cast = _EVENT_LOG_CAST for casting of fmt arguments to uint32.
  267. * Only first 4 arguments are casted to uint32. event_logn() is called
  268. * if more than 4 arguments are present. This function internally assumes
  269. * all arguments are uint32
  270. */
  271. #define _EVENT_LOG(cast, tag, fmt, ...) \
  272. static char logstr[] __attribute__ ((section(".logstrs"))) = fmt; \
  273. static uint32 fmtnum __attribute__ ((section(".lognums"))) = (uint32) &logstr; \
  274. _EVENT_LOG_VA_NUM_ARGS(cast, ##__VA_ARGS__, \
  275. F, E, D, C, B, A, 9, 8, \
  276. 7, 6, 5, 4, 3, 2, 1, 0) \
  277. (tag, (int) &fmtnum , ## __VA_ARGS__)
  278. #define EVENT_LOG_FAST(tag, fmt, ...) \
  279. do { \
  280. if (event_log_tag_sets != NULL) { \
  281. uint8 tag_flag = *(event_log_tag_sets + tag); \
  282. if ((tag_flag & ~EVENT_LOG_TAG_FLAG_SET_MASK) != 0) { \
  283. _EVENT_LOG(_EVENT_LOG, tag, fmt , ## __VA_ARGS__); \
  284. } \
  285. } \
  286. } while (0)
  287. #define EVENT_LOG_COMPACT(tag, fmt, ...) \
  288. do { \
  289. _EVENT_LOG(_EVENT_LOG, tag, fmt , ## __VA_ARGS__); \
  290. } while (0)
  291. /* Event log macro with casting to uint32 of arguments */
  292. #define EVENT_LOG_FAST_CAST(tag, fmt, ...) \
  293. do { \
  294. if (event_log_tag_sets != NULL) { \
  295. uint8 tag_flag = *(event_log_tag_sets + tag); \
  296. if ((tag_flag & ~EVENT_LOG_TAG_FLAG_SET_MASK) != 0) { \
  297. _EVENT_LOG(_EVENT_LOG_CAST, tag, fmt , ## __VA_ARGS__); \
  298. } \
  299. } \
  300. } while (0)
  301. #define EVENT_LOG_COMPACT_CAST(tag, fmt, ...) \
  302. do { \
  303. _EVENT_LOG(_EVENT_LOG_CAST, tag, fmt , ## __VA_ARGS__); \
  304. } while (0)
  305. #define EVENT_LOG(tag, fmt, ...) EVENT_LOG_COMPACT(tag, fmt , ## __VA_ARGS__)
  306. #define EVENT_LOG_CAST(tag, fmt, ...) EVENT_LOG_COMPACT_CAST(tag, fmt , ## __VA_ARGS__)
  307. #define _EVENT_LOG_REMOVE_PAREN(...) __VA_ARGS__
  308. #define EVENT_LOG_REMOVE_PAREN(args) _EVENT_LOG_REMOVE_PAREN args
  309. #define EVENT_LOG_CAST_PAREN_ARGS(tag, pargs) \
  310. EVENT_LOG_CAST(tag, EVENT_LOG_REMOVE_PAREN(pargs))
  311. #define EVENT_LOG_FAST_CAST_PAREN_ARGS(tag, pargs) \
  312. EVENT_LOG_FAST_CAST(tag, EVENT_LOG_REMOVE_PAREN(pargs))
  313. #define EVENT_LOG_COMPACT_CAST_PAREN_ARGS(tag, pargs) \
  314. EVENT_LOG_COMPACT_CAST(tag, EVENT_LOG_REMOVE_PAREN(pargs))
  315. /* Minimal event logging. Event log internally calls event_logx()
  316. * log return address in caller.
  317. * Note that the if(0){..} below is to avoid compiler warnings
  318. * due to unused variables caused by this macro
  319. */
  320. #define EVENT_LOG_RA(tag, args) \
  321. do { \
  322. if (0) { \
  323. EVENT_LOG_COMPACT_CAST_PAREN_ARGS(tag, args); \
  324. } \
  325. event_log_caller_return_address(tag); \
  326. } while (0)
  327. #define EVENT_LOG_IS_ON(tag) (*(event_log_tag_sets + (tag)) & ~EVENT_LOG_TAG_FLAG_SET_MASK)
  328. #define EVENT_LOG_IS_LOG_ON(tag) (*(event_log_tag_sets + (tag)) & EVENT_LOG_TAG_FLAG_LOG)
  329. #define EVENT_LOG_BUFFER(tag, buf, size) event_log_buffer(tag, buf, size)
  330. #define EVENT_DUMP event_log_buffer
  331. extern uint8 *event_log_tag_sets;
  332. extern int event_log_init(osl_t *osh);
  333. extern int event_log_set_init(osl_t *osh, int set_num, int size);
  334. extern int event_log_set_expand(osl_t *osh, int set_num, int size);
  335. extern int event_log_set_shrink(osl_t *osh, int set_num, int size);
  336. extern int event_log_tag_start(int tag, int set_num, int flags);
  337. extern int event_log_tag_set_retrieve(int tag);
  338. extern int event_log_tag_stop(int tag);
  339. typedef void (*event_log_logtrace_trigger_fn_t)(void *ctx);
  340. void event_log_set_logtrace_trigger_fn(event_log_logtrace_trigger_fn_t fn, void *ctx);
  341. event_log_top_t *event_log_get_top(void);
  342. extern int event_log_get(int set_num, int buflen, void *buf);
  343. extern uint8 *event_log_next_logtrace(int set_num);
  344. extern void event_log0(int tag, int fmtNum);
  345. extern void event_log1(int tag, int fmtNum, uint32 t1);
  346. extern void event_log2(int tag, int fmtNum, uint32 t1, uint32 t2);
  347. extern void event_log3(int tag, int fmtNum, uint32 t1, uint32 t2, uint32 t3);
  348. extern void event_log4(int tag, int fmtNum, uint32 t1, uint32 t2, uint32 t3, uint32 t4);
  349. extern void event_logn(int num_args, int tag, int fmtNum, ...);
  350. extern void event_log_time_sync(uint32 ms);
  351. extern void event_log_buffer(int tag, uint8 *buf, int size);
  352. extern void event_log_caller_return_address(int tag);
  353. extern int event_log_set_destination_set(int set, event_log_set_destination_t dest);
  354. extern event_log_set_destination_t event_log_set_destination_get(int set);
  355. extern int event_log_flush_log_buffer(int set);
  356. extern uint16 event_log_get_available_space(int set);
  357. extern bool event_log_is_set_configured(int set_num);
  358. extern bool event_log_is_tag_valid(int tag);
  359. /* returns number of blocks available for writing */
  360. extern int event_log_free_blocks_get(int set);
  361. extern bool event_log_is_ready(void);
  362. #endif /* EVENT_LOG_DUMPER */
  363. #endif /* EVENT_LOG_COMPILE */
  364. #endif /* __ASSEMBLER__ */
  365. #endif /* _EVENT_LOG_H_ */