|
Packit Service |
d40955 |
/*
|
|
Packit Service |
d40955 |
* Copyright (c) 2020 Red Hat, Inc.
|
|
Packit Service |
d40955 |
*
|
|
Packit Service |
d40955 |
* This program is free software; you can redistribute it and/or
|
|
Packit Service |
d40955 |
* modify it under the terms of the GNU General Public License
|
|
Packit Service |
d40955 |
* as published by the Free Software Foundation; either version 2
|
|
Packit Service |
d40955 |
* of the License, or (at your option) any later version.
|
|
Packit Service |
d40955 |
*
|
|
Packit Service |
d40955 |
* This program is distributed in the hope that it will be useful,
|
|
Packit Service |
d40955 |
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
Packit Service |
d40955 |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
Packit Service |
d40955 |
* GNU General Public License for more details.
|
|
Packit Service |
d40955 |
*
|
|
Packit Service |
d40955 |
* You should have received a copy of the GNU General Public License
|
|
Packit Service |
d40955 |
* along with this program; if not, write to the Free Software
|
|
Packit Service |
d40955 |
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
|
Packit Service |
d40955 |
* 02110-1301, USA.
|
|
Packit Service |
d40955 |
*
|
|
Packit Service |
d40955 |
* $Id: //eng/vdo-releases/aluminum/src/c++/vdo/base/trace.c#1 $
|
|
Packit Service |
d40955 |
*/
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
#include "trace.h"
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
#include "logger.h"
|
|
Packit Service |
d40955 |
#include "stringUtils.h"
|
|
Packit Service |
d40955 |
#include "timeUtils.h"
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
TRACE_LOCATION_SECTION TraceLocationRecord baseTraceLocation[] = {
|
|
Packit Service |
d40955 |
{
|
|
Packit Service |
d40955 |
.function = "<none>",
|
|
Packit Service |
d40955 |
.line = 0,
|
|
Packit Service |
d40955 |
},
|
|
Packit Service |
d40955 |
};
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
/**********************************************************************/
|
|
Packit Service |
d40955 |
void addTraceRecord(Trace *trace, TraceLocation location)
|
|
Packit Service |
d40955 |
{
|
|
Packit Service |
d40955 |
if (trace->used < NUM_TRACE_RECORDS) {
|
|
Packit Service |
d40955 |
TraceRecord *record = &trace->records[trace->used];
|
|
Packit Service |
d40955 |
trace->used++;
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
record->when = nowUsec();
|
|
Packit Service |
d40955 |
record->tid = getThreadId();
|
|
Packit Service |
d40955 |
record->location = location - baseTraceLocation;
|
|
Packit Service |
d40955 |
}
|
|
Packit Service |
d40955 |
}
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
/*
|
|
Packit Service |
d40955 |
* The record display format used is a comma-separated list, each item
|
|
Packit Service |
d40955 |
* containing: optional function name; "@" + timestamp with seconds
|
|
Packit Service |
d40955 |
* and microseconds for the first record; if not the first record, "+"
|
|
Packit Service |
d40955 |
* and offset in microseconds from previous timestamp.
|
|
Packit Service |
d40955 |
*
|
|
Packit Service |
d40955 |
* If the buffer's too small, it'll end with an ellipsis.
|
|
Packit Service |
d40955 |
*/
|
|
Packit Service |
d40955 |
void formatTrace(Trace *trace,
|
|
Packit Service |
d40955 |
char *buffer,
|
|
Packit Service |
d40955 |
size_t bufferLength,
|
|
Packit Service |
d40955 |
size_t *msgLen)
|
|
Packit Service |
d40955 |
{
|
|
Packit Service |
d40955 |
if (trace == NULL) {
|
|
Packit Service |
d40955 |
return;
|
|
Packit Service |
d40955 |
}
|
|
Packit Service |
d40955 |
memset(buffer, 0, bufferLength);
|
|
Packit Service |
d40955 |
char *buf = buffer;
|
|
Packit Service |
d40955 |
char *bufferEnd = buffer + bufferLength - 1;
|
|
Packit Service |
d40955 |
if (trace->used > 0) {
|
|
Packit Service |
d40955 |
TraceRecord *record = &trace->records[0];
|
|
Packit Service |
d40955 |
TraceLocationRecord *location = baseTraceLocation + record->location;
|
|
Packit Service |
d40955 |
snprintf(buf, bufferEnd - buf, "Trace[%s@%llu.%06llu",
|
|
Packit Service |
d40955 |
location->function, record->when / 1000000,
|
|
Packit Service |
d40955 |
record->when % 1000000);
|
|
Packit Service |
d40955 |
buf += strlen(buf);
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
for (unsigned int i = 1; i < trace->used; i++) {
|
|
Packit Service |
d40955 |
TraceRecord *prev = record;
|
|
Packit Service |
d40955 |
record++;
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
snprintf(buf, bufferEnd - buf, ",");
|
|
Packit Service |
d40955 |
buf += strlen(buf);
|
|
Packit Service |
d40955 |
|
|
Packit Service |
d40955 |
location = baseTraceLocation + record->location;
|
|
Packit Service |
d40955 |
unsigned long timeDiff = record->when - prev->when;
|
|
Packit Service |
d40955 |
snprintf(buf, bufferEnd - buf, "%s+%lu",
|
|
Packit Service |
d40955 |
location->function, timeDiff);
|
|
Packit Service |
d40955 |
buf += strlen(buf);
|
|
Packit Service |
d40955 |
}
|
|
Packit Service |
d40955 |
if (bufferLength > 7) {
|
|
Packit Service |
d40955 |
if (buffer[bufferLength-5] != '\0') {
|
|
Packit Service |
d40955 |
// too long
|
|
Packit Service |
d40955 |
strcpy(buffer+bufferLength-5, "...]");
|
|
Packit Service |
d40955 |
} else {
|
|
Packit Service |
d40955 |
strcpy(buf, "]");
|
|
Packit Service |
d40955 |
}
|
|
Packit Service |
d40955 |
}
|
|
Packit Service |
d40955 |
}
|
|
Packit Service |
d40955 |
*msgLen = (buf - buffer);
|
|
Packit Service |
d40955 |
}
|