Intel® Simics® Simulator for Intel® FPGAs: User Guide

ID 784383
Date 4/01/2024
Public

A newer version of this document is available. Customers should click here to go to the newest version.

Document Table of Contents

9.1.1. Debugging a Linux Application with GDB

The GNU Project debugger, or GDB, is a popular debugger used in Unix-type systems and supports several programming languages such as C and C++. One of the advantages of this debugger is that it can be used without the need to have additional hardware connected to the system.

The GDB software can be run in the same system that is running the software to debug, but it also can be executed from the Host PC using the connectivity that Intel® Simics® simulator provides through the Intel® Simics® Service Node.

To run GDB through the Intel® Simics® Service Node, use one of the following approaches:

  • Connect to a real network defining an incoming forwarding port to support GDB which uses the TCP protocol.
  • Use the Intel® Simics® simulator internal GDB server.
There are some differences between both methods (mainly during the setup), but in both cases, it is possible to perform the debug of the software that runs in the target system. The sections that follow describe both methods. In both cases, the same example which consists of a small Linux application written in C language is used. This application is shown next:
#define _GNU_SOURCE
 
#include <stdio.h>
#include <sched.h>
 
#define NUM_CORES 4
unsigned int coreCount[NUM_CORES];
 
int getCore(){
   static int corePrev = -1;
   int core;
 
    core = sched_getcpu();
    if (core != corePrev)
    {
       coreCount[core]++; 
       corePrev = core;
    }
    return core;
}
 
int main()
{
    int x = 1000;
    int core;    
    int a;
    int b;
    int c;
    volatile int exitVar = 0;
    
    core = getCore();
    printf("=== My Debug example on Core %d ===\n", core); 
 
    while(exitVar==0)
    {
        core = getCore();        
    }
    a = x;
    b = x;
    c = a + b;
    printf("%d\n", c);
    for (core = 0; core < NUM_CORES; core++)
        printf("  core[%d]: %d times\r\n", core, coreCount[core]);
 
    return 0;
}

The application starts in the main() function defining some integers variables. The exitVar variable is defined as volatile and is initialized as 0. In the code, there is a while loop that remains looping until the exitVar is not 0. The debugger is used to change its value, so the application can leave the loop so this can be completed. When compiling this application, include debug information in the ELF file generated, so GDB can use this as part of the debug.

The command used to compile this application is: gcc -g -o testGdb testGdb.c and the output is the testGdb ELF file.

The following examples show two different methods for debugging an Linux application running the target System using GDB. The main difference between these two methods is that the first method explicitly started the GDB Server in the Target System, while the second method uses the Intel® Simics® simulator internal GDB server.