1 /*
2  * SPDX-FileCopyrightText: Copyright (c) 2009-2019 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
3  * SPDX-License-Identifier: MIT
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining a
6  * copy of this software and associated documentation files (the "Software"),
7  * to deal in the Software without restriction, including without limitation
8  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9  * and/or sell copies of the Software, and to permit persons to whom the
10  * Software is furnished to do so, subject to the following conditions:
11  *
12  * The above copyright notice and this permission notice shall be included in
13  * all copies or substantial portions of the Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18  * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21  * DEALINGS IN THE SOFTWARE.
22  */
23 #ifndef _NVLOG_H_
24 #define _NVLOG_H_
25 
26 #ifdef __cplusplus
27 extern "C" {
28 #endif
29 
30 #include "nvtypes.h"
31 #include "nvstatus.h"
32 
33 /******************* Common Debug & Trace Defines **************************\
34 *                                                                           *
35 * Module: NVLOG.H                                                           *
36 *                                                                           *
37 \***************************************************************************/
38 
39 // Include common NvLog definitions
40 #include "nvlog_defs.h"
41 
42 // Include printf definitions
43 #include "nvlog/nvlog_printf.h"
44 
45 extern NVLOG_LOGGER             NvLogLogger;
46 extern NVLOG_PRINT_LOGGER       NvLogPrintLogger;
47 
48 /********************************/
49 /*****  Exported functions  *****/
50 /********************************/
51 
52 
53 /**
54  * @brief Global NvLog initialization function
55  *
56  * @return NV_OK on success
57  */
58 NV_STATUS nvlogInit(void *pData);
59 
60 /**
61  * @brief Update the NvLog configuration from the registry
62  *
63  */
64 void nvlogUpdate(void);
65 
66 /**
67  * @brief Global NvLog deinitialization function
68  *
69  * @return NV_OK on success
70  */
71 NV_STATUS nvlogDestroy(void);
72 
73 /**
74  * @brief Allocate a new NvLog buffer
75  *
76  * @param[in]   size          Size of the buffer to allocate
77  * @param[in]   flags         Buffer flags, uses NVLOG_BUFFER_FLAGS_* DRF's
78  * @param[in]   tag           Tag for the new buffer, to identify it in a dump
79  * @param[out]  pBufferHandle Handle of the newly created buffer
80  *
81  * @return NV_OK on success
82  */
83 NV_STATUS nvlogAllocBuffer(NvU32 size, NvU32 flags, NvU32 tag, NVLOG_BUFFER_HANDLE *pBufferHandle, ...);
84 
85 /**
86  * @brief Deallocate a buffer with the given handle
87  *
88  * @param[in]   hBuffer     Handle of the buffer to deallocate
89  * @param[in]   bDeallocPreserved Deallocate preserved buffers
90  */
91 void nvlogDeallocBuffer(NVLOG_BUFFER_HANDLE hBuffer, NvBool bDeallocPreserved);
92 
93 /**
94  * @brief Write to a buffer with the given handle
95  *
96  * @param[in]   hBuffer     Handle of the buffer to write to
97  * @param[in]   pData       Pointer to the data to be written
98  * @param[in]   dataSize    Size of the data to be written
99  *
100  * @return NV_OK on success
101  */
102 NV_STATUS nvlogWriteToBuffer(NVLOG_BUFFER_HANDLE hBuffer, NvU8 *pData, NvU32 dataSize);
103 
104 /**
105  * @brief Extract a chunk of a buffer
106  *
107  * @param[in]     hBuffer    Handle of the buffer to extract
108  * @param[in]     chunkNum   Index (0-based) of the chunk to extract
109  * @param[in,out] pCunkSize  In  - Size of the chunk to extract
110  *                           Out - Size that was actually extracted, can be less
111  * @param[out]    pDest      Pointer to the memory the chunk will be copied to
112  *
113  * @return NV_OK on success
114  */
115 NV_STATUS nvlogExtractBufferChunk(NVLOG_BUFFER_HANDLE hBuffer, NvU32 chunkNum, NvU32 *pChunkSize, NvU8 *pDest);
116 
117 /**
118  * @brief Get the size of a specified buffer
119  *
120  * @param[in]     hBuffer   Handle of the buffer
121  * @param[out]    pSize     Buffer size.
122  *
123  * @return NV_OK on success
124  */
125 NV_STATUS nvlogGetBufferSize(NVLOG_BUFFER_HANDLE hBuffer, NvU32 *pSize);
126 
127 /**
128  * @brief Get the tag of a specified buffer.
129  *
130  * @param[in]     hBuffer   Handle of the buffer
131  * @param[out]    pTag      Buffer tag.
132  *
133  * @return NV_OK on success
134  */
135 NV_STATUS nvlogGetBufferTag(NVLOG_BUFFER_HANDLE hBuffer, NvU32 *pTag);
136 
137 /**
138  * @brief Get flags for a specified buffer.
139  *        Flag fields are defined as NVLOG_BUFFER_FLAGS_* in nvlog_defs.h
140  *
141  * @param[in]     hBuffer   Handle of the buffer
142  * @param[out]    pFlags    Buffer flags.
143  *
144  * @return NV_OK on success
145  */
146 NV_STATUS nvlogGetBufferFlags(NVLOG_BUFFER_HANDLE hBuffer, NvU32 *pFlags);
147 
148 /**
149  * @brief Pause/resume logging to a specified buffer
150  *
151  * @param[in]     hBuffer   Handle of the buffer
152  * @param[out]    bPause    NV_TRUE ??Pause, NV_FALSE ??resume
153  *
154  * @return NV_OK on success
155  */
156 NV_STATUS nvlogPauseLoggingToBuffer(NVLOG_BUFFER_HANDLE hBuffer, NvBool bPause);
157 
158 /**
159  * @brief Pause/resume logging to all buffers
160  *
161  * @param[out]    bPause    NV_TRUE ??Pause, NV_FALSE ??resume
162  *
163  * @return NV_OK on success
164  */
165 NV_STATUS nvlogPauseAllLogging(NvBool bPause);
166 
167 /**
168  * @brief Get the handle of a buffer with the given tag
169  *
170  * @param[in]     tag            Tag of the buffer requested
171  * @param[out]    pBufferHandle  Handle of the buffer
172  *
173  * @return NV_OK on success
174  */
175 NV_STATUS nvlogGetBufferHandleFromTag(NvU32 tag, NVLOG_BUFFER_HANDLE *pBufferHandle);
176 
177 /**
178  * @brief Get the handle of a buffer with the given tag
179  *
180  * @param[in]     tag            Tag of the buffer requested
181  * @param[out]    pBufferHandle  Handle of the buffer
182  *
183  * @return NV_OK on success
184  */
185 NV_STATUS nvlogGetBufferSnapshot(NVLOG_BUFFER_HANDLE hBuffer, NvU8 *pDest, NvU32 destSize);
186 
187 
188 /**
189  * @brief Dumps all logs into the the kernel print log
190  *
191  * @note this will write to the log even if all other prints are disabled,
192  * including external release builds. The output will be base64 encoded and
193  * not decodable without the database, and pollute the logs. Use with caution.
194  *
195  * The format of the dump will be the same as the OS Crash Log dumps.
196  */
197 void nvlogDumpToKernelLog(NvBool bDumpUnchangedBuffersOnlyOnce);
198 
199 //
200 // The values returned by CheckFilter functions contain up to four buffers.
201 // These indexes are in the local buffer array (i.e. in NVLOG_PRINT_LOGGER)
202 // There can be more than 256 total NvLog buffers, but only 256 per subsystem.
203 //
204 #define NVLOG_FILTER_BUFFER_NONE    0xFF
205 
206 //
207 // NvLog Print functions
208 //
209 
210 /**
211  * @brief Check the filtering rules for a given DBG_PRINTF
212  *
213  * @param[in]     fileId         ID (name hash) of the file
214  * @param[in]     line           Line number of the print
215  * @param[in]     level          Debug level (DBG_LEVEL_*) of the print
216  * @param[in]     module         Debug module (DBG_MODULE_*) of the print
217  *
218  * @return 32 bits to indicate which of the print buffers to log to.
219  */
220 NvU32 nvlogPrintCheckFilter(NvU32 fileId, NvU16 line, NvU32 level, NvU32 module);
221 
222 /**
223  * @brief Global NvLog Print initialization function
224  *
225  * @return NV_OK on success
226  */
227 NV_STATUS nvlogPrintInit(void);
228 
229 /**
230  * @brief NvLog Print update function
231  *
232  * @return NV_OK on success
233  */
234 NV_STATUS nvlogPrintUpdate(void);
235 
236 /**
237  * @brief Global NvLog Print deinitialization function
238  *
239  * @return NV_OK on success
240  */
241 NV_STATUS nvlogPrintDestroy(void);
242 
243 /**
244  * @brief Global NvLog ETW capture state function
245  *
246  * @return NV_OK on success
247  */
248 NV_STATUS nvlogETWCaptureState(void);
249 
250 //
251 // Global initialization macros
252 //
253 extern volatile NvU32 nvlogInitCount;
254 #define NVLOG_INIT(pData)                                 \
255     do                                                    \
256     {                                                     \
257         if (portAtomicIncrementU32(&nvlogInitCount) == 1) \
258         {                                                 \
259             nvlogInit(pData);                             \
260         }                                                 \
261     } while (0)
262 
263 #define NVLOG_UPDATE()                                    \
264     do                                                    \
265     {                                                     \
266         if (nvlogInitCount == 1)                          \
267         {                                                 \
268             nvlogUpdate();                                \
269         }                                                 \
270     } while (0)
271 
272 #define NVLOG_DESTROY()                                   \
273     do                                                    \
274     {                                                     \
275         if (portAtomicDecrementU32(&nvlogInitCount) == 0) \
276         {                                                 \
277             nvlogDestroy();                               \
278         }                                                 \
279     } while (0)
280 
281 /********************************/
282 /******  NvLog Filtering  *******/
283 /********************************/
284 
285 //
286 // Used both by print and regtrace functions.
287 //
288 
289 /**
290  * @brief Binary search the range array for a given number
291  *
292  * @param[in]   ranges    Range array to search
293  * @param[in]   numRanges Size of the given array
294  * @param[in]   num       Number to search for.
295  *
296  * @return  Number that is found in the given range.
297  *          If no number is found, returns ~0 (0xFFFFFFFF)
298  */
299 NvU32 nvlogFindInRange16Array(NVLOG_RANGE_16 *ranges, NvU32 numRanges, NvU16 num);
300 /**
301  * @brief Binary search the range array for a given number
302  *
303  * @param[in]   ranges    Range array to search
304  * @param[in]   numRanges Size of the given array
305  * @param[in]   num       Number to search for.
306  *
307  * @return  Number that is found in the given range.
308  *          If no number is found, returns ~0 (0xFFFFFFFF)
309  */
310 NvU32 nvlogFindInRange32Array(NVLOG_RANGE_32 *ranges, NvU32 numRanges, NvU32 num);
311 
312 // Returns the rules for the given fileId-lineNum pair
313 /**
314  * @brief Binary search the range array for a given number
315  *
316  * @param[in]   pFileLineFilter    File:line filter to check
317  * @param[in]   fileId             ID of the file to search
318  * @param[in]   lineNum            Line number to search in the file entry
319  *
320  * @return  Number that is found for the given file:line.
321  *          If no number is found, returns ~0 (0xFFFFFFFF)
322  */
323 NvU32 nvlogGetFileLineFilterRules(NVLOG_FILELINE_FILTER *pFileLineFilter, NvU32 fileId, NvU16 lineNum);
324 
325 
326 /**
327  * @brief Dump nvlog to kernel log only if enabled (performs regkey and platform checks)
328  */
329 void nvlogDumpToKernelLogIfEnabled(void);
330 
331 #ifdef __cplusplus
332 } // extern "C"
333 #endif
334 
335 #endif // _NVLOG_H_
336