xref: /aosp_15_r20/external/libopus/silk/debug.h (revision a58d3d2adb790c104798cd88c8a3aff4fa8b82cc)
1*a58d3d2aSXin Li /***********************************************************************
2*a58d3d2aSXin Li Copyright (c) 2006-2011, Skype Limited. All rights reserved.
3*a58d3d2aSXin Li Redistribution and use in source and binary forms, with or without
4*a58d3d2aSXin Li modification, are permitted provided that the following conditions
5*a58d3d2aSXin Li are met:
6*a58d3d2aSXin Li - Redistributions of source code must retain the above copyright notice,
7*a58d3d2aSXin Li this list of conditions and the following disclaimer.
8*a58d3d2aSXin Li - Redistributions in binary form must reproduce the above copyright
9*a58d3d2aSXin Li notice, this list of conditions and the following disclaimer in the
10*a58d3d2aSXin Li documentation and/or other materials provided with the distribution.
11*a58d3d2aSXin Li - Neither the name of Internet Society, IETF or IETF Trust, nor the
12*a58d3d2aSXin Li names of specific contributors, may be used to endorse or promote
13*a58d3d2aSXin Li products derived from this software without specific prior written
14*a58d3d2aSXin Li permission.
15*a58d3d2aSXin Li THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
16*a58d3d2aSXin Li AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17*a58d3d2aSXin Li IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18*a58d3d2aSXin Li ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
19*a58d3d2aSXin Li LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20*a58d3d2aSXin Li CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
21*a58d3d2aSXin Li SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22*a58d3d2aSXin Li INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
23*a58d3d2aSXin Li CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24*a58d3d2aSXin Li ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25*a58d3d2aSXin Li POSSIBILITY OF SUCH DAMAGE.
26*a58d3d2aSXin Li ***********************************************************************/
27*a58d3d2aSXin Li 
28*a58d3d2aSXin Li #ifndef SILK_DEBUG_H
29*a58d3d2aSXin Li #define SILK_DEBUG_H
30*a58d3d2aSXin Li 
31*a58d3d2aSXin Li /* Set to 1 to enable DEBUG_STORE_DATA() macros for dumping
32*a58d3d2aSXin Li  * intermediate signals from the codec.
33*a58d3d2aSXin Li  */
34*a58d3d2aSXin Li #define SILK_DEBUG 0
35*a58d3d2aSXin Li 
36*a58d3d2aSXin Li /* Flag for using timers */
37*a58d3d2aSXin Li #define SILK_TIC_TOC 0
38*a58d3d2aSXin Li 
39*a58d3d2aSXin Li #if SILK_DEBUG || SILK_TIC_TOC
40*a58d3d2aSXin Li #include "typedef.h"
41*a58d3d2aSXin Li #include <string.h>     /* strcpy, strcmp */
42*a58d3d2aSXin Li #include <stdio.h>      /* file writing */
43*a58d3d2aSXin Li #endif
44*a58d3d2aSXin Li 
45*a58d3d2aSXin Li #ifdef  __cplusplus
46*a58d3d2aSXin Li extern "C"
47*a58d3d2aSXin Li {
48*a58d3d2aSXin Li #endif
49*a58d3d2aSXin Li 
50*a58d3d2aSXin Li #if SILK_TIC_TOC
51*a58d3d2aSXin Li 
52*a58d3d2aSXin Li unsigned long GetHighResolutionTime(void); /* O  time in usec*/
53*a58d3d2aSXin Li 
54*a58d3d2aSXin Li #if (defined(_WIN32) || defined(_WINCE))
55*a58d3d2aSXin Li #include <windows.h>    /* timer */
56*a58d3d2aSXin Li #else   /* Linux or Mac*/
57*a58d3d2aSXin Li #include <sys/time.h>
58*a58d3d2aSXin Li #endif
59*a58d3d2aSXin Li 
60*a58d3d2aSXin Li /*********************************/
61*a58d3d2aSXin Li /* timer functions for profiling */
62*a58d3d2aSXin Li /*********************************/
63*a58d3d2aSXin Li /* example:                                                         */
64*a58d3d2aSXin Li /*                                                                  */
65*a58d3d2aSXin Li /* TIC(LPC)                                                         */
66*a58d3d2aSXin Li /* do_LPC(in_vec, order, acoef);    // do LPC analysis              */
67*a58d3d2aSXin Li /* TOC(LPC)                                                         */
68*a58d3d2aSXin Li /*                                                                  */
69*a58d3d2aSXin Li /* and call the following just before exiting (from main)           */
70*a58d3d2aSXin Li /*                                                                  */
71*a58d3d2aSXin Li /* silk_TimerSave("silk_TimingData.txt");                           */
72*a58d3d2aSXin Li /*                                                                  */
73*a58d3d2aSXin Li /* results are now in silk_TimingData.txt                           */
74*a58d3d2aSXin Li 
75*a58d3d2aSXin Li void silk_TimerSave(char *file_name);
76*a58d3d2aSXin Li 
77*a58d3d2aSXin Li /* max number of timers (in different locations) */
78*a58d3d2aSXin Li #define silk_NUM_TIMERS_MAX                  50
79*a58d3d2aSXin Li /* max length of name tags in TIC(..), TOC(..) */
80*a58d3d2aSXin Li #define silk_NUM_TIMERS_MAX_TAG_LEN          30
81*a58d3d2aSXin Li 
82*a58d3d2aSXin Li extern int           silk_Timer_nTimers;
83*a58d3d2aSXin Li extern int           silk_Timer_depth_ctr;
84*a58d3d2aSXin Li extern char          silk_Timer_tags[silk_NUM_TIMERS_MAX][silk_NUM_TIMERS_MAX_TAG_LEN];
85*a58d3d2aSXin Li #ifdef _WIN32
86*a58d3d2aSXin Li extern LARGE_INTEGER silk_Timer_start[silk_NUM_TIMERS_MAX];
87*a58d3d2aSXin Li #else
88*a58d3d2aSXin Li extern unsigned long silk_Timer_start[silk_NUM_TIMERS_MAX];
89*a58d3d2aSXin Li #endif
90*a58d3d2aSXin Li extern unsigned int  silk_Timer_cnt[silk_NUM_TIMERS_MAX];
91*a58d3d2aSXin Li extern opus_int64    silk_Timer_sum[silk_NUM_TIMERS_MAX];
92*a58d3d2aSXin Li extern opus_int64    silk_Timer_max[silk_NUM_TIMERS_MAX];
93*a58d3d2aSXin Li extern opus_int64    silk_Timer_min[silk_NUM_TIMERS_MAX];
94*a58d3d2aSXin Li extern opus_int64    silk_Timer_depth[silk_NUM_TIMERS_MAX];
95*a58d3d2aSXin Li 
96*a58d3d2aSXin Li /* WARNING: TIC()/TOC can measure only up to 0.1 seconds at a time */
97*a58d3d2aSXin Li #ifdef _WIN32
98*a58d3d2aSXin Li #define TIC(TAG_NAME) {                                     \
99*a58d3d2aSXin Li     static int init = 0;                                    \
100*a58d3d2aSXin Li     static int ID = -1;                                     \
101*a58d3d2aSXin Li     if( init == 0 )                                         \
102*a58d3d2aSXin Li     {                                                       \
103*a58d3d2aSXin Li         int k;                                              \
104*a58d3d2aSXin Li         init = 1;                                           \
105*a58d3d2aSXin Li         for( k = 0; k < silk_Timer_nTimers; k++ ) {         \
106*a58d3d2aSXin Li             if( strcmp(silk_Timer_tags[k], #TAG_NAME) == 0 ) { \
107*a58d3d2aSXin Li                 ID = k;                                     \
108*a58d3d2aSXin Li                 break;                                      \
109*a58d3d2aSXin Li             }                                               \
110*a58d3d2aSXin Li         }                                                   \
111*a58d3d2aSXin Li         if (ID == -1) {                                     \
112*a58d3d2aSXin Li             ID = silk_Timer_nTimers;                        \
113*a58d3d2aSXin Li             silk_Timer_nTimers++;                           \
114*a58d3d2aSXin Li             silk_Timer_depth[ID] = silk_Timer_depth_ctr;    \
115*a58d3d2aSXin Li             strcpy(silk_Timer_tags[ID], #TAG_NAME);         \
116*a58d3d2aSXin Li             silk_Timer_cnt[ID] = 0;                         \
117*a58d3d2aSXin Li             silk_Timer_sum[ID] = 0;                         \
118*a58d3d2aSXin Li             silk_Timer_min[ID] = 0xFFFFFFFF;                \
119*a58d3d2aSXin Li             silk_Timer_max[ID] = 0;                         \
120*a58d3d2aSXin Li         }                                                   \
121*a58d3d2aSXin Li     }                                                       \
122*a58d3d2aSXin Li     silk_Timer_depth_ctr++;                                 \
123*a58d3d2aSXin Li     QueryPerformanceCounter(&silk_Timer_start[ID]);         \
124*a58d3d2aSXin Li }
125*a58d3d2aSXin Li #else
126*a58d3d2aSXin Li #define TIC(TAG_NAME) {                                     \
127*a58d3d2aSXin Li     static int init = 0;                                    \
128*a58d3d2aSXin Li     static int ID = -1;                                     \
129*a58d3d2aSXin Li     if( init == 0 )                                         \
130*a58d3d2aSXin Li     {                                                       \
131*a58d3d2aSXin Li         int k;                                              \
132*a58d3d2aSXin Li         init = 1;                                           \
133*a58d3d2aSXin Li         for( k = 0; k < silk_Timer_nTimers; k++ ) {         \
134*a58d3d2aSXin Li         if( strcmp(silk_Timer_tags[k], #TAG_NAME) == 0 ) {  \
135*a58d3d2aSXin Li                 ID = k;                                     \
136*a58d3d2aSXin Li                 break;                                      \
137*a58d3d2aSXin Li             }                                               \
138*a58d3d2aSXin Li         }                                                   \
139*a58d3d2aSXin Li         if (ID == -1) {                                     \
140*a58d3d2aSXin Li             ID = silk_Timer_nTimers;                        \
141*a58d3d2aSXin Li             silk_Timer_nTimers++;                           \
142*a58d3d2aSXin Li             silk_Timer_depth[ID] = silk_Timer_depth_ctr;    \
143*a58d3d2aSXin Li             strcpy(silk_Timer_tags[ID], #TAG_NAME);         \
144*a58d3d2aSXin Li             silk_Timer_cnt[ID] = 0;                         \
145*a58d3d2aSXin Li             silk_Timer_sum[ID] = 0;                         \
146*a58d3d2aSXin Li             silk_Timer_min[ID] = 0xFFFFFFFF;                \
147*a58d3d2aSXin Li             silk_Timer_max[ID] = 0;                         \
148*a58d3d2aSXin Li         }                                                   \
149*a58d3d2aSXin Li     }                                                       \
150*a58d3d2aSXin Li     silk_Timer_depth_ctr++;                                 \
151*a58d3d2aSXin Li     silk_Timer_start[ID] = GetHighResolutionTime();         \
152*a58d3d2aSXin Li }
153*a58d3d2aSXin Li #endif
154*a58d3d2aSXin Li 
155*a58d3d2aSXin Li #ifdef _WIN32
156*a58d3d2aSXin Li #define TOC(TAG_NAME) {                                             \
157*a58d3d2aSXin Li     LARGE_INTEGER lpPerformanceCount;                               \
158*a58d3d2aSXin Li     static int init = 0;                                            \
159*a58d3d2aSXin Li     static int ID = 0;                                              \
160*a58d3d2aSXin Li     if( init == 0 )                                                 \
161*a58d3d2aSXin Li     {                                                               \
162*a58d3d2aSXin Li         int k;                                                      \
163*a58d3d2aSXin Li         init = 1;                                                   \
164*a58d3d2aSXin Li         for( k = 0; k < silk_Timer_nTimers; k++ ) {                 \
165*a58d3d2aSXin Li             if( strcmp(silk_Timer_tags[k], #TAG_NAME) == 0 ) {      \
166*a58d3d2aSXin Li                 ID = k;                                             \
167*a58d3d2aSXin Li                 break;                                              \
168*a58d3d2aSXin Li             }                                                       \
169*a58d3d2aSXin Li         }                                                           \
170*a58d3d2aSXin Li     }                                                               \
171*a58d3d2aSXin Li     QueryPerformanceCounter(&lpPerformanceCount);                   \
172*a58d3d2aSXin Li     lpPerformanceCount.QuadPart -= silk_Timer_start[ID].QuadPart;   \
173*a58d3d2aSXin Li     if((lpPerformanceCount.QuadPart < 100000000) &&                 \
174*a58d3d2aSXin Li         (lpPerformanceCount.QuadPart >= 0)) {                       \
175*a58d3d2aSXin Li         silk_Timer_cnt[ID]++;                                       \
176*a58d3d2aSXin Li         silk_Timer_sum[ID] += lpPerformanceCount.QuadPart;          \
177*a58d3d2aSXin Li         if( lpPerformanceCount.QuadPart > silk_Timer_max[ID] )      \
178*a58d3d2aSXin Li             silk_Timer_max[ID] = lpPerformanceCount.QuadPart;       \
179*a58d3d2aSXin Li         if( lpPerformanceCount.QuadPart < silk_Timer_min[ID] )      \
180*a58d3d2aSXin Li             silk_Timer_min[ID] = lpPerformanceCount.QuadPart;       \
181*a58d3d2aSXin Li     }                                                               \
182*a58d3d2aSXin Li     silk_Timer_depth_ctr--;                                         \
183*a58d3d2aSXin Li }
184*a58d3d2aSXin Li #else
185*a58d3d2aSXin Li #define TOC(TAG_NAME) {                                             \
186*a58d3d2aSXin Li     unsigned long endTime;                                          \
187*a58d3d2aSXin Li     static int init = 0;                                            \
188*a58d3d2aSXin Li     static int ID = 0;                                              \
189*a58d3d2aSXin Li     if( init == 0 )                                                 \
190*a58d3d2aSXin Li     {                                                               \
191*a58d3d2aSXin Li         int k;                                                      \
192*a58d3d2aSXin Li         init = 1;                                                   \
193*a58d3d2aSXin Li         for( k = 0; k < silk_Timer_nTimers; k++ ) {                 \
194*a58d3d2aSXin Li             if( strcmp(silk_Timer_tags[k], #TAG_NAME) == 0 ) {      \
195*a58d3d2aSXin Li                 ID = k;                                             \
196*a58d3d2aSXin Li                 break;                                              \
197*a58d3d2aSXin Li             }                                                       \
198*a58d3d2aSXin Li         }                                                           \
199*a58d3d2aSXin Li     }                                                               \
200*a58d3d2aSXin Li     endTime = GetHighResolutionTime();                              \
201*a58d3d2aSXin Li     endTime -= silk_Timer_start[ID];                                \
202*a58d3d2aSXin Li     if((endTime < 100000000) &&                                     \
203*a58d3d2aSXin Li         (endTime >= 0)) {                                           \
204*a58d3d2aSXin Li         silk_Timer_cnt[ID]++;                                       \
205*a58d3d2aSXin Li         silk_Timer_sum[ID] += endTime;                              \
206*a58d3d2aSXin Li         if( endTime > silk_Timer_max[ID] )                          \
207*a58d3d2aSXin Li             silk_Timer_max[ID] = endTime;                           \
208*a58d3d2aSXin Li         if( endTime < silk_Timer_min[ID] )                          \
209*a58d3d2aSXin Li             silk_Timer_min[ID] = endTime;                           \
210*a58d3d2aSXin Li     }                                                               \
211*a58d3d2aSXin Li         silk_Timer_depth_ctr--;                                     \
212*a58d3d2aSXin Li }
213*a58d3d2aSXin Li #endif
214*a58d3d2aSXin Li 
215*a58d3d2aSXin Li #else /* SILK_TIC_TOC */
216*a58d3d2aSXin Li 
217*a58d3d2aSXin Li /* define macros as empty strings */
218*a58d3d2aSXin Li #define TIC(TAG_NAME)
219*a58d3d2aSXin Li #define TOC(TAG_NAME)
220*a58d3d2aSXin Li #define silk_TimerSave(FILE_NAME)
221*a58d3d2aSXin Li 
222*a58d3d2aSXin Li #endif /* SILK_TIC_TOC */
223*a58d3d2aSXin Li 
224*a58d3d2aSXin Li 
225*a58d3d2aSXin Li #if SILK_DEBUG
226*a58d3d2aSXin Li /************************************/
227*a58d3d2aSXin Li /* write data to file for debugging */
228*a58d3d2aSXin Li /************************************/
229*a58d3d2aSXin Li /* Example: DEBUG_STORE_DATA(testfile.pcm, &RIN[0], 160*sizeof(opus_int16)); */
230*a58d3d2aSXin Li 
231*a58d3d2aSXin Li #define silk_NUM_STORES_MAX                                  100
232*a58d3d2aSXin Li extern FILE *silk_debug_store_fp[ silk_NUM_STORES_MAX ];
233*a58d3d2aSXin Li extern int silk_debug_store_count;
234*a58d3d2aSXin Li 
235*a58d3d2aSXin Li /* Faster way of storing the data */
236*a58d3d2aSXin Li #define DEBUG_STORE_DATA( FILE_NAME, DATA_PTR, N_BYTES ) {          \
237*a58d3d2aSXin Li     static opus_int init = 0, cnt = 0;                              \
238*a58d3d2aSXin Li     static FILE **fp;                                               \
239*a58d3d2aSXin Li     if (init == 0) {                                                \
240*a58d3d2aSXin Li         init = 1;                                                   \
241*a58d3d2aSXin Li         cnt = silk_debug_store_count++;                             \
242*a58d3d2aSXin Li         silk_debug_store_fp[ cnt ] = fopen(#FILE_NAME, "wb");       \
243*a58d3d2aSXin Li     }                                                               \
244*a58d3d2aSXin Li     fwrite((DATA_PTR), (N_BYTES), 1, silk_debug_store_fp[ cnt ]);   \
245*a58d3d2aSXin Li }
246*a58d3d2aSXin Li 
247*a58d3d2aSXin Li /* Call this at the end of main() */
248*a58d3d2aSXin Li #define SILK_DEBUG_STORE_CLOSE_FILES {                              \
249*a58d3d2aSXin Li     opus_int i;                                                     \
250*a58d3d2aSXin Li     for( i = 0; i < silk_debug_store_count; i++ ) {                 \
251*a58d3d2aSXin Li         fclose( silk_debug_store_fp[ i ] );                         \
252*a58d3d2aSXin Li     }                                                               \
253*a58d3d2aSXin Li }
254*a58d3d2aSXin Li 
255*a58d3d2aSXin Li #else /* SILK_DEBUG */
256*a58d3d2aSXin Li 
257*a58d3d2aSXin Li /* define macros as empty strings */
258*a58d3d2aSXin Li #define DEBUG_STORE_DATA(FILE_NAME, DATA_PTR, N_BYTES)
259*a58d3d2aSXin Li #define SILK_DEBUG_STORE_CLOSE_FILES
260*a58d3d2aSXin Li 
261*a58d3d2aSXin Li #endif /* SILK_DEBUG */
262*a58d3d2aSXin Li 
263*a58d3d2aSXin Li #ifdef  __cplusplus
264*a58d3d2aSXin Li }
265*a58d3d2aSXin Li #endif
266*a58d3d2aSXin Li 
267*a58d3d2aSXin Li #endif /* SILK_DEBUG_H */
268