comparison g23m-gsm/dl/dl_trace.c @ 0:75a11d740a02

initial import of gsm-fw from freecalypso-sw rev 1033:5ab737ac3ad7
author Mychaela Falconia <falcon@freecalypso.org>
date Thu, 09 Jun 2016 00:02:41 +0000
parents
children
comparison
equal deleted inserted replaced
-1:000000000000 0:75a11d740a02
1 /*
2 +-----------------------------------------------------------------------------
3 | Project :
4 | Modul :
5 +-----------------------------------------------------------------------------
6 | Copyright 2002 Texas Instruments Berlin, AG
7 | All rights reserved.
8 |
9 | This file is confidential and a trade secret of Texas
10 | Instruments Berlin, AG
11 | The receipt of or possession of this file does not convey
12 | any rights to reproduce or disclose its contents or to
13 | manufacture, use, or sell anything it may describe, in
14 | whole, or in part, without the specific written consent of
15 | Texas Instruments Berlin, AG.
16 +-----------------------------------------------------------------------------
17 | Purpose : This Modul defines the offline trace functions
18 | for the component DL of the mobile station.
19 +-----------------------------------------------------------------------------
20 */
21
22 #ifndef DL_TRACE_C
23 #define DL_TRACE_C
24
25 #include "config.h"
26 #include "fixedconf.h"
27 #include "condat-features.h"
28
29 #define ENTITY_DL
30
31 /*==== INCLUDES ===================================================*/
32 #include "typedefs.h"
33 #include <string.h>
34 #include "vsi.h"
35 #include "pconst.cdg"
36 #include "custom.h"
37 #include "gsm.h"
38 #include "mon_dl.h"
39 #include "prim.h"
40 #include "pei.h"
41 #include "tok.h"
42 #include "ccdapi.h"
43 #include "dl.h"
44
45 /*==== EXPORT =====================================================*/
46 /*==== PRIVAT =====================================================*/
47 #if defined(DL_TRACE_ENABLED)
48 #ifdef OPTION_MULTITHREAD
49 #define TRACE_TYPE _ENTITY_PREFIXED(TRACE_TYPE)
50 #define CHANNEL _ENTITY_PREFIXED(CHANNEL)
51 #define STATES _ENTITY_PREFIXED(STATES)
52 #endif /* OPTION_MULTITHREAD */
53 LOCAL const char* const STATES[] = {
54 "INVALID",
55 "DISABLED",
56 "IDLE_DL",
57 "SUSPENDED",
58 "AWAITING_ESTABLISHMENT",
59 "MULTI_FRAME_ESTABLISHED",
60 "TIMER_RECOVERY",
61 "AWAITING_RELEASE"
62 };
63 LOCAL const char* const TRACE_TYPE[] = { "UL", "DL", "Ev", "St", "PL", "RR" };
64 LOCAL const char* const CH_TYPE[] = { " ", "SA", "SD", "FH", "FF", "CC", "BC", "PC", "PE", "CB", "BE" };
65 LOCAL const char SAPI_TYPE[] = { '0', '1', '2', '3', ' '};
66
67 LOCAL void array2hex (UBYTE *inarray, char *outarray, int size);
68
69 #if !defined(DL_IMMEDIATE_TRACE)
70
71 /*==== TEST TRACE ===================================================*/
72 #define TEST_ENTITY_DL
73
74 /*==== VARIABLES ==================================================*/
75 /*==== FUNCTIONS ==================================================*/
76 /*
77 * The Data Link Layer Trace is a cyclic buffer for
78 * debugging layer 2 problems.
79 *
80 * The buffer will be initialized at startup and will
81 * be filled by the function dl_trace() until it is full.
82 * The size of the buffer is IDLE_TRACE_SIZE.
83 *
84 * The content is
85 *
86 * trace_type (uplink, downlink, event state, alr_event, rr_event)
87 * Channel Type (SACCH, SDDCH, FACCH)
88 * real system clock
89 * State (DL states)
90 * pending disc request
91 * data (layer frame, eevnt strings, state)
92 *
93 * During IDLE mode (triggered by RX_PERIODIC_IND in ALR/TIL_main.c)
94 * an output is written to as SYST trace.
95 * (IDLE_TRACE_MAX_READED traces each trigger)
96 */
97
98 #define IDLE_TRACE_SIZE 512
99 #define IDLE_TRACE_MAX_READED 16
100
101 #if (((IDLE_TRACE_SIZE-1) & (~IDLE_TRACE_SIZE)) == (IDLE_TRACE_SIZE-1))
102 #define POWER_OF_2
103 #pragma message("IDLE_TRACE_SIZE is power of 2")
104 #else
105 #pragma message("IDLE_TRACE_SIZE is NOT power of 2")
106 #endif
107
108 typedef struct
109 {
110 UBYTE trace_type;
111 UBYTE ch_type;
112 UBYTE sapi;
113 T_TIME sysClock;
114 UBYTE disc_request;
115 UBYTE state;
116 UBYTE data [MAX_L2_FRAME_SIZE];
117 } T_IDLE_TRACE_DATA;
118
119 #ifdef OPTION_MULTITHREAD
120 #define IDLE_Trace_buffer _ENTITY_PREFIXED(IDLE_Trace_buffer)
121 #define IDLE_Trace_write_index _ENTITY_PREFIXED(IDLE_Trace_write_index)
122 #define IDLE_Trace_read_index _ENTITY_PREFIXED(IDLE_Trace_read_index)
123 #endif /* OPTION_MULTITHREAD */
124
125 GLOBAL T_IDLE_TRACE_DATA IDLE_Trace_buffer [IDLE_TRACE_SIZE];
126 GLOBAL USHORT IDLE_Trace_write_index = 0;
127 GLOBAL USHORT IDLE_Trace_read_index = 0;
128
129 LOCAL T_HANDLE sem_DL_TRC;
130
131 GLOBAL void dl_trace_init (void)
132 {
133 sem_DL_TRC = vsi_s_open (VSI_CALLER "DL_IDLE_TRACE",1);
134 if (sem_DL_TRC NEQ VSI_ERROR)
135 dl_trace_clear (0);
136 else
137 SYST_TRACE ("DL:canīt open semaphore \"DL_IDLE_TRACE\"");
138 }
139
140 GLOBAL void dl_trace_exit (void)
141 {
142 if (sem_DL_TRC NEQ VSI_ERROR)
143 vsi_s_close (VSI_CALLER sem_DL_TRC);
144 }
145
146 GLOBAL void dl_trace_clear ()
147 {
148 dl_trace_read_all (0); /* first, get all remaining traces (if exists) */
149
150 ENTER_CRITICAL_SECTION (sem_DL_TRC);
151 IDLE_Trace_write_index = IDLE_Trace_read_index = 0;
152 LEAVE_CRITICAL_SECTION (sem_DL_TRC);
153
154 TRACE_EVENT ("offline trace reset");
155 DL_OFFLINE_TRACE (TRACE_DL_EVENT, TRACE_CH_UNKNOWN, 0, "offline trace reset");
156 }
157
158 /*
159 +--------------------------------------------------------------------+
160 | PROJECT : GSM-PS (6147) MODULE : DL_COM |
161 | STATE : code ROUTINE : dl_trace |
162 +--------------------------------------------------------------------+
163
164 PURPOSE : Fill in a trace.
165
166 */
167 GLOBAL void dl_trace (UCHAR trace_type, UCHAR channel, UCHAR ch_type, UCHAR* data)
168 {
169 T_IDLE_TRACE_DATA* trace_data;
170 USHORT write_index1, write_index2;/* trace_size must not be greater than 2 */
171 UBYTE trace_size;
172
173 if (data)
174 {
175 #if defined (DISABLE_MEASREPORT_TRACE)
176 if ((ch_type EQ L2_CHANNEL_SACCH) AND
177 (data[2] EQ 0x01) AND
178 (data[3] EQ 0x03) AND
179 (data[4] EQ 0x49))
180 return;
181 #endif /* DISABLE_MEASREPORT_TRACE */
182
183 #if defined (DISABLE_EMPTY_UI)
184 if ((trace_type EQ TRACE_DOWNLINK) OR (trace_type EQ TRACE_UPLINK))
185 {
186 if ((ch_type EQ L2_CHANNEL_SACCH) AND
187 (data[3] EQ 0x03) AND
188 (data[4] EQ 0x01))
189 return;
190 else if (
191 (data[1] EQ 0x03) AND
192 (data[2] EQ 0x01))
193 return;
194 }
195 #endif /* DISABLE_EMPTY_UI */
196 }
197
198 TEST_SEMAPHORE (sem_DL_TRC);
199 ENTER_CRITICAL_SECTION(sem_DL_TRC);
200
201 trace_size = 1;
202 if ((trace_type EQ TRACE_PL_EVENT) OR (trace_type EQ TRACE_RR_EVENT))
203 {
204 if (data AND strlen ((char *)data) >= 23)
205 trace_size = 2;
206 }
207
208 #if defined(POWER_OF_2)
209 write_index1 = (IDLE_Trace_write_index + 1) & (IDLE_TRACE_SIZE - 1); /* if IDLE_TRACE_SIZE power of 2 */
210 write_index2 = (IDLE_Trace_write_index + trace_size) & (IDLE_TRACE_SIZE - 1); /* if IDLE_TRACE_SIZE power of 2 */
211 #else
212 write_index1 = (IDLE_Trace_write_index + 1) % IDLE_TRACE_SIZE; /* if IDLE_TRACE_SIZE not power of 2 */
213 write_index2 = (IDLE_Trace_write_index + trace_size) % IDLE_TRACE_SIZE; /* if IDLE_TRACE_SIZE not power of 2 */
214 #endif /* POWER_OF_2 */
215 if ((write_index1 NEQ IDLE_Trace_read_index) AND (write_index2 NEQ IDLE_Trace_read_index))
216 { /* buffer is not full */
217 trace_data = &IDLE_Trace_buffer[IDLE_Trace_write_index];
218
219 trace_data->trace_type = trace_type;
220 if ((trace_type EQ TRACE_PL_EVENT) OR (trace_type EQ TRACE_RR_EVENT))
221 {
222 trace_data->state = trace_size;
223 }
224 else
225 {
226 GET_INSTANCE_DATA;
227 trace_data->ch_type = ch_type;
228 switch (channel)
229 {
230 case C_SACCH0:
231 case C_DCCH0:
232 trace_data->disc_request = dl_data->dcch0_disc_request;
233 trace_data->state = dl_data->state [C_DCCH0];
234 trace_data->sapi = PS_SAPI_0;
235 break;
236 case C_DCCH3:
237 trace_data->disc_request = dl_data->dcch3_disc_request;
238 trace_data->state = dl_data->state [C_DCCH3];
239 trace_data->sapi = PS_SAPI_3;
240 break;
241 default:
242 trace_data->disc_request = 0;
243 trace_data->state = 0;
244 trace_data->sapi = NOT_PRESENT_8BIT;
245 break;
246 }
247 }
248
249 vsi_t_time (VSI_CALLER &trace_data->sysClock);
250
251 if (data)
252 {
253 memcpy (trace_data->data, data, MAX_L2_FRAME_SIZE);
254 if ((trace_type NEQ TRACE_UPLINK) AND (trace_type NEQ TRACE_DOWNLINK))
255 {
256 trace_data->data[MAX_L2_FRAME_SIZE-1] = 0;
257 }
258
259 if (trace_size EQ 2)
260 {
261 if (IDLE_Trace_write_index EQ (IDLE_TRACE_SIZE - 1))/* the last buffer index ? */
262 trace_data = &IDLE_Trace_buffer[0];/* -> overflow to the first buffer index */
263 else
264 trace_data++;
265 memcpy (trace_data->data, data+MAX_L2_FRAME_SIZE-1, MAX_L2_FRAME_SIZE-1);
266 trace_data->data[MAX_L2_FRAME_SIZE-1] = 0;
267 }
268 }
269
270 IDLE_Trace_write_index = write_index2;
271 }/* endif buffer is not full */
272
273 LEAVE_CRITICAL_SECTION (sem_DL_TRC);
274
275 #if defined(_SIMULATION_)
276 dl_trace_read (0);
277 #endif /* _SIMULATION_ */
278 }
279
280 /*
281 +--------------------------------------------------------------------+
282 | PROJECT : GSM-PS (6147) MODULE : DL_COM |
283 | STATE : code ROUTINE : dl_trace_read |
284 +--------------------------------------------------------------------+
285
286 PURPOSE : Fill in a trace.
287
288 */
289 GLOBAL void dl_trace_read_all ()
290 {
291 USHORT write_index, read_index;
292
293 do
294 {
295 dl_trace_read ();
296
297 ENTER_CRITICAL_SECTION (sem_DL_TRC);
298 write_index = IDLE_Trace_write_index;
299 read_index = IDLE_Trace_read_index;
300 LEAVE_CRITICAL_SECTION (sem_DL_TRC);
301 } while (read_index NEQ write_index);
302 }
303
304 GLOBAL void dl_trace_read ()
305 {
306 T_IDLE_TRACE_DATA* trace_data;
307 USHORT write_index, read_index, left;
308 UBYTE trace_size;
309 static char buffer[80];
310 UBYTE j, o, readed = 0;
311
312 TEST_SEMAPHORE (sem_DL_TRC);
313
314 ENTER_CRITICAL_SECTION (sem_DL_TRC);
315 write_index = IDLE_Trace_write_index;
316 read_index = IDLE_Trace_read_index;
317 LEAVE_CRITICAL_SECTION (sem_DL_TRC);
318
319 if (read_index EQ write_index)
320 {
321 #if defined (_TARGET_) AND !defined( GPRS ) AND defined(FF_GTI)
322 sleep_mode ();
323 #endif /* _TARGET_ AND !GPRS AND !FF_GTI */
324 return;
325 }
326
327 while (read_index NEQ write_index)
328 {
329 ENTER_CRITICAL_SECTION (sem_DL_TRC);
330 trace_data = &IDLE_Trace_buffer[read_index];
331 LEAVE_CRITICAL_SECTION (sem_DL_TRC);
332
333 #if defined(POWER_OF_2)
334 left = (write_index - read_index - 1) & (IDLE_TRACE_SIZE-1);
335 #else
336 left = (IDLE_TRACE_SIZE + write_index - read_index - 1) % IDLE_TRACE_SIZE;
337 #endif /* POWER_OF_2 */
338
339 if (trace_data->ch_type > ELEMENTS(CH_TYPE))
340 trace_data->ch_type = 0;
341
342 if (trace_data->sapi >= ELEMENTS (SAPI_TYPE))
343 trace_data->sapi = ELEMENTS (SAPI_TYPE) - 1;
344
345 trace_size = 1;/* default */
346 switch (trace_data->trace_type)
347 {
348 case TRACE_UPLINK:
349 case TRACE_DOWNLINK:
350 sprintf (buffer, "[%03d]:%07lu %c%d %s %s ",
351 left,
352 trace_data->sysClock,
353 trace_data->disc_request?'D':' ',
354 trace_data->state,
355 TRACE_TYPE[trace_data->trace_type],
356 CH_TYPE[trace_data->ch_type]);
357 o = strlen (buffer);
358 array2hex (trace_data->data, buffer+o, 23);
359 break;
360
361 case TRACE_DL_EVENT:
362 sprintf (buffer, "[%03d]:%07lu %c%d Ev %s%c %s",
363 left,
364 trace_data->sysClock,
365 trace_data->disc_request?'D':' ',
366 trace_data->state,
367 CH_TYPE[trace_data->ch_type],
368 SAPI_TYPE[trace_data->sapi],
369 trace_data->data);
370 break;
371
372 case TRACE_PL_EVENT:
373 case TRACE_RR_EVENT:
374 trace_size = trace_data->state;
375 if (trace_size EQ 2)
376 {
377 T_IDLE_TRACE_DATA *trace_data2;
378 if (read_index EQ (IDLE_TRACE_SIZE - 1))/* the last buffer index ? */
379 trace_data2 = &IDLE_Trace_buffer[0];/* -> overflow to the first buffer index */
380 else
381 trace_data2 = trace_data+1;
382
383 sprintf (buffer, "[%03d]:%07lu %d Ev %s %s%s",
384 left,
385 trace_data->sysClock,
386 trace_data->state,
387 TRACE_TYPE[trace_data->trace_type],
388 trace_data->data,
389 trace_data2->data);
390 }
391 else
392 {
393 sprintf (buffer, "[%03d]:%07lu %d Ev %s %s",
394 left,
395 trace_data->sysClock,
396 trace_data->state,
397 TRACE_TYPE[trace_data->trace_type],
398 trace_data->data);
399 }
400 break;
401
402 case TRACE_CHSTATE:
403 sprintf (buffer, "[%03d]:%07lu %c%d ST %s%c state=%s",
404 left,
405 trace_data->sysClock,
406 trace_data->disc_request?'D':' ',
407 trace_data->state,
408 CH_TYPE[trace_data->ch_type],
409 SAPI_TYPE[trace_data->sapi],
410 STATES[trace_data->state]);
411 break;
412
413 default:
414 buffer[0] = 0;
415 break;
416 }
417
418 if (buffer[0])
419 {
420 SYST_TRACE (buffer);
421 }
422 else
423 {
424 SYST_TRACE ("dl_trace_read() failed");
425 }
426
427 ENTER_CRITICAL_SECTION (sem_DL_TRC);
428 trace_data->sysClock = 0; /* readed */
429 IDLE_Trace_read_index += trace_size;
430 #if defined(POWER_OF_2)
431 IDLE_Trace_read_index &= (IDLE_TRACE_SIZE-1);/* if power of 2 */
432 #else
433 IDLE_Trace_read_index %= IDLE_TRACE_SIZE; /* if not power of 2 */
434 #endif /* POWER_OF_2 */
435 read_index = IDLE_Trace_read_index;
436 write_index = IDLE_Trace_write_index;
437 LEAVE_CRITICAL_SECTION (sem_DL_TRC);
438
439 if (readed++ >= IDLE_TRACE_MAX_READED)
440 break;
441 }/* endwhile */
442 }
443
444 #else /* DL_IMMEDIATE_TRACE */
445
446 #define IMM_TRACE_SIZE 2
447 typedef struct
448 {
449 UBYTE sapi;
450 T_TIME sysClock;
451 UBYTE disc_request;
452 UBYTE state;
453 UBYTE data [IMM_TRACE_SIZE*MAX_L2_FRAME_SIZE];
454 } T_TRACE_DATA;
455
456 #ifdef OPTION_MULTITHREAD
457 #define print_buffer _ENTITY_PREFIXED(print_buffer)
458 #define trace_buffer _ENTITY_PREFIXED(trace_buffer)
459 #endif /* OPTION_MULTITHREAD */
460 LOCAL char print_buffer[25+IMM_TRACE_SIZE*MAX_L2_FRAME_SIZE];
461 LOCAL T_TRACE_DATA trace_buffer;
462
463 /*
464 +--------------------------------------------------------------------+
465 | PROJECT : GSM-PS (6147) MODULE : DL_COM |
466 | STATE : code ROUTINE : dl_trace |
467 +--------------------------------------------------------------------+
468
469 PURPOSE : Fill in a trace.
470
471 */
472
473 GLOBAL void dl_fast_trace (UBYTE trace_type, UBYTE channel, UBYTE ch_type,
474 T_TIME trace_time, ULONG trace_mask, UBYTE* data)
475 {
476 T_TRACE_DATA* trace_data;
477 UBYTE o;
478
479 /* While TC_USER2 is set, measurements and empty frames will be traced always */
480 if (data AND ((trace_mask & TC_USER2) EQ 0))
481 {
482 if ((ch_type EQ L2_CHANNEL_SACCH) AND
483 (data[2] EQ 0x01) AND
484 (data[3] EQ 0x03) AND
485 (data[4] EQ 0x49))
486 return;
487
488 if ((trace_type EQ TRACE_DOWNLINK) OR (trace_type EQ TRACE_UPLINK))
489 {
490 if ((ch_type EQ L2_CHANNEL_SACCH) AND
491 (data[3] EQ 0x03) AND
492 (data[4] EQ 0x01))
493 return;
494 else if (
495 (data[1] EQ 0x03) AND
496 (data[2] EQ 0x01))
497 return;
498 }
499 }
500
501 trace_data = &trace_buffer;
502 trace_data->sysClock = trace_time;
503 if (!((trace_type EQ TRACE_PL_EVENT) OR (trace_type EQ TRACE_RR_EVENT)))
504 {
505 GET_INSTANCE_DATA;
506 switch (channel)
507 {
508 case C_SACCH0:
509 case C_DCCH0:
510 trace_data->disc_request = dl_data->dcch0_disc_request;
511 trace_data->state = dl_data->state [C_DCCH0];
512 trace_data->sapi = PS_SAPI_0;
513 break;
514 case C_DCCH3:
515 trace_data->disc_request = dl_data->dcch3_disc_request;
516 trace_data->state = dl_data->state [C_DCCH3];
517 trace_data->sapi = PS_SAPI_3;
518 break;
519 default:
520 trace_data->disc_request = 0;
521 trace_data->state = 0;
522 trace_data->sapi = NOT_PRESENT_8BIT;
523 break;
524 }
525 }
526
527 if (data)
528 {
529 if ((trace_type EQ TRACE_UPLINK) OR (trace_type EQ TRACE_DOWNLINK))
530 {
531 memcpy (trace_data->data, data, MAX_L2_FRAME_SIZE);
532 }
533 else
534 {
535 strncpy ((char *)trace_data->data, (char *)data, IMM_TRACE_SIZE*MAX_L2_FRAME_SIZE-1);
536 trace_data->data[IMM_TRACE_SIZE*MAX_L2_FRAME_SIZE-1] = 0;
537 }
538 }
539 else
540 {
541 trace_data->data[0] = 0;
542 }
543
544
545 if (ch_type > ELEMENTS(CH_TYPE))
546 ch_type = 0;
547
548 if (trace_data->sapi >= ELEMENTS (SAPI_TYPE))
549 trace_data->sapi = ELEMENTS (SAPI_TYPE) - 1;
550
551 switch (trace_type)
552 {
553 case TRACE_UPLINK:
554 case TRACE_DOWNLINK:
555 sprintf (print_buffer, "DLTRC:%07lu %c%d %s %s%c ",
556 trace_data->sysClock,
557 trace_data->disc_request?'D':' ',
558 trace_data->state,
559 TRACE_TYPE[trace_type],
560 CH_TYPE[ch_type],
561 SAPI_TYPE[trace_data->sapi]);
562 o = strlen (print_buffer);
563 array2hex (trace_data->data, print_buffer+o, 23);
564 break;
565
566 case TRACE_DL_EVENT:
567 sprintf (print_buffer, "DLTRC:%07lu %c%d Ev %s%c %s",
568 trace_data->sysClock,
569 trace_data->disc_request?'D':' ',
570 trace_data->state,
571 CH_TYPE[ch_type],
572 SAPI_TYPE[trace_data->sapi],
573 trace_data->data);
574 break;
575
576 case TRACE_PL_EVENT:
577 case TRACE_RR_EVENT:
578 sprintf (print_buffer, "DLTRC:%07lu %d Ev %s %s",
579 trace_data->sysClock,
580 trace_data->state,
581 TRACE_TYPE[trace_type],
582 trace_data->data);
583 break;
584
585 case TRACE_CHSTATE:
586 sprintf (print_buffer, "DLTRC:%07lu %c%d ST %s%c state=%s",
587 trace_data->sysClock,
588 trace_data->disc_request?'D':' ',
589 trace_data->state,
590 CH_TYPE[ch_type],
591 SAPI_TYPE[trace_data->sapi],
592 STATES[trace_data->state]);
593 break;
594
595 default:
596 print_buffer[0] = 0;
597 break;
598 }
599
600 TRACE_USER_CLASS (TC_USER1, print_buffer);
601
602 #if 0
603 if (print_buffer[0])
604 {
605 #if defined(_SIMULATION_)
606 TRACE_EVENT_WIN (print_buffer);
607 #else /* _SIMULATION_ */
608 SYST_TRACE_P ((DLTRC,print_buffer));
609 #endif /* _SIMULATION_ */
610 }
611 #endif /* 0 */
612 }
613 #endif /* DL_IMMEDIATE_TRACE */
614
615 LOCAL void array2hex (UBYTE *inarray, char *outarray, int size)
616 {
617 int col=0, n=0;
618 UBYTE b, nh, nl;
619
620 while (n < size)
621 {
622 b = inarray[n++];
623 nh = b>>4;
624 nl = b&0x0f;
625 outarray[col++] = nh > 9 ? nh + 'A' - 10 : nh + '0';
626 outarray[col++] = nl > 9 ? nl + 'A' - 10 : nl + '0';
627 }
628 outarray[col] = 0;
629 }
630 #endif /* DL_TRACE_ENABLED */
631
632 #if defined (DL_TRACE_PFREE)
633 GLOBAL void* my_pfree(void *pointer, int line, char *file)
634 {
635
636 char buffer[23];
637 sprintf (buffer, "%s#%u:%p", file+2, line, pointer);
638 dl_trace (TRACE_DL_EVENT, TRACE_CH_UNKNOWN, buffer);
639
640 if (pointer)
641 {
642 PFREE (pointer);
643 }
644 else
645 {
646 SYST_TRACE_P((SYST, "%s#%u: PFREE(NULL)", file, line));
647 }
648
649 return NULL;
650 }
651 #endif /* DL_TRACE_PFREE */
652
653 #endif /* DL_TRACE_C */