summaryrefslogtreecommitdiffstats
path: root/src/usr
diff options
context:
space:
mode:
authorCamVan Nguyen <ctnguyen@us.ibm.com>2011-06-23 13:51:42 -0500
committerA. Patrick Williams III <iawillia@us.ibm.com>2011-07-01 09:05:29 -0500
commita62f6ced825e39e2f96ea207818c6a75b75744ab (patch)
tree601917015a675a6378f5c873782d038164653471 /src/usr
parent4021070c48ff9dbb8730006ff01b83b5b8051fc5 (diff)
downloadtalos-hostboot-a62f6ced825e39e2f96ea207818c6a75b75744ab.tar.gz
talos-hostboot-a62f6ced825e39e2f96ea207818c6a75b75744ab.zip
Added support for individual trace buffers
Change-Id: Ief2834b241df6ca2ab13ee2a440d9f081399e252 Reviewed-on: http://gfw160.austin.ibm.com:8080/gerrit/156 Tested-by: Jenkins Server Reviewed-by: A. Patrick Williams III <iawillia@us.ibm.com>
Diffstat (limited to 'src/usr')
-rw-r--r--src/usr/example/example.C2
-rw-r--r--src/usr/trace/test/tracetest.H47
-rw-r--r--src/usr/trace/trace.C201
3 files changed, 223 insertions, 27 deletions
diff --git a/src/usr/example/example.C b/src/usr/example/example.C
index 290d8abc4..287721e5a 100644
--- a/src/usr/example/example.C
+++ b/src/usr/example/example.C
@@ -7,9 +7,11 @@
#include <example/examplerc.H>
#include <errl/errlentry.H>
+#if 0
//static mutex_t value = MUTEX_INITIALIZER;
trace_desc_t *g_trac_test = NULL;
TRAC_INIT(&g_trac_test, "EXAMPLE", 4096);
+#endif
extern "C"
void _start(void *ptr)
diff --git a/src/usr/trace/test/tracetest.H b/src/usr/trace/test/tracetest.H
index 0767352c6..5b8e3d29b 100644
--- a/src/usr/trace/test/tracetest.H
+++ b/src/usr/trace/test/tracetest.H
@@ -10,6 +10,7 @@
#include <cxxtest/TestSuite.H>
//#include <trace/interface.H>
#include <tracinterface.H>
+#include <stdio.h>
class TraceTest : public CxxTest::TestSuite
{
@@ -123,6 +124,52 @@ public:
}
}
}
+
+ /**
+ * @test Test max component name size
+ */
+ void testTracCompName(void)
+ {
+ trace_desc_t *g_trac_test = NULL;
+ char l_comp[] = "EXAMPLE89ABCDEFGHI";
+
+ TRAC_INIT_BUFFER(&g_trac_test, l_comp, 4096);
+
+ if(g_trac_test == NULL)
+ {
+ TS_FAIL("g_trac_test was returned as NULL!");
+ }
+ else
+ {
+ TRACFCOMP(g_trac_test, INFO_MRK"Testing max component name");
+ }
+ }
+
+ /**
+ * @test Test max number of buffers
+ */
+ void testTracMaxBuffers(void)
+ {
+ trace_desc_t *g_trac_test = NULL;
+ char l_comp[8] = "TRACE";
+
+ for (uint32_t i=0; i < 26; i++)
+ {
+ sprintf (l_comp, "TRACE%d", i);
+
+ g_trac_test = NULL;
+ TRAC_INIT_BUFFER(&g_trac_test, l_comp, 4096);
+
+ if(g_trac_test == NULL)
+ {
+ TS_FAIL("g_trac_test was returned as NULL!");
+ }
+ else
+ {
+ TRACFCOMP(g_trac_test, INFO_MRK"Testing max buffers %u", i);
+ }
+ }
+ }
};
#endif
diff --git a/src/usr/trace/trace.C b/src/usr/trace/trace.C
index 569af1e08..cdad6103c 100644
--- a/src/usr/trace/trace.C
+++ b/src/usr/trace/trace.C
@@ -15,6 +15,7 @@
#include <stdarg.h>
#include <arch/ppc.H>
#include <kernel/console.H>
+#include <kernel/pagemgr.H>
#include <limits.h>
#include <stdlib.h>
#include <sys/task.h>
@@ -37,12 +38,30 @@ const uint32_t TRAC_TIME_REAL = 0; // upper 32 = seconds, lower 32 = microsec
const uint32_t TRAC_TIME_50MHZ = 1;
const uint32_t TRAC_TIME_200MHZ = 2;
const uint32_t TRAC_TIME_167MHZ = 3; // 166666667Hz
-const uint32_t COMP_NAME_SIZE = 16;
+const uint32_t COMP_NAME_SIZE = 16; // NULL terminated string
-const uint64_t TRAC_DEFAULT_BUFFER_SIZE = 0x1000;
+// Initial implementation is to allocate a fixed 2KB buffer to each
+// component on request.
+// NOTE: any change to this value will require change to Trace::initBuffer()
+// since currently malloc() does not work for large allocations/fragmentations
+// and we are using PageManager::allocatePage() to allocate space for two
+// buffers at a time. Once malloc() works, we can remove this constraint.
+const uint64_t TRAC_DEFAULT_BUFFER_SIZE = 0x0800; //2KB
-// Global trace buffer. - Keep global so it can be found in syms file
-trace_desc_t *g_trac_global = NULL;
+// NOTE: This constant should only be changed to an even number for now.
+// Same reason as above.
+const uint64_t TRAC_MAX_NUM_BUFFERS = 24;
+
+const char * const TRAC_DEFAULT_BUFFER_NAME = "DEFAULT";
+
+// Global component trace buffer array. Initially allow for 24 buffers max.
+// Keep global so it can be found in syms file
+typedef struct trace_desc_array {
+ char comp[COMP_NAME_SIZE]; // the buffer name
+ trace_desc_t * td_entry; // pointer to the buffer
+}trace_desc_array_t;
+
+trace_desc_array_t g_desc_array[TRAC_MAX_NUM_BUFFERS];
/******************************************************************************/
// Trace::getTheInstance
@@ -59,10 +78,7 @@ Trace::Trace()
{
mutex_init(&iv_trac_mutex);
- g_trac_global = static_cast<trace_desc_t *>(malloc(TRAC_DEFAULT_BUFFER_SIZE));
-
- initValuesBuffer(g_trac_global,
- "GLOBAL");
+ memset(g_desc_array, 0, sizeof(g_desc_array));
}
/******************************************************************************/
@@ -83,15 +99,125 @@ void Trace::initBuffer(trace_desc_t **o_td, const char* i_comp,
/*------------------------------------------------------------------------*/
/* Local Variables */
/*------------------------------------------------------------------------*/
+ uint32_t i = 0;
+ char * l_td = NULL;
+ char l_comp[COMP_NAME_SIZE] = {'\0'};
/*------------------------------------------------------------------------*/
/* Code */
/*------------------------------------------------------------------------*/
if(*o_td == NULL)
{
- // Just assign it to the global buffer since we only have
- // one buffer
- *o_td = g_trac_global;
+ // Limit component name to 15 characters.
+ // Too bad we don't have strncpy(), strncmp()
+ if (strlen(i_comp) > (COMP_NAME_SIZE -1))
+ {
+ memcpy(l_comp, i_comp, COMP_NAME_SIZE - 1);
+ }
+ else
+ {
+ strcpy(l_comp, i_comp);
+ }
+
+ // CRITICAL REGION START
+ mutex_lock(&iv_trac_mutex);
+
+ // Search through the descriptor array for the first unallocated buffer.
+ // The last buffer is the reserved default buffer for any component
+ // which didn't get its own buffer.
+ for (i = 0; i < (TRAC_MAX_NUM_BUFFERS - 1); i++)
+ {
+ if(!strcmp(l_comp, g_desc_array[i].comp))
+ {
+ //printk("Trace::initBuffer - buffer already allocated %d\n", i);
+
+ // Buffer is already allocated. Return the buffer.
+ *o_td = g_desc_array[i].td_entry;
+
+ break;
+ }
+ else if (strlen(g_desc_array[i].comp) == 0)
+ {
+ //printk("Trace::initBuffer - found unallocated buffer %d\n", i);
+
+ // Found the first unallocated buffer; use this one.
+
+ // Set the component name for the buffer
+ strcpy(g_desc_array[i].comp, l_comp);
+
+ // Allocate memory if needed
+ if (NULL == g_desc_array[i].td_entry)
+ {
+ //printk("Trace::initBuffer - allocate memory\n");
+
+ // Allocate memory for two buffers.
+ // Once malloc() works, we can allocate memory for one
+ // one buffer at a time.
+ l_td = static_cast<char *>(PageManager::allocatePage());
+
+ g_desc_array[i].td_entry =
+ reinterpret_cast<trace_desc_t *>(l_td);
+
+ g_desc_array[i+1].td_entry =
+ reinterpret_cast<trace_desc_t *>(
+ l_td + TRAC_DEFAULT_BUFFER_SIZE);
+ }
+
+ // Initialize the buffer header
+ initValuesBuffer(g_desc_array[i].td_entry,
+ g_desc_array[i].comp);
+
+ // Return the newly allocated buffer
+ *o_td = g_desc_array[i].td_entry;
+
+ break;
+ }
+ }
+
+ if ((TRAC_MAX_NUM_BUFFERS - 1) == i)
+ {
+ //printk("Trace::initBuffer - allocate default buffer %d\n", i);
+
+ // We're out of buffers to allocate.
+ // Use the default buffer reserved for everyone else.
+ // Initialize only once
+ if (strlen(g_desc_array[i].comp) == 0)
+ {
+ // Set the component name for the buffer
+ strcpy(g_desc_array[i].comp, TRAC_DEFAULT_BUFFER_NAME);
+
+ // Allocate memory if needed
+ // Memory should have already been reserved if
+ // TRAC_MAX_NUM_BUFFERS is an even # and we're using
+ // PageManager::allocatePage(). Add check just in
+ // case TRAC_MAC_NUM_BUFFERS is set to an odd number.
+ if (NULL == g_desc_array[i].td_entry)
+ {
+ //printk("Trace::initBuffer - allocate memory\n");
+
+ // Allocate memory for buffer
+ l_td = static_cast<char *>(PageManager::allocatePage());
+
+ // Throw away the last 2KB for now to keep code simple
+ // until we decide to add support for variable-sized
+ // buffers. Also, once we change to use malloc(),
+ // we won't have this problem.
+ g_desc_array[i].td_entry =
+ reinterpret_cast<trace_desc_t *>(l_td);
+ }
+
+ // Initialize the buffer header
+ initValuesBuffer(g_desc_array[i].td_entry,
+ g_desc_array[i].comp);
+ }
+
+ // Return the default buffer
+ *o_td = g_desc_array[i].td_entry;
+ }
+
+ mutex_unlock(&iv_trac_mutex);
+ // CRITICAL REGION END
+
}
return;
@@ -166,7 +292,7 @@ void Trace::trace_adal_write_all(trace_desc_t *io_td,
// need to add that on to total size
l_entry_size += sizeof(uint32_t);
- // Now add on size for acutal number of arguments we're tracing
+ // Now add on size for actual number of arguments we're tracing
l_entry_size += (num_args * sizeof(uint64_t));
// Word align the entry
@@ -407,36 +533,57 @@ void Trace::convertTime(trace_entry_stamp_t *o_entry)
}
/******************************************************************************/
-// getTd - TODO
+// getTd
/******************************************************************************/
trace_desc_t * Trace::getTd(const char *i_comp)
{
/*------------------------------------------------------------------------*/
/* Local Variables */
/*------------------------------------------------------------------------*/
- //uint32_t l_num_des = 0;
- //uint32_t i=0;
- //trace_desc_t * l_td = NULL;
+ uint32_t i=0;
+ trace_desc_t * l_td = NULL;
+ char l_comp[COMP_NAME_SIZE] = {'\0'};
/*------------------------------------------------------------------------*/
/* Code */
/*------------------------------------------------------------------------*/
-#if 0
- l_num_des = sizeof(g_des_array) / sizeof(trace_descriptor_array_t);
-
- for(i=0;i<l_num_des;i++)
+ if (strlen(i_comp) != 0)
{
- if(memcmp(i_comp,(g_des_array[i].entry)->comp,(size_t)COMP_NAME_SIZE) == 0)
+ // Limit component name to 15 characters.
+ if (strlen(i_comp) > (COMP_NAME_SIZE -1))
{
- // Found the component
- l_td = g_des_array[i].entry;
- break;
+ memcpy(l_comp, i_comp, COMP_NAME_SIZE - 1);
+ }
+ else
+ {
+ strcpy(l_comp, i_comp);
+ }
+
+ // Search all allocated component buffers
+ for(i=0;
+ (i < (TRAC_MAX_NUM_BUFFERS - 1)) &&
+ (strlen(g_desc_array[i].comp) != 0);
+ i++)
+ {
+ if(!strcmp(l_comp, g_desc_array[i].comp))
+ {
+ // Found the component buffer
+ l_td = g_desc_array[i].td_entry;
+ break;
+ }
+ }
+
+ if (((TRAC_MAX_NUM_BUFFERS - 1) == i) &&
+ (strlen(g_desc_array[i].comp) != 0))
+
+ {
+ // Must be the default buffer
+ l_td = g_desc_array[i].td_entry;
}
}
-#endif
- // Only one trace buffer currently
- return(g_trac_global);
+
+ return(l_td);
}
/******************************************************************************/
OpenPOWER on IntegriCloud