Bus Trace

Analyzer ›› Trace Concepts ››
Parent Previous Next

Contents

Contents        1

1.1        Preface        2

2        Trace Configuration Settings        2

2.1        Recorder        3

2.2        Trigger and Qualifier        4

2.3        AUX Signals        7

3        Troubleshooting Scenarios        8

3.1        Record everything        8

3.2        Plain Trigger/Qualifier Configuration        9

3.3        Watchdog Trigger        17

3.4        Duration Tracker        23

3.5        Q between B and C events        26

3.6        Pre/Post Qualifier        29

3.7        Data Change        35


1.1Preface

This document covers trace use on iSYSTEM debug and test tools featuring a so called bus trace. Bus trace means that the trace hardware can sample and capture microcontroller address and data bus value at every CPU cycle. Bus trace provides a very detailed insight into the microcontroller behavior during the program execution.

Bus trace exists on nearly all iSYSTEM in-circuit emulation tools. Additionally, it’s also available on iSYSTEM on-chip debug & test tools supporting Nexus trace or ARM ETM trace, on top of which iSYSTEM proprietary RTR (Real-Time Trace Reconstruction) technology is integrated.

List of debug & test tool configurations featuring bus trace:

iC1000 PowerEmulator (all supported architectures)

iC2000 PowerEmulator including PowerAnalyzer module (all supported architectures)

EM Microelectronic CoolRISC Active POD

Freescale 68HC08 Active PODs II

Freescale 68HCS12 Active PODs

Freescale MC9S12X ActivePRO/GT PODs

Freescale 68K ActiveGT PODs

Freescale 68332 ActiveGT POD

Renesas V850ES/Fx3 ActivePRO and ActiveGT POD

Renesas 78K0R and RL78 ActiveGT POD

Renesas 78K0 ActivePRO POD

Renesas R8C/3x ActivePRO POD

iTRACE PRO/GT & ARM ARM7 ETM (RTR)

iTRACE PRO/GT & Freescale MPC5553/5554, MPC5561/5565/5566/5567 (RTR)

iTRACE GT & Freescale MPC56x (RTR)

The document first explains bus trace configuration settings and the second part contains examples explaining typical troubleshooting scenarios.

2Trace Configuration Settings

It is presumed that the user is already familiar with winIDEA Analyzer window within which the trace functionality is integrated together with the profiler and the coverage. winIDEA Analyzer window is explained in the Analyzer Window help topic within winIDEA Help/Contents.

When creating a new trace session, trace Trigger dialog appears, consisting of Recorder tab, Trigger and Qualifier tab and an optional AUX Card tab, available on iTRACE PRO/GT or Active PRO/GT development system.


2.1Recorder


Start

Recorder can start recording immediately or on a trigger event defined in the ‘Trigger and Qualifier’ tab. As a third choice, recorder can be configured for ‘Continous mode’ operation in which it starts recording immediately and it keeps recording until the application is stopped.

Buffer Size

This parameter limits the maximum size of the analyzer file residing on the PC. Recorder stops recording once the analyzer file exceeds the size limit. The parameter doesn’t have a direct correlation with the trace physical storage buffer size.

Smaller file size yields faster GUI experience. Therefore it’s recommended to keep it small as long as there is no need for long trace sessions.

Older development systems such as the iC1000 Power Emulator features small physical trace buffer (for today’s standards) in a range of e.g. 16K frames.  For this reason, the analyzer file remains small and this setting has no real importance.

Contemporary development systems featuring 2 GB (iTRACE GT) or more of physical trace buffer and the “upload while sampling’ technology can often trace program execution infinitely and for this reason, session time is actually limited only by the physical size of the analyzer file on the PC.

Trigger Position

Trigger position can be set at the beginning, in the center or at the end of the trace buffer. Trigger position should be set at the beginning when major focus is on a trace analysis after the trigger event and should be set at the end, when focus of the analysis is before the trigger event.

Break On Trigger

Application is stopped on the trigger event when the option is checked.

2.2Trigger and Qualifier


Single bus trace Trigger and Qualifier dialog


Major part of the dialog is occupied by four events marked A, B, C and Q which all can configured from the same items (Address, Data, Control and optional AUX). Items are logically OR combined vertically and are AND combined horizontally. For example next configuration will have a match whenever CPU_TestAsm or InterruptRoutine addresses are being fetched on the microcontroller trace bus.


Trigger event can be combined as a logical combination of events A, B and C while Qualifier event can be a logical combination of all 4 possible events.

Trigger

The development system offers 3-level trigger. Events A, B and C can be logically combined in numerous ways, including counter n for B event. All three events can be one or more instruction address matches or ranges.

Qualifier

Qualifier defines which events qualify to be recorded. It’s a filter implemented in the tool hardware saving physical trace storage memory only for information of interest and by doing so prolonging the trace session time. Per default Qualifier is configured for ‘Everything’, which yields recording complete application program execution and all data accesses.

Most often the ‘Q Event‘ selection is used (when qualifier is being used) and can be configured for one or more instruction (or data) address matches or ranges. It is possible to define unlimited number of areas, which can be a simple address range, a function or a source line.

A so called Pre/Post Qualifier is available as an add-on to the prime qualifier usage.

Pre Qualifier can record up to 8 CPU cycles before the qualifier event and Post Qualifier up to 8 CPU cycles after the qualifier event.

One possible use case is when tracing data accesses only, where trace provides no information on which instruction or source code is origin of the individual data access.  By configuring Pre Qualifier to record few samples before the qualifier (configured to record data accesses), trace will provide information which parts of program generate each qualified data access.

Second use case is to configure qualifier on a complete function or just its entry point and Pre Qualifier is used to record few instructions before, which makes possible to identify, which part of executed program actually called the qualified function.

Renesas 78K/78K0R/RL78 and EM Microelectronic CoolRISC in-circuit emulation debug & test tools feature dual bus trace, where program and data bus are physically separated when brought outside of the emulation device. The trace Trigger dialog is stretched horizontally since both, Trigger and Qualifier manage program bus (marked as Instruction or Primary Bus) and data bus (marked as Access or Secondary Bus) separately.



Renesas 78K, 78K0R, RL78 dual bus trace



EM Microelectronic CoolRISC dual bus trace


2.3AUX Signals

Optional AUX Card in combination with iTRACE PRO/GT or ActivePRO/GT PODs provides auxiliary signals, which can be recorded in parallel with the trace. All settings are done in the AUX Card tab within the Trigger dialog.

Sampling and Trigger

Sampling can be configured for:

Off

Auxiliary signals are not recorded.

Trace

Auxiliary signals are sampled and recorded with the trace clock, which is typically the CPU clock.

Trace + AUXC Signals Rising or Falling Edge

Auxiliary signals are sampled and recorded with the trace clock, which is typically the CPU clock and additionally with falling/rising edge of the selected auxiliary signals.


Auxiliary signals additionally recorded on rising/falling edge of AUX2/AUX3 signal


Trace can also trigger on a state change of auxiliary signals.


Trace trigger set on AUX0 = ’’1’’

Input Threshold

When signals connected to the auxiliary inputs have non-standard voltage levels or there are problems with sampling, input sampling threshold voltage level can be adjusted individually for a group of 8 signals.

3Troubleshooting Scenarios

3.1Record everything

This configuration is used to record the contiguous program flow either from the program start on or up to the moment, when the program stops.

The trace can start recording on the initial program start from the reset or after resuming the program from the breakpoint location. The trace records and displays program flow from the start until the trace buffer fulfills.

As an alternative, the trace can stop recording on a program stop. ‘Continuous mode’ use allows roll over of the trace buffer, which results in the trace recording up to the moment when the application stops. In practice, the trace displays the program flow just before the program stops. For instance, due to the breakpoint hit, due to the erratic state of the CPU, which yields the program stop, or due to the stop debug command issued by the user.

Example: The application enters unexpectedly in a halted mode (sleep mode, power down mode) during normal program execution. Such cases can be investigated only by using the trace since the CPU is no longer under the debugger’s control while in halted mode. Using the trace, the course of program before the halted mode entry is recorded and the source of the unexpected entry can be found.

Select ‘Record everything’ operation type in the ‘Analyzer Configuration’ drop down menu.

Make sure that ‘Continuous mode’ option is selected as a Recorder start to ensure that the trace buffer rolls over while recording the running program. The trace will stop as soon as the program execution is stopped. Set the buffer size to the desired amount.

With these settings the trace records program flow while it is running. As soon as the program enters halted mode or is stopped due to any other reason, the trace stops recording. The source of the problem can be analyzed easily since the program flow before the program stop is recorded.

3.2Basic Trigger/Qualifier Configuration

Configuration with a simple trigger set on a variable being accessed or an instruction being executed are described in this section. Additionally, simple qualifiers are configured.

If it’s required to stop the program on a trigger event, check the ‘On trigger break execution’ option in the ‘Trace Configuration’ dialog.

Example: The trace starts recording after the Type_Struct function is called for the fifth time.

Add new ‘Trace’ analyzer configuration and open the configuration window.

Set recorder to start ‘On Trigger’ and choose the desired buffer size. The trigger position can be set at the beginning, center or at end of the trace buffer. Set the position based on your particular case since the code being of interest can be executed after or before the trigger event.

On ‘Trigger and qualifier’ page select ‘n*B’ for the trigger condition. When the trigger on a first occurrence is required, ‘A’ can be opted instead of ‘n*B’ in the trigger condition field.

Set Type_Struct entry point for the event B and set 5 in the counter field.

When configuring an event on a code, select ‘OP-CODE Fetch’ access type for the Control Item to obtain correct results, which may otherwise be distorted due to the CPU pipeline queue. Select either ‘Memory Write’ or ‘Data Read’ access type when configuring an event on a data. List of available controls depends on the selected target, so different options might be available.

The trace is now configured.

Initialize the complete system, start the trace and run the program.

Let’s inspect the results. Trigger point (frame 0) holds fifth Type_Struct function entry.


Trace Window results

Example: The code writing 0x166 to the iCounter variable needs to be analyzed. The same trace configuration can be used to verify that the variable never gets written 0x166 as for instance expected from the application. In such case, the trigger would never occur normally.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

Edit ‘Trigger and Qualifier’ settings. Select ‘A’ for the trigger condition.

Configure 0x166 memory write to the iCounter variable as the event A. Set iCounter address in the ‘Address Item’ dialog and check ‘Cover entire object range’ option.

Next write a value in the ‘Data Item’ dialog and select proper data size. Maximum ‘Data Item’ size is limited by the CPU architecture. Only 8 and 16-bit values are valid and can be monitored properly in case of 16-bit CPU. Correct triggering on 32-bit variable requires code arming.

Set ‘Memory Write’ cycle type in the ‘Control Item’ dialog.

The trace is configured.



If a 0x166 write to the iCounter variable occurs, the trace triggers and displays the code that caused the write.


Trace Window results



Example: Func3 routine only is recorded.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

Select ‘Anything’ for the trigger condition and ‘Q event’ for the Qualifier.

Define Func3 routine for the event Q. When configuring Address Item for the event Q, select Func3 routine from the Symbol Browser and check ‘Cover entire object range’ option. By doing so, the Address Item is configured on a range bounded by Func3 entry point and Func3 exit point. A range size is displayed below the option, being 150 bytes for Func3 routine.



The trace is configured.

Initialize the complete system, start the trace and run the program. The trace records CPU activity only while Func3 routine is executed.


Example: Trace monitors the value of iCounter variable while the application is running.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

Select ‘Anything’ for the trigger, ‘Q event’ for the Qualifier.

Configure write to iCounter variable as the event Q. Set iCounter address in the ‘Address Item’ dialog and check ‘Cover entire object range’ option.

Next, set ‘Memory Write’ for the bus cycle type in the ‘Control Item’ dialog.

The trace is configured.



Initialize the complete system, start the trace and run the program. The trace records all writes to iCounter variable.


Trace Window results



3.3Watchdog Trigger

A standard trigger condition, logically combined from events A, B and C, is not used to trigger directly the trace, but it’s responsible for keeping a free running trace watchdog timer from timing out. The trace watchdog time-out is adjustable.

When the trace watchdog timer times out, the trace triggers and optionally stops the application. The problematic code can be found by inspecting the program flow in the trace history.

Typical use:

If the application being debugged features a watchdog timer, the trace watchdog trigger can be used to trap the situations when the application watchdog timer times out and resets the system.

Typically, a “trace watchdog reset” condition is configured as a memory write to a specific memory location (e.g. watchdog register), which resets the watchdog timer to the start of a new time-out period. In case of the external watchdog timer being reset by the target signal, the external trace (AUX) input, where the signal must be connected, is configured, instead of a memory write.

Time-out period of the trace watchdog timer must be set less than the period of the application watchdog so the trace can stop the application just before the application watchdog times out and resets the system.

If the application itself doesn’t feature a watchdog mechanism, the trace watchdog trigger can be used to supervise the application. The user needs to determine a part of the code that is executed periodically and its execution period, while the program behaves expectedly. The code, resetting the trace watchdog timer, can be, for instance, a function or data write/read access. The execution period is set for the trace watchdog timer time-out period. When the application misbehaves, the “watchdog reset” code is no longer executed within the normal execution period, the trace watchdog timer times out and the trace triggers.

The code being executed a definite time after the program start can be analyzed.

Configuring Watchdog Trigger

The user needs to enter the period of the trace watchdog timer and define the “trace watchdog reset” condition, which can be logically combined from events A, B and C.

1) Check the ‘Watchdog’ option and specify the time-out period in the ‘Trigger’ field in the ‘Trigger and Qualifier Configuration’ dialog.



2) Next, define the “trace watchdog reset” condition. Typically, only the event A is selected for the “trace watchdog reset” condition and then e.g. a CPU memory write or a reset watchdog routine, resetting the watchdog, is configured for the event A. Of course, a more complex condition can be set up instead of the event A only.


Example: Motorola HCS12 target application features on-chip COP watchdog, which enables the user to check that a program is running and sequencing properly. When the COP is being used, software is responsible for keeping a free running watchdog timer from timing out. If the watchdog timer times out it’s an indication that the software is no longer being executed in the intended sequence; thus a system reset is initiated.

When COP is enabled, the program must write 0x55 and 0xAA (in this order) to the ARMCOP register (0xE000) during the selected time-out period. Once this is done, the internal COP counter resets to the start of a new time-out period. If the program fails to do this, the part will reset. Also if any value other than 0x55 and 0xAA is written, the part is immediately reset.

The COP timer time-out period is 21 ms in this particular example. It may vary between the applications since it’s configurable. The watchdog timer is reset within 18 ms during the normal program flow.

The trace is going to be configured to trap COP time out and stop the program before it initiates the system reset. The user can find the code where the program misbehaves in the trace history.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

On the ‘Trigger and Qualifier’ page select ‘A then n*B’ for the trigger condition, check the ‘Watchdog’ option and enter 20 ms for the trace watchdog timer time-out period.

Next, configure the event A (reset sequence – first part) as memory write 0x55 to the address 0xE000 (ARMCOP register) and the event B (reset sequence – second part) as memory write 0xAA to the address 0xE000 (ARMCOP register).




While the application operates correctly, the trace never triggers. When the application misbehaves, the trace triggers and stops the program before the system reset is initiated.

If a maximum trace history is required, select maximum trace buffer size and position the trace trigger at the end of the trace buffer.


Example: The application features (external) target watchdog timer, which is normally periodically reset every 54.7 ms by the WDT_RESET target signal.

The trace needs to be configured to trap the target watchdog timer time out and stop the program before the system reset is initiated. Then the user can find the code where the program misbehaves using the trace history.

One of the available external trace inputs (AUX0) is used, where the WDT_RESET signal from the target is connected. Refer to the hardware reference document delivered beside the emulation system to obtain more details on locating and connecting the AUX0 input.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

On the ‘Trigger and Qualifier’ page select ‘A’ for the trigger condition, check ‘Watchdog’ option and enter 54.0 ms for the trace watchdog timer time-out period.

Next, configure AUX0=1 for the event A. The trace will trigger as soon as the target WDT_RESET signal stops resetting the target watchdog within 54.0 ms period.



Again, while the application operates correctly the trace never triggers. However, when the application misbehaves, the trace triggers and stops the program before the system reset is initiated.

If a maximum trace history is required, select maximum trace buffer size and position the trace trigger at the end of the trace buffer.


Example: The code being executed 2.3 ms after the CPU start has to be recorded.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

To record part of the program, which is distant from the CPU start point in a manner of time, select ‘A->B duration tracker’ for the trigger condition, check the ‘Watchdog’ option and enter the time when the trace triggers. Don’t define anything for events A and B. This will ensure that the trace watchdog timer never resets and triggers on the first time-out that is after 2.3 ms.

Additionally, the trace can stop the program execution after 2.3 ms by checking ‘On trigger break execution’ option in the ‘Trace Configuration’ dialog. This trace configuration can be used to stop the program at any time.

Complete program flow around the trigger point can be recorded, or interesting parts only by using the qualifier. ‘Q between B and C’ qualifier type cannot be used in this configuration.

Start the session. Initialize the system, start the trace and run the application.

Image below shows that the assembler instruction INY belonging to the +aa; source line of the Type_Enum function is executed 2.3 ms after the program start. It may be a bit confusing since the assembler instruction ‘INY’ holds 0 ns time stamp in the trace window. It’s due to the fact that this is a trigger event, which always holds 0 ns time stamp. All recorded frames hold time stamp values relative to the trigger event respectively trigger frame. In this particular example, first instruction executed after reset (address 0xF000) holds –2.3 ms time stamp, which is correct.


Trace Window results



3.4Duration Tracker

The duration tracker measures the time that the CPU spends executing a part of the application constrained by the event A as a start point and the event B as an end point. Typically, a function or an interrupt routine is an object of interest and thereby constrained by events A and B. However, it can be any part of the program flow constrained by events A and B.

Both events can be defined independently as an instruction fetch from the specific address or data write/read to/from the specific memory location or an active auxiliary signal.


Duration Tracker provides following information for the analyzed object:

- Minimum time

- Maximum time

- Average time

- Current time

- Number of hits

- Total profiled object time

- Total CPU time

Duration tracker results are updated on the fly without intrusion on the real time program execution. Additionally, the duration tracker can trigger and break the program, when the elapsed time between events A and B exceeds the limits defined by the user. Maximum (Max Time) or minimum time (Min Time) or both can be set for the trigger condition.

Set maximum time when a part of the program e.g a function must be executed in less than TMAX time units.

Set minimum time when a part of the program e.g. a function taking care of some conversion must finish the conversion in less than TMIN time units.

Exceeding the limit(s) can stop the application and the code exceeding the limits can be found in the trace window.

Max Time is evaluated as soon as the event B is detected after the event A or simply, Current Time is compared against Max Time after the program leaves the object being tracked.

Min Time is compared with the Current Time as soon as the event A is detected or simply, Current Time is compared against Min Time as soon as the program enters the object being tracked.

Based on the trace history, the user can easily find why the program executed out of the normal limits. Trace results can be additionally filtered out by using the qualifier.

Example: There is a Timer2Int interrupt routine, which terminates in 420 μs under normal conditions. The user wants to trigger and break the program execution when the Timer2Int interrupt routine executes longer than 420 μs, which represent abnormal behavior of the application.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘End’.

Select, ‘A->B duration tracker’ for the trigger condition.

Next, we need to define the object of interest. Select, Timer2Int entry point for the event A and Timer2Int exit point for the event B. Make sure you select ‘Fetch’ access type for the control bus for both events since the object of our interest is the code.

Check the ‘Max Timer >’ option and enter 420 μs for the limit.

If the program must stop when the trigger condition occurs, check ‘Break On Trigger’ option in the trace configuration dialog. Note that the CPU stops few CPU cycles after the trigger event due to the latency of the hardware processing the trigger and stopping the CPU.

Before starting the trace session, open the Trigger Status Bar using the according trace toolbar.  Existing trace window is extended by the bar displaying the Duration Tracker and the Watchdog Trigger proprietary information.


Now, the trace is configured. Initialize the system, start the trace and run the application. The application either runs or it’s stopped by the trace trigger if we check the ‘Break On Trigger’ option.

Let’s assume that the application behaves abnormally and the program stops by the trace trigger. It means that the CPU spent more than 420 μs in Timer2Int interrupt routine. Let’s analyze the trace content.

Trace Window results

Go to the trigger event by pressing ‘J’ key or selecting ‘Jump to Trigger position’ from the local menu. The trace window shows the code being executed 420 μs after the application entered Timer2Int interrupt routine.

By inspecting the trace history we can find out why the Timer2Int executed longer than 420 μs. The routine should normally terminate in less than 420 μs.

Next, let’s analyze duration tracker results displayed in the Duration Tracker Status Bar.


Duration Tracker Status Bar

Duration Tracker Status Bar reports:

Timer2Int minimum execution time was 54.95 μs

Timer2Int average execution time was 235.90 μs

Timer2Int maximum and current execution time was 416.85 μs

Last execution of the Timer2Int took longer than 420 μs, since we got a trigger, which stopped the program. This time cannot be seen yet since the program stopped before the function exited. The Status Bar displays last recorded maximum and current time.

Timer2Int routine completed 27 times.

The CPU spent 6.37 ms in the Timer2Int routine being 22.85% of the total time.

The duration tracker run for 27.88 ms.

If the Timer2Int routine doesn’t exceed Min Time nor Max Time values, the debugger exhibits run debug status and the duration tracker status bar displays current statistics about the tracked object from the start on. Status bar is updated on the fly while the application is running.

Note 1: Events A and B can also be configured on external signals. In case of an airbag application, the event A can be a signal from the sensor unit reporting a car crash and the event B can be an output signal to the airbag firing mechanism. Duration tracker can be used to measure the time that the airbag control unit requires to process the sensor signals and fire the airbags. Such an application is very time critical and stressed. It can be tested over a long period using Duration Tracker, which stops the application as soon as the airbag doesn’t fire in less than TMIN and display the critical program flow.

Note 2: Duration Tracker can be used in a way in which it works like the execution profiler (one of the analyzer operation modes) on a single object (e.g. function/routine) profiting two things, the results can be uploaded on the fly while the CPU is running and the object can be tracked over a long period. Define no trigger and the duration tracker updates statistic results while the program runs.


3.5Q between B and C events

In this mode, the trace records particular CPU cycles, which are executed within the specific section of the code.

Example: The user wants to record memory writes to the iCounter variable, while function Type_Pointers is executed.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

Select ‘Q between B, C events’ in the Qualifier combo box. Event B represents start and the event C stop trace recording condition. Recorded CPU activity can be further filtered out by the qualifier event Q.



Configure Type_Pointers entry point for the event B and Type_Pointers exit point for the event C event.

Finally, configure iCounter memory write cycle for the event Q.

As soon as the event B occurs, the trace starts considering the qualifier Q and records the CPU cycles matching with the Q condition until the event C. Event B represent enable and event C disable condition for the qualifier Q.

iCounter variable is modified by the Type_Pointers function approximately every 805.7 μs.


Trace Window results

Due to the CPU behavior, it’s possible that the iCounter memory write is not recorded by the trace (at current trace settings) although being modified by the application. Assume that we have the following function:

void Type_Pointers()

{

char c;

char *pC;

char **ppC;


c='A';

pC=&c;

++*pC;

ppC=&pC;

++(**ppC);

++iCounter;

}

The program flow recorded by the trace would be:


Trace Window results

iCounter memory write is actually executed after the Type_Pointers function exits. Therefore, the trace configured like in the example, would not record any iCounter memory write cycles although expected by the user.

3.6Pre/Post Qualifier

Pre Qualifier can record up to 8 CPU cycles before the qualifier event and Post Qualifier up to 8 CPU cycles after the qualifier event. The qualifier can be configured in a standard way and then additionally up to 8 CPU cycles can be recorded before and/or after the qualifier.

Example: The application writes to the 16-bit iCounter variable from various functions constantly. Normally, only a function Type_Pointers writes 0x32 to the iCounter variable, which results in displaying a special graphic character on the LCD display connected to the CPU. However, it seems there is a bug in the application since the special character is displayed on the LCD also when the Type_Pointers is not called at all. The code writing 0x32 to the variable iCounter and not belonging to the Type_Pointers function will be found using the trace.

The trace needs to be configured to record 0x32 writes to the iCounter. Additionally, a section of the code executed before the write needs to be recorded to be able to find the source of the write. Using filter in the trace window, the user can filter out the code, which normally modifies the iCounter, and find the problematic code.

Add new ‘Trace’ analyzer configuration and open the configuration window. Set the Recorder to start ‘On Trigger’ and set the trigger position to ‘Center’.

Leave the trigger set on ‘Anything’ by default.

Select ‘Q event’ for the Qualifier and configure ‘Record 8 samples before Q’.

Finally, define the event Q. Set iCounter address and check ‘Cover entire object range’ option in the Address Item dialog.

Enter a value in the ‘Data Item’ dialog and select proper data size. Select ‘16 bits’ data size since iCounter is a 16-bit variable.

Finally, set ‘Memory Write’ for the bus cycle type in the ‘Control Item’ dialog. The trace is configured.


Initialize the system, start the trace and run the application. The trace records iCounter 0x32 memory write cycles and 8 previous CPU cycles. In this example, the trace buffer fills up slowly and the trace is stopped manually after the special character is displayed on the LCD when it shouldn’t. Let’s inspect the trace results.


Trace Window results

In the example, the trace recorded 58s of the CPU execution and encloses 8078 CPU cycles (frames). The trace buffer is quite empty comparing to the maximum possible trace buffer since there can be up to 128K frames recorded. Due to the huge amount of recorded cycles, we need to filter out all the expected CPU cycles to be able to allocate the problematic code. Some intuition is necessary to be able to find the problematic section of code. One of possible approaches will be described.

Type_Pointers function exit normally precedes iCounter 0x32 memory writes.  Save the trace record at this point (File/Save As…). Next, modify the qualifier settings in a way that only one CPU cycle is recorded before the qualifier.

Make another trace record with new trace settings.



Trace Window Results

As before, Type_Pointers exit point precedes the memory write. We could start manually searching for a frame differing from the Type_Pointers exit point but it could take a while since the buffer can have up to 128K frames. Let’s use the filter being built in the trace widow to find the problematic code.

Configure filter named Filt1 set on iCounter memory write and filter named Filt2 set on Type_Pointers exit point.

Filter expressions:

Filt1 = (Address == {#iCounter}) & (Content = "Memory Write")


Filt2 = Address == {Type_Pointers_EXIT_}

Hide states defined by these two filters by unchecking the ‘State View Visibility’ check boxes in the ‘States and Filters’ dialog.



Only a problematic code remains in the trace window.


Trace Window results - problematic code allocated

The problematic code is allocated at address 0xF1EA and 0xF26A. Double-click on the assembler instruction (first frame) or on the source line (second frame) points out the code being the source of the problem. If more CPU cycles than a single one before the problematic write are required, open the previously saved trace record and search for the problematic addresses 0xF1EA and 0xF26A.


Trace Window results

Note: An alternative to this example is to use ‘Q between B and C events’ trace configuration. Refer to the section 5.5. for more details on this trace configuration. Set trigger to ‘Anything’ and select ‘Q between B, C events’ in the Qualifier combo box. Event Q remains configured like in the example. Then configure Type_Pointers exit point for the event B and Type_Pointers entry point for the event C. The trace now records the code matching with the qualifier and not belonging to the Type_Pointers routine.


3.7Data Change

A trigger or qualifier condition can be set on a change of a certain variable. Additionally, it can be set that the condition matches only when the data value is changing to a particular value. A single value, bit mask or a range can be entered for the value. Pre/Post Qualifier can be used supplementary.

Example: The trace records every write changing the 16-bit iDataChangeVar value and the belonging code modifying the value. The trace has to start recording on first CPU_Pointers function call.

Select ‘Use trigger/qualifier’ operation type in the ‘Trace configuration’ dialog, add a new trigger and open ‘Trigger and Qualifier Configuration’ dialog.

Select ‘A’ for the trigger condition and configure event A by entering CPU_Pointers entry point for the Address Item and ‘OP-CODE Fetch’ cycle for the Control Item.

Select ‘Q event’ for the qualifier and define event Q.

Enter the address of the iDataChangeVar variable in the ‘Address Item’ dialog either manually by writing its physical address or by picking up the iDataChangeVar address from the Symbol Browser. Make sure that ‘Cover entire object range’ option is checked too.

In the ‘Data Item’ dialog, check the ‘Monitor data value change’ option and set ‘16 bits’ for the Data Size since 16-bit variable is going to be monitored.

Select ‘Memory Write’ cycle type in the ‘Control Item’ dialog.




Finally, configure Post Qualifier to record 4 samples before the event Q. This will ensure that the code (4 CPU cycles) modifying the iDataChangeVar variable will be recorded too. It’s up to the user to record more or less cycles before the event Q.

Initialize the system, start the trace and run the application.


Trace Window results

Let’s analyze the results. iDataChangeVar variable changes the value at frames -1, -6, -11. Double-click on the source line or assembly instruction before the memory write points to the code writing a new value. Trigger point (CPU_Pointers function entry) itself is not recorded since the trigger point doesn’t match with the configured qualifier condition.

Memory writes modifying the variable are recorded only. Memory writes writing the same value like previous memory write are not recorded. Plain qualifier condition (‘Monitor data value change’ option unchecked) must be used when all memory writes have to be recorded.



Example: The trace has to record every write modifying 16-bit iDataChangeVar variable to a value 0x6 and the belonging code.

Select ‘Use trigger/qualifier’ operation type in the ‘Trace configuration’ dialog, add a new trigger and open ‘Trigger and Qualifier Configuration’ dialog.

Set the trigger condition to ‘Anything’ and the qualifier to ‘Q Event’.

Next, configure event Q. Address and Control Item are set in the same way like in the previous example. Don’t forget to check ‘Cover entire object range’ in the ‘Address Item’ dialog. Enter 0x6 value, check ‘Monitor data value change’ option and select ‘16 bits’ data size for the ‘Data Item’.

Finally, configure the Pre Qualifier according to your needs. ‘Record 4 samples before Q’ is set in this example.





Initialize the system, start the trace and run the application.


Trace Window results

iDataChangeVar variable is modified by different code. Double-click on the source lines will point out the program section writing 0x6 to the iDataChangeVar variable. In this particular example, Address_TestScopes and Type_Mixed write 0x6 to the variable.















































Disclaimer: iSYSTEM assumes no responsibility for any errors which may appear in this document, reserves the right to change devices or specifications detailed herein at any time without notice, and does not make any commitment to update the information herein.

© iSYSTEM. All rights reserved.