Skip to content

Commit e24aa97

Browse files
committed
Segger RTT: support CONFIG_SEGGER_RTT_INIT_MODE and optimizations
* Different initialization modes of Control Block * Safer INIT() like in SystemView V352a * Made _aTerminalId const like in SystemView V352a Signed-off-by: Giancarlo Stasi <[email protected]>
1 parent b011c45 commit e24aa97

File tree

1 file changed

+41
-3
lines changed

1 file changed

+41
-3
lines changed

SEGGER/SEGGER_RTT.c

Lines changed: 41 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -254,7 +254,9 @@ Additional information:
254254
**********************************************************************
255255
*/
256256

257-
static unsigned char _aTerminalId[16] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
257+
static const unsigned char _aTerminalId[16] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
258+
259+
static const char _aInitStr[] = "\0\0\0\0\0\0TTR REGGES"; // Init complete ID string to make sure that things also work if RTT is linked to a no-init memory area
258260

259261
/*********************************************************************
260262
*
@@ -309,15 +311,14 @@ static unsigned char _ActiveTerminal;
309311
volatile SEGGER_RTT_CB* pRTTCBInit; \
310312
pRTTCBInit = (volatile SEGGER_RTT_CB*)((char*)&_SEGGER_RTT + SEGGER_RTT_UNCACHED_OFF); \
311313
do { \
312-
if (pRTTCBInit->acID[0] == '\0') { \
314+
if (pRTTCBInit->acID[0] != 'S') { \
313315
_DoInit(); \
314316
} \
315317
} while (0); \
316318
}
317319

318320
static void _DoInit(void) {
319321
volatile SEGGER_RTT_CB* p; // Volatile to make sure that compiler cannot change the order of accesses to the control block
320-
static const char _aInitStr[] = "\0\0\0\0\0\0TTR REGGES"; // Init complete ID string to make sure that things also work if RTT is linked to a no-init memory area
321322
unsigned i;
322323
//
323324
// Initialize control block
@@ -1892,6 +1893,28 @@ int SEGGER_RTT_SetFlagsDownBuffer(unsigned BufferIndex, unsigned Flags) {
18921893
return r;
18931894
}
18941895

1896+
#if defined(CONFIG_SEGGER_RTT_INIT_MODE_STRONG_CHECK)
1897+
static void SEGGER_RTT_StrongCheckInit(void) {
1898+
volatile SEGGER_RTT_CB* p;
1899+
p = (volatile SEGGER_RTT_CB*)((char*)&_SEGGER_RTT + SEGGER_RTT_UNCACHED_OFF);
1900+
unsigned i;
1901+
bool DoInit = false;
1902+
1903+
RTT__DMB(); // Force order of memory accesses for cores that may perform out-of-order memory accesses
1904+
for (i = 0; i < sizeof(_aInitStr) - 1; ++i) {
1905+
if (p->acID[i] != _aInitStr[sizeof(_aInitStr) - 2 - i]) { // Skip terminating \0 at the end of the array
1906+
DoInit = true;
1907+
break;
1908+
}
1909+
}
1910+
RTT__DMB(); // Force order of memory accesses for cores that may perform out-of-order memory accesses
1911+
1912+
if (DoInit) {
1913+
_DoInit();
1914+
}
1915+
}
1916+
#endif
1917+
18951918
/*********************************************************************
18961919
*
18971920
* SEGGER_RTT_Init
@@ -1902,7 +1925,22 @@ int SEGGER_RTT_SetFlagsDownBuffer(unsigned BufferIndex, unsigned Flags) {
19021925
*
19031926
*/
19041927
void SEGGER_RTT_Init (void) {
1928+
/*
1929+
* The standard Segger code calls only _DoInit() here. This happens,
1930+
* for example, in a bootloader or in stand-alone applications.
1931+
* For applications started by a bootloader, Segger recommends not
1932+
* calling this function, as all the recommended APIs use INIT().
1933+
* Unfortunately Zephyr log backend uses SEGGER_RTT_WriteSkipNoLock()
1934+
* that doesn't call INIT(), so the additional two following variants
1935+
* have been added here for a safe API usage.
1936+
*/
1937+
#if defined(CONFIG_SEGGER_RTT_INIT_MODE_STRONG_CHECK)
1938+
SEGGER_RTT_StrongCheckInit();
1939+
#elif defined(CONFIG_SEGGER_RTT_INIT_MODE_WEAK_CHECK)
1940+
INIT();
1941+
#else
19051942
_DoInit();
1943+
#endif
19061944
}
19071945

19081946
/*********************************************************************

0 commit comments

Comments
 (0)