Compiling and debugging

Let's start by looking at some things you should consider when you start to write a program for the BlackBerry 10 OS.

Making your code more portable

To help you create portable applications, the BlackBerry 10 OS lets you compile for specific standards and include OS-specific code.

Conforming to standards

The header files supplied with the C library provide the proper declarations for the functions and for the number and types of arguments used with them. Constant values used in conjunction with the functions are also declared. The files can usually be included in any order, although individual function descriptions show the preferred order for specific headers.

When you use the -ansi option, qcc compiles strict ANSI code. Use this option when you're creating an application that must conform to the ANSI standard. The effect on the inclusion of ANSI- and POSIX-defined header files is that certain portions of the header files are omitted for:

  • ANSI header files, these are the portions that go beyond the ANSI standard
  • POSIX header files, these are the portions that go beyond the POSIX standard

You can then use the qcc -D option to define feature-test macros to select those portions that are omitted. Here are the most commonly used feature-test macros:

Include those portions of the header files that relate to the POSIX standard (IEEE Standard Portable Operating System Interface for Computer Environments - POSIX 1003.1, 1996)
Make the libraries use 64-bit file offsets.
Include declarations for the functions that support large files (those whose names end with 64).
Include everything defined in the header files. This is the default.

Feature-test macros may be defined on the command line, or in the source file before any header files are included. The latter is illustrated in the following example, in which an ANSI- and POSIX-conforming application is being developed.

#define _POSIX_C_SOURCE=199506
#include <limits.h>
#include <stdio.h>
#if defined(_QNX_SOURCE)
  #include "non_POSIX_header1.h"
  #include "non_POSIX_header2.h"
  #include "non_POSIX_header3.h"

You then compile the source code using the -ansi option.

The following ANSI header files are affected by the _POSIX_C_SOURCE feature-test macro:

  • <limits.h>
  • <setjmp.h>
  • <signal.h>
  • <stdio.h>
  • <stdlib.h>
  • <time.h>

The following ANSI and POSIX header files are affected by the _QNX_SOURCE feature-test macro:

Header file Type
<ctype.h> ANSI
<fcntl.h> POSIX
<float.h> ANSI
<limits.h> ANSI
<math.h> ANSI
<process.h> extension to POSIX
<setjmp.h> ANSI
<signal.h> ANSI
<sys/stat.h> POSIX
<stdio.h> ANSI
<stdlib.h> ANSI
<string.h> ANSI
<termios.h> POSIX
<time.h> ANSI
<sys/types.h> POSIX
<unistd.h> POSIX

You can also set the POSIXLY_CORRECT environment variable to 1. This environment variable is used by Unix-style operating systems to alter behavior to comply with POSIX where it's different from the OS's default behavior.

For example, if POSIXLY_CORRECT is set, functions that check the length of a pathname do so before removing any redundant . and .. components. If POSIXLY_CORRECT isn't set, the functions check the length after removing any redundant components.

POSIXLY_CORRECT is a de facto standard that isn't defined by POSIX.

Including OS-specific code

If you need to include OS-specific code in your application, you can wrap it in an #ifdef to make the program more portable. The qcc utility defines these preprocessor symbols (or manifest constants):

The target is a QNX operating system (QNX 4, QNX Neutrino, or BlackBerry 10 OS).
The target is the QNX Neutrino RTOS or BlackBerry 10 OS.

For example:

#if defined(__QNX__)
   /* QNX-specific (any flavor) code here */

   #if defined(__QNXNTO__)
      /* QNX Neutrino-specific code here */
      /* QNX 4-specific code here */

For information about other preprocessor symbols that you might find useful, see Manifests.

Header files in /usr/include

The ${QNX_TARGET} /usr/include directory includes at least the following subdirectories (in addition to the usual sys):

ARPA header files concerning the Internet, FTP and TELNET.
Descriptions of various hardware devices.
arm, x86
CPU-specific header files. You typically don't need to include them directly — they're included automatically. There are some files that you might want to look at:
  • Files ending in *intr.h might describe interrupt vector numbers for use with InterruptAttach() and InterruptAttachEvent().
  • Files ending with *cpu.h describe the registers and other information about the processor.
Network interface descriptions.
netinet, netinet6, netkey
Header files concerning TCP/IP.

Last modified: 2015-03-31

Got questions about leaving a comment? Get answers from our Disqus FAQ.

comments powered by Disqus