This is an automated email from the ASF dual-hosted git repository.

lupyuen pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git


The following commit(s) were added to refs/heads/master by this push:
     new f401467a94e arch/tricore: add TriCore up_backtrace() support
f401467a94e is described below

commit f401467a94e81332506fa9c3e1a3f53d2facbfb8
Author: donghaokun <[email protected]>
AuthorDate: Tue May 19 11:14:26 2026 +0800

    arch/tricore: add TriCore up_backtrace() support
    
    Implement up_backtrace() for TriCore by walking the CSA chain and
    collecting return addresses from upper CSA A11 register.
    
    Signed-off-by: LukeKun <[email protected]>
---
 arch/Kconfig                                |   1 +
 arch/tricore/src/common/CMakeLists.txt      |   1 +
 arch/tricore/src/common/Make.defs           |   1 +
 arch/tricore/src/common/tricore_backtrace.c | 132 ++++++++++++++++++++++++++++
 4 files changed, 135 insertions(+)

diff --git a/arch/Kconfig b/arch/Kconfig
index 8f3e23dd9c0..7cd6ec4f10d 100644
--- a/arch/Kconfig
+++ b/arch/Kconfig
@@ -197,6 +197,7 @@ config ARCH_SPARC
 
 config ARCH_TRICORE
        bool "Infineon TriCore"
+       select ARCH_HAVE_BACKTRACE
        select ARCH_HAVE_INTERRUPTSTACK
        select ARCH_HAVE_STACKCHECK
        select ARCH_HAVE_SYSCALL_HOOKS
diff --git a/arch/tricore/src/common/CMakeLists.txt 
b/arch/tricore/src/common/CMakeLists.txt
index 6832abebe62..19bcfe4f7eb 100644
--- a/arch/tricore/src/common/CMakeLists.txt
+++ b/arch/tricore/src/common/CMakeLists.txt
@@ -22,6 +22,7 @@
 
 set(SRCS
     tricore_allocateheap.c
+    tricore_backtrace.c
     tricore_cache.c
     tricore_checkstack.c
     tricore_createstack.c
diff --git a/arch/tricore/src/common/Make.defs 
b/arch/tricore/src/common/Make.defs
index ccff2af627d..4817dc830c0 100644
--- a/arch/tricore/src/common/Make.defs
+++ b/arch/tricore/src/common/Make.defs
@@ -23,6 +23,7 @@
 HEAD_CSRC += tricore_doirq.c
 
 CMN_CSRCS += tricore_allocateheap.c
+CMN_CSRCS += tricore_backtrace.c
 CMN_CSRCS += tricore_cache.c
 CMN_CSRCS += tricore_checkstack.c
 CMN_CSRCS += tricore_createstack.c
diff --git a/arch/tricore/src/common/tricore_backtrace.c 
b/arch/tricore/src/common/tricore_backtrace.c
new file mode 100644
index 00000000000..11679ca74e8
--- /dev/null
+++ b/arch/tricore/src/common/tricore_backtrace.c
@@ -0,0 +1,132 @@
+/****************************************************************************
+ * arch/tricore/src/common/tricore_backtrace.c
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+#include <nuttx/arch.h>
+#include "sched/sched.h"
+#include "tricore_internal.h"
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: backtrace
+ *
+ * Description:
+ *  backtrace() parsing the return address through A11 register
+ *
+ ****************************************************************************/
+
+nosanitize_address
+static int backtrace(uintptr_t pcxi, void **buffer, int size, int *skip)
+{
+  int i = 0;
+
+  for (; ((pcxi & FCX_FREE) != 0U) && (i < size); )
+    {
+      uintptr_t *csa;
+
+      csa = tricore_csa2addr(pcxi);
+      if (csa == NULL)
+        {
+          break;
+        }
+
+      if ((pcxi & PCXI_UL) != 0U)
+        {
+          if ((*skip)-- <= 0)
+            {
+              buffer[i++] = (void *)csa[REG_UA11];
+            }
+        }
+
+      pcxi = csa[0];
+    }
+
+  return i;
+}
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: up_backtrace
+ *
+ * Description:
+ *  up_backtrace()  returns  a backtrace for the TCB, in the array
+ *  pointed to by buffer.  A backtrace is the series of currently active
+ *  function calls for the program.  Each item in the array pointed to by
+ *  buffer is of type void *, and is the return address from the
+ *  corresponding stack frame.  The size argument specifies the maximum
+ *  number of addresses that can be stored in buffer.   If  the backtrace is
+ *  larger than size, then the addresses corresponding to the size most
+ *  recent function calls are returned; to obtain the complete backtrace,
+ *  make sure that buffer and size are large enough.
+ *
+ * Input Parameters:
+ *   tcb    - Address of the task's TCB
+ *   buffer - Return address from the corresponding stack frame
+ *   size   - Maximum number of addresses that can be stored in buffer
+ *   skip   - number of addresses to be skipped
+ *
+ * Returned Value:
+ *   up_backtrace() returns the number of addresses returned in buffer
+ *
+ * Assumptions:
+ *   Have to make sure tcb keep safe during function executing, it means
+ *   1. Tcb have to be self or not-running.  In SMP case, the running task
+ *      PC & SP cannot be backtrace, as whose get from tcb is not the newest.
+ *   2. Tcb have to keep not be freed.  In task exiting case, have to
+ *      make sure the tcb get from pid and up_backtrace in one critical
+ *      section procedure.
+ *
+ ****************************************************************************/
+
+int up_backtrace(struct tcb_s *tcb, void **buffer, int size, int skip)
+{
+  struct tcb_s *rtcb = running_task();
+  int ret;
+
+  if (size <= 0 || !buffer)
+    {
+      return 0;
+    }
+
+  if (tcb == NULL || tcb == rtcb)
+    {
+      ret = backtrace((uintptr_t)__mfcr(CPU_PCXI),
+                      buffer, size, &skip);
+    }
+  else
+    {
+      ret = backtrace(tricore_addr2csa(tcb->xcp.regs),
+                      buffer, size, &skip);
+    }
+
+  return ret;
+}

Reply via email to