Cross Linux Topics

This appendix describes topics that are specific to the GNAT for Cross Linux.

Building a Cross Linux Application

To use GNAT Pro for Cross Linux the environment variable ENV_PREFIX needs to be set to the path containing the sysroot of your target. As background, the sysroot is the root directory for the folders containing the system headers and libraries provided by the target system. A typical sysroot would contain the following directories:

mysysroot:
 |--> lib:
 |--> lib64: (on 64-bit Linux)
 \--> usr:
       |--> include:
       |--> lib:
       \--> lib64: (on 64-bit Linux)

At a minimum the sysroot should contain glibc 2.5 or greater.

Please refer to your Embedded Linux distribution on how to obtain a sysroot corresponding to your target. GNAT Pro supports both single architecture sysroots and Debian-style multiarch sysroots. Please note the Ubuntu cross compiler toolchain provided by the crossbuild-essential-* packages do not provide a sysroot useable by GNAT Pro.

If you have trouble obtaining a sysroot, it is possible to build one by copying the target libraries from the target to your host. For instance, if you are developing with a ppc64-linux target, you could do the following to build a sysroot directory on your host:

$ mkdir ./sysroot
$ mkdir ./sysroot/usr
$ scp -rp my-ppc64-linux-target:/usr/include ./sysroot/usr/
$ scp -rp my-ppc64-linux-target:/usr/lib ./sysroot/usr/
$ scp -rp my-ppc64-linux-target:/usr/lib64 ./sysroot/usr/
$ scp -rp my-ppc64-linux-target:/lib ./sysroot/
$ scp -rp my-ppc64-linux-target:/lib64 ./sysroot/

To use that sysroot, you can then export ENV_PREFIX as follow.

$ export ENV_PREFIX=`pwd`/sysroot

To build the basic Hello world example on ppc64-linux, you can then invoke gprbuild with the following options:

$ gprbuild --target=powerpc64-generic-linux-gnu hello.adb

WARNING: Some Linux systems provide linker scripts, e.g. libc.so, that may point to other shared libraries using a full path that starts with a double-slash ‘//’. While this does not cause any problem on GNU/Linux hosts, on Windows hosts, such paths are interpreted as UNC path. This should not prevent sysroot to be expanded, however Windows users creating sysroots from a live target system may want to fix them to avoid the latency of a network search.

Some sysroot trees intended for Linux hosts contain symlinks, which are not correctly handled by Windows hosts. Before using such a sysroot on a Windows host, you can use rsync on the Linux end to craft a copy where symlinks are replaced by their target file, like so:

$ rsync sysroot/ sysroot_no_symlink/ -a --copy-links -v

Debugging an Application on Cross Linux

This section describes the steps needed to run the Cross Linux debugger.

The debugging solution that GNAT provides on this target consists of three tools:

  • gdbserver: A debugging server on target, which provides a low-level interface to control the debugged program.

  • gdb: The debugger itself, run on the host; it connects to GDBserver and allows the user to control the debugged program through a command-line interface.

  • gnatstudio: GNAT Studio, which provides a graphical front-end for gdb.

To start a debugging session, you first need to start the program under control of GDBserver. For example, if the board has an internet connection to the development host, and assuming the Internet hostname of the board is myboard, your application is named myapp, and the port on which GDBserver will wait for requests is port 2345, the command would be:

myboard> gdbserver myboard:2345 myapp

This starts the execution of your program on the target, and then suspends it at the very beginning. Once this is done, GDBserver then waits for the debugger to connect.

You can now start the debugger. In GNAT Studio, in the Languages tab of the project properties page, you would specify the name of the debugger (e.g. powerpc64-generic-linux-gnu-gdb). You would then be able to start this debugger with the command: Debug => Initialize => <No Main Program>. Alternatively, you can run the debugger gdb from the command line.

You are now ready to connect the debugger to the GDB server:

(gdb) target remote myboard:2345

Once the debugger is connected to the GDBserver, you can debug your program as usual (insert breakpoints, inspect variables and memory, etc); remember that the program’s execution has already been started by GDBserver, and thus use “continue” to resume the program’s execution, rather than “run”. Below is an example of a debugging session where the user is interested in debugging a function called some_function, and therefore, after connecting to the target, inserts a breakpoint and then resumes his program until reaching that breakpoint:

(gdb) target remote myboard:2345
   ...
(gdb) break some_function
   ...
(gdb) continue
   ...

Note that the debugger needs access to the exact shared libraries being used by your program. By default, what the debugger does is automatically download from the target a copy of each shared library the program uses. It is recommended to keep the default, as this ensures that the debugger’s knowledge of the shared libraries matches exactly the libraries actually installed on the target, which is crucial. However, if you are debugging on a target with a slow connection, the download may be taking long enough that you would prefer to maintain on the host a copy of the target system’s shared library (the sysroot described above), and then tell the debugger to use your sysroot instead. For this, before connecting to GDBserver, use the following debugger command (where SYSROOT_PATH should be replaced by the path where the sysroot is located on the host):

(gdb) set sysroot SYSROOT_PATH
   ...

For further information about the debugger or the GDB server, please refer to the GDB User’s Manual.