1 MPLAB® Harmony Class B Library for PIC32CM JH Devices

The Class B Library provides APIs to perform self-tests for the on-board systems of the microcontroller.

Features Tested by the Class B Library

Table 1-1. Components tested by the Class B library
Component

Reference (Table H1 of IEC 60730-1)

Fault/ErrorAcceptable Measures
CPU Registers1.1Stuck-atStatic memory test
CPU Program Counter1.3Stuck-atStatic memory test
Interrupts2No interrupt / too frequent interruptFunctional test
CPU Clock3Wrong frequencyFrequency monitoring
Flash4.1All single bit faultsModified checksum
SRAM4.2DC faultStatic memory test
SRAM data path5.1Stuck-atStatic memory test
SRAM data path5.2Wrong addressStatic memory test
Digital I/O7.1Abnormal operationInput comparison or output verification

Class B Peripheral Library Usage

This topic describes the basic architecture of the Class B library and provides information and examples on how to use it. APIs defined by the Class B library can be used either by the start-up code or by the application code. The application may use PLIBs, drivers or middleware from the Harmony 3 software framework along with the Class B library code.

Abstraction Model

The following picture shows positioning of Class B library in a Harmony 3 based application.

Start-up vs. Run-time

The Class B library contains many self-test routines those can be executed at startup and run-time. If a self-test is executed at startup, it is called as a Start-up Self-test (SST) and if it is executed at run-time, then it is called a Run-time Self-test (RST). There are a few self-tests which can be used only as SST or as RST, such self-tests have SST or RST in the API name eg: CLASSB_RST_IOTest(), CLASSB_SST_InterruptTest(). If a self-test API does not have SST or RST in its name, then it can be used at startup as well as runtime.

Start-up Self-test (SST)

SSTs are used to test a component inside the microcontroller before it is initialized and used. When the Class B library is added via MPLAB® Code Configurator (MCC), the selected SSTs are inserted into the _on_reset() function which is called from the Reset_Handler(). This means that none of the data initialization could have happened before running SSTs. So, the Class B library initializes necessary variables before using them. It is not mandatory to test all the components during startup. The SRAM can be tested partially if a faster startup is needed by the application. In this case, modify the corresponding configuration macro (CLASSB_SRAM_STARTUP_TEST_SIZE) present in classb.h file to change the size of the tested area.

Run-time Self-test (RST)

RSTs can be used by the application during run-time to check safe operation of different components in the microcontroller. These tests are non-destructive. In the case of run-time tests, the application shall decide which test to execute when.

Components in the Library

The Class B library contains self-test routines for different components listed in Table 1-1.

Critical and Non-critical Components

Based on the impact of failure, different components inside this Class B library are categorized as critical or non-critical.

If the self-test for CPU registers, PC or Flash detects a failure, the code execution is stopped, and it remains in an infinite loop. This is to prevent unsafe code execution. In the case of non-critical components, a failsafe function (CLASSB_SelfTest_FailSafe) is called when a failure is detected. This function contains a software break point and an infinite loop. Further code shall be added into this function as per the application need. The failsafe function must not return to the Class B library, since it is called due to a self-test failure. Avoid use of features which depend on the failed component. For example, if self-test for clock is failed, it is not advisable to use UART for error reporting as BAUD rate may not be accurate. In the case of SRAM failure, avoid the use of function calls or use of variables in SRAM. A simple error reporting mechanism in this case of SRAM failure can be toggling of an IO pin.

Critical Components

  1. CPU registers including the Program Counter
  2. Internal Flash program memory
Figure 1-1. Generic Flow of Critical Tests

Non-critical Components

  1. CPU clock
  2. IO pins
  3. Internal SRAM
  4. Interrupts
Figure 1-2. Generic Flow of Non-Critical Tests

Self-tests for Components in the Library

CPU Registers

The ARM® Cortex®-M0+ is the CPU on the PIC32CM JH devices. The Class B library checks the processor core registers for stuck-at faults. The stuck-at condition causes register bit to remain at logic 0 or logic 1. Code execution should be stopped if this error condition is detected in any of the CPU registers.

This self-test follows the register save/restore convention specified by AAPCS. It can be used at startup as well as run-time. The Program Counter (PC) self-test is designed as a separate test since this register cannot be checked with usual test data patterns.

Figure 1-3. Flow chart of the self-test for CPU registers

Program Counter (PC)

The self-test for PC checks whether a stuck-at condition is present in the PC register. The stuck-at condition causes register bit to remain at logic 0 or logic 1. Code execution should be stopped if this error condition is detected.

The self-test for PC calls multiple functions in predefined order and verifies that each function is executed and returns the expected value. If the return values of all test functions are correct, the Program Counter is assumed to be working fine. This self-test can be used at startup as well as run-time.

Figure 1-4. Flow chart of the self-test for Program Counter (PC)

Flash

The internal flash memory of the device needs to be checked for proper functionality. The NVMCTRL embeds a functional safety feature in the form of a ‘single-error correction’ and ‘double-error detection’ (SECDED) Hamming Error Correction Code (ECC). This feature applies to the main Flash memory panel, the Data Flash, the User Row, the Software Calibration Area, and the Serial Number. Each single bit error in any 64-bit word of these sections will be corrected seamlessly by the NVMCTRL (and not written back in memory). Each double bit error will be detected but not corrected. For each 64-bit word in the memory, 8 bits are added in memory for storing the ECC. The standalone ECC logic comes with a fault injection and capture logic, used for testing the ECC feature.

The routine to enable the ECC feature on the Flash memory is available in the Class B library and this routine is called in the startup if it is selected via the Harmony 3 MCC configuration.

SRAM

The SRAM on the device is tested during runtime with the help ECC feature on the device. The ECC feature is enabled by default after a reset, and can then be disabled and re-enabled using the CTRLA.ENABLE bit. This disabling/enabling only applies to ECC decoding upon reads. The ECC encoding upon writes is always enabled and cannot be disabled. More details are available in the datasheet chapter MCRAMC. During the startup, the SRAM is tested by the Class B library with the help of the SMBIST peripheral.

Clock

The self-test for CPU clock checks whether the CPU clock frequency is within the permissible range. It uses RTC and SysTick to measure the CPU clock frequency. The RTC is clocked at 32768 Hz from the 32 kHz External Crystal Oscillator and CPU clock can be from any other high frequency oscillator. If the CPU clock frequency is within specified error limit, it returns PASS. The test duration is defined by one of the input arguments. The clock self-test can be used at startup as well as run-time.

Notes:
  1. This self-test uses the RTC peripheral. Thus, if it is used during run-time, the RTC shall not be used by the application for continuous modes such as real time clock or calendar. If the RTC is used for some other purpose, it must be reconfigured after running the clock self-test.
  2. Keep the clock test duration lesser than the WDT timeout period, to avoid the WDT resetting the device.
Figure 1-5. Flow chart of the self-test for CPU clock frequency

Interrupt

The self-test for this element checks the interrupts functionality of the microcontroller. It configures the Nested Vectored Interrupt Controller (NVIC), the Real-Time Counter (RTC) and the Timer Counter 0 (TC0) peripherals to test the interrupt handling mechanism. It verifies that at least one interrupt is generated and handled properly. This self-test also checks whether the number of interrupts generated are too many within a given time period. It reports a PASS if the RTC has generated at least one interrupt and the total number of interrupts generated by the TC0 is greater than one and less than the specified upper limit. The clock used for RTC is 1kHz from the internal OSCULP32K and for TC0 the clock is same as the default CPU clock (48MHz from the DFLL48M). The interrupt self-test can be used only at startup.

Note:
  1. This startup self-test utilizes the interrupts generated by RTC and TC0. For run-time testing of interrupts, a separate self-test need to be developed.
Figure 1-6. Flow chart of the self-test for interrupts

IO pin

The self-test for IO pins verifies that any output pin is able to keep the configured logic state on the pin and any input pin is able to read the logic state present on the pin.

As the exact use of an IO pin is decide by the application, it is the responsibility of the application to configure the IO pin direction and drive the pin to the expected state before calling this self-test. Before testing an output pin, call CLASSB_IO_InputSamplingEnable() function to enable input sampling for the IO pin. When testing an input pin, ensure that the IO pin is externally kept at a defined logic state. The IO pin self-test can be used only at run-time.

Figure 1-7. Flow chart of the self-test for IO pins

Class B Peripheral Library - Timing of self-tests

Table 1-2. Peripherals other than Flash and SRAM
NameTime (in microseconds)
CLASSB_CPU_RegistersTest20
CLASSB_CPU_PCTest12
CLASSB_RST_IOTest8
CLASSB_ClockTest7650
CLASSB_SST_InterruptTest13800
Table 1-3. SRAM Startup Test
NameTime (in microseconds)Tested size
SRAM Memory Built-In Self-Test (SMBIST )300032 KB
Notes:
  1. Timing is measured using onchip peripherals (SysTick and TC) at optimization level -O1 with CPU running at 48MHz from the internal 48MHz oscillator. Before using these self-tests in an application it is recommended to check self-test timings with the required configuration (CPU clock, compiler optimization, memory size).
  2. During run-time, the internal Flash and the SRAM are monitored by the corresponding ECC peripherals. Thus no timing measurement is required.
  3. Following IDE and toolchain are used for timing measurements
    1. MPLAB X v6.10
    2. XC32 Compiler v4.30

Configuring the Library (MPLAB X)

This section provides details necessary to integrate the Class B library with other software components.

Optimization Requirements

The self-test routines provides by the Class B software does not have any specific optimization requirements.

Reserved SRAM area for the Class B library

Dedicated SRAM area is needed for the self-tests in the Class B library. This should help to prevent unintentional access to the area by the application. Initial 64 bytes of the SRAM 0x20000000 shall be reserved.

This reserved SRAM must not be accessed from outside the Class B library. To check or update test results, use the corresponding interface APIs. When the Class B library is added into the project with the help of MCC, the linker setting is modified by MCC as shown below. The numbers used in this example is for a device with 64kB of SRAM.

-DRAM_ORIGIN=0x20000040 -DRAM_LENGTH=0xffc0

Modified Startup Sequence

When generating project with help of MPLAB Harmony 3, the startup code is present in a file named startup_xc32. This file contains the Reset_Handler which has all startup code that runs before the main() function. Initialization of the Class B library is done from the _on_reset function which is the first function to be executed from the Reset_Handler. The function named CLASSB_Startup_Tests executes all startup self-tests inserted into classb.c file by the MCC. If none of the self-tests are failed, this function returns CLASSB_STARTUP_TEST_PASSED. If any of the startup self-tests are failed, this function does not return because of the following reason. In the case of critical failures (CPU registers or internal flash), the corresponding self-test remains in an infinite loop to avoid unsafe execution of code. The self-tests for SRAM, Clock and Interrupt are considered non-critical since it may be possible to execute a fail-safe function after detecting a failure. In such case, the CLASSB_SelfTest_FailSafe() function is called when a failure is detected. Since the default implementation of CLASSB_SelfTest_FailSafe routine contains an infinite loop, it won't return to the caller.

Note:
  1. The library defines the _on_reset function and handles some of the reset causes. The application developer shall insert functions to handle the rest of the reset causes.

WDT Test and Timeout

The Watchdog timer is used as a recovery mechanism in case of software failures. The Class B library enables the WDT and checks whether a WDT reset is issued if the timer is not cleared. In CLASSB_Startup_Tests (in file classb.c), before performing startup self-tests, the WDT timeout period is configured. It can be modified after generating the project. During startup, the device runs from 4 MHz internal clock. Before running any self-test which takes longer time (SRAM or Flash test), configuring the CPU clock at 48 MHz will help to reduce the execution time. If any of these self-tests takes more time than the WDT timeout period, it results in a WDT reset. Thus, properly configuring the WDT period is essential during startup as well as runtime.

Configuring Startup Tests via MCC

Clone the classb_pic32cm_jh repo. When an MPLAB Harmony 3 project is created, the MCC lists all available components that can be added to the project. The self-tests which need to run during startup can be configured via MCC. The Configuration Options menu appears with a mouse click on the Class B Library component inside the Project Graph. The configurations done via MCC does not configure the library, instead it helps to modify the input arguments and to decide whether to run a specific test during startup.

Class B Library Interface

Table 1-4. List of Constants
NameDescription
CLASSB_CLOCK_DEFAULT_CLOCK_FREQDefault CPU clock speed.
CLASSB_CLOCK_ERROR_PERCENTClock error percentage selected for startup test.
CLASSB_CLOCK_MAX_CLOCK_FREQMaximum CPU clock speed.
CLASSB_CLOCK_MAX_SYSTICK_VALUpper limit of SysTick counter.
CLASSB_CLOCK_MAX_TEST_ACCURACYMaximum detectable accuracy for clock self-test.
CLASSB_CLOCK_MUL_FACTORMultiplication factor used in clock test.
CLASSB_CLOCK_RTC_CLK_FREQRTC clock frequency.
CLASSB_CLOCK_TEST_RATIO_NS_MSRatio of mili second to nano second.
CLASSB_CLOCK_TEST_RTC_RATIO_NSDuration of RTC clock in nano seconds.
CLASSB_COMPL_RESULT_ADDRAddress of one's complement test results.
CLASSB_INTERRUPT_COUNT_VAR_ADDRAddress of the variable which keeps interrupt count.
CLASSB_INTERRUPT_TEST_VAR_ADDRAddress of the variable which keeps interrupt test internal status.
CLASSB_INTR_DEVICE_VECT_OFFSETDefines the offset for first device specific interrupt.
CLASSB_INTR_MAX_INT_COUNTDefines the upper limit for interrupt count.
CLASSB_INTR_TEST_RTC_COUNTDefines the counter value for RTC peripheral.
CLASSB_INTR_TEST_TC_COUNTDefines the counter value for TC0 peripheral.
CLASSB_INTR_VECTOR_TABLE_SIZEDefines the size of the vector table.
CLASSB_INVALID_TEST_IDInvalid test ID.
CLASSB_ONGOING_TEST_VAR_ADDRAddress at which the ID of ongoing test is stored.
CLASSB_RESULT_ADDRAddress of test results.
CLASSB_SRAM_APP_AREA_STARTDefines the start address of the SRAM for the application.
CLASSB_TEST_IN_PROG_VAR_ADDRAddress of the variable which indicates that a Class B test is in progress.
CLASSB_WDT_TEST_IN_PROG_VAR_ADDRAddress of the variable which indicates that a WDT test is in progress.
Table 1-5. List of Data Types
NameDescription
CLASSB_CPU_PC_TEST_VALUESData type for PC Test input and output values.
CLASSB_INIT_STATUSIdentifies Class B initialization status.
CLASSB_PORT_INDEXPORT index definitions for Class B library I/O pin test.
CLASSB_PORT_PINPIN definitions for Class B library I/O pin test.
CLASSB_PORT_PIN_STATEPORT pin state.
CLASSB_RST_RESULT_BFPointer to the structure for the Class B library run-time self-test result. This can be used to point to the result address 0x20000004. It will help to see the result in text form via watch window.
CLASSB_SST_RESULT_BFPointer to the structure for the Class B library startup self-test result. This can be used to point to the result address 0x20000000. It will help to see the result in text form via watch window.
CLASSB_STARTUP_STATUSIdentifies startup test status.
CLASSB_TEST_IDIdentifies Class B library tests.
CLASSB_TEST_STATEIdentifies Class B library test state.
CLASSB_TEST_STATUSIdentifies result from Class B library test.
CLASSB_TEST_TYPEIdentifies type of the Class B library test.
Table 1-6. List of Interface Routines
NameDescription
CLASSB_App_WDT_RecoveryThis function is called if a WDT reset has happened during run-time.
CLASSB_CPU_RegistersTestThis self-test checks the processor core registers.
CLASSB_CPU_PCTestThis self-test checks the Program Counter register (PC).
CLASSB_ClearTestResultsClears the results of SSTs or RSTs.
CLASSB_ClockTestThis self-test checks whether the CPU clock frequency is within the permissible limit.
CLASSB_FLASH_CallbackThis function is used for interrupt callback.
CLASSB_FLASH_ECC_InterruptHandlerThis function is called if FLASH ECC interrupt occurs.
CLASSB_FLASH_EccInitInitialize ECC to perform fault detection on FLASH.
CLASSB_GetTestResultReturns the result of the specified self-test.
CLASSB_GlobalsInitThis function initializes the global variables for the classb library.
CLASSB_IO_InputSamplingEnableEnable input sampling for an IO pin.
CLASSB_InitThis function is executed on every device reset. This shall be called right after the reset, before any other initialization is performed.
CLASSB_SelfTest_FailSafeThis function is called if any of the non-critical tests detects a failure.
CLASSB_SRAM_CallbackThis function is used for interrupt callback.
CLASSB_SRAM_ECC_InterruptHandlerThis function is called if SRAM ECC interrupt occurs.
CLASSB_SRAM_EccInitInitialize ECC to perform fault detection on SRAM.
CLASSB_SST_InterruptTestThis self-test checks basic functionality of the interrupt handling mechanism.
CLASSB_SST_WDT_RecoveryThis function is called if a WDT reset has happened during the execution of an SST.
CLASSB_Startup_TestsThis function executes all startup self-tests inserted into classb.c file.
CLASSB_RST_IOTestThis self-test can be used to perform plausibility checks on IO pins.
CLASSB_TestWDTThis function tests the WatchDog Timer (WDT).