|  | 
|  | 1 | +# nto-qnx | 
|  | 2 | + | 
|  | 3 | +**Tier: 3** | 
|  | 4 | + | 
|  | 5 | +[BlackBerry® QNX®][BlackBerry] Neutrino (nto) Real-time operating system. | 
|  | 6 | +The support has been implemented jointly by [Elektrobit Automotive GmbH][Elektrobit] | 
|  | 7 | +and [BlackBerry][BlackBerry]. | 
|  | 8 | + | 
|  | 9 | +[BlackBerry]: https://blackberry.qnx.com | 
|  | 10 | +[Elektrobit]: https://www.elektrobit.com | 
|  | 11 | + | 
|  | 12 | +## Target maintainers | 
|  | 13 | + | 
|  | 14 | +- Florian Bartels, `[email protected]` , https://github.com/flba-eb | 
|  | 15 | +- Tristan Roach, `[email protected]` , https://github.com/gh-tr | 
|  | 16 | + | 
|  | 17 | +## Requirements | 
|  | 18 | + | 
|  | 19 | +Currently, only cross-compilation for QNX Neutrino on AArch64 and x86_64 are supported (little endian). | 
|  | 20 | +Adding other architectures that are supported by QNX Neutrino is possible. | 
|  | 21 | + | 
|  | 22 | +The standard library does not yet support QNX Neutrino. Therefore, only `no_std` code can | 
|  | 23 | +be compiled. | 
|  | 24 | + | 
|  | 25 | +`core` and `alloc` (with default allocator) are supported. | 
|  | 26 | + | 
|  | 27 | +Applications must link against `libc.so` (see example). This is required because applications | 
|  | 28 | +always link against the `crt` library and `crt` depends on `libc.so`. | 
|  | 29 | + | 
|  | 30 | +The correct version of `qcc` must be available by setting the `$PATH` variable (e.g. by sourcing `qnxsdp-env.sh` of the | 
|  | 31 | +QNX Neutrino toolchain). | 
|  | 32 | + | 
|  | 33 | +### Small example application | 
|  | 34 | + | 
|  | 35 | +```rust,ignore (platform-specific) | 
|  | 36 | +#![no_std] | 
|  | 37 | +#![no_main] | 
|  | 38 | +#![feature(lang_items)] | 
|  | 39 | +
 | 
|  | 40 | +// We must always link against libc, even if no external functions are used | 
|  | 41 | +// "extern C" - Block can be empty but must be present | 
|  | 42 | +#[link(name = "c")] | 
|  | 43 | +extern "C" { | 
|  | 44 | +    pub fn printf(format: *const core::ffi::c_char, ...) -> core::ffi::c_int; | 
|  | 45 | +} | 
|  | 46 | +
 | 
|  | 47 | +#[no_mangle] | 
|  | 48 | +pub extern "C" fn main(_argc: isize, _argv: *const *const u8) -> isize { | 
|  | 49 | +    const HELLO: &'static str = "Hello World, the answer is %d\n\0"; | 
|  | 50 | +    unsafe { | 
|  | 51 | +        printf(HELLO.as_ptr() as *const _, 42); | 
|  | 52 | +    } | 
|  | 53 | +    0 | 
|  | 54 | +} | 
|  | 55 | +
 | 
|  | 56 | +use core::panic::PanicInfo; | 
|  | 57 | +
 | 
|  | 58 | +#[panic_handler] | 
|  | 59 | +fn panic(_panic: &PanicInfo<'_>) -> ! { | 
|  | 60 | +    loop {} | 
|  | 61 | +} | 
|  | 62 | +
 | 
|  | 63 | +#[lang = "eh_personality"] | 
|  | 64 | +#[no_mangle] | 
|  | 65 | +pub extern "C" fn rust_eh_personality() {} | 
|  | 66 | +``` | 
|  | 67 | + | 
|  | 68 | +The QNX Neutrino support of Rust has been tested with QNX Neutrino 7.1. | 
|  | 69 | + | 
|  | 70 | +There are no further known requirements. | 
|  | 71 | + | 
|  | 72 | +## Conditional compilation | 
|  | 73 | + | 
|  | 74 | +For conditional compilation, following QNX Neutrino specific attributes are defined: | 
|  | 75 | + | 
|  | 76 | +- `target_os` = `"nto"` | 
|  | 77 | +- `target_env` = `"nto71"` (for QNX Neutrino 7.1) | 
|  | 78 | + | 
|  | 79 | +## Building the target | 
|  | 80 | + | 
|  | 81 | +1. Create a `config.toml` | 
|  | 82 | + | 
|  | 83 | +Example content: | 
|  | 84 | + | 
|  | 85 | +```toml | 
|  | 86 | +profile = "compiler" | 
|  | 87 | +changelog-seen = 2 | 
|  | 88 | +``` | 
|  | 89 | + | 
|  | 90 | +2. Compile the Rust toolchain for an `x86_64-unknown-linux-gnu` host (for both `aarch64` and `x86_64` targets) | 
|  | 91 | + | 
|  | 92 | +Run the following: | 
|  | 93 | + | 
|  | 94 | +```bash | 
|  | 95 | +env \ | 
|  | 96 | +    CC_aarch64-unknown-nto-qnx7.1.0="qcc" \ | 
|  | 97 | +    CFLAGS_aarch64-unknown-nto-qnx7.1.0="-Vgcc_ntoaarch64le_cxx" \ | 
|  | 98 | +    CXX_aarch64-unknown-nto-qnx7.1.0="qcc" \ | 
|  | 99 | +    AR_aarch64_unknown_nto_qnx7.1.0="ntoaarch64-ar" \ | 
|  | 100 | +    CC_x86_64-pc-nto-qnx7.1.0="qcc" \ | 
|  | 101 | +    CFLAGS_x86_64-pc-nto-qnx7.1.0="-Vgcc_ntox86_64_cxx" \ | 
|  | 102 | +    CXX_x86_64-pc-nto-qnx7.1.0="qcc" \ | 
|  | 103 | +    AR_x86_64_pc_nto_qnx7.1.0="ntox86_64-ar" \ | 
|  | 104 | +        ./x.py build --target aarch64-unknown-nto-qnx7.1.0 --target x86_64-pc-nto-qnx7.1.0 --target x86_64-unknown-linux-gnu rustc library/core library/alloc/ | 
|  | 105 | +``` | 
|  | 106 | + | 
|  | 107 | +## Building Rust programs | 
|  | 108 | + | 
|  | 109 | +Rust does not yet ship pre-compiled artifacts for this target. To compile for this target, you must either build Rust with the target enabled (see "Building the target" above), or build your own copy of  `core` by using | 
|  | 110 | +`build-std` or similar. | 
|  | 111 | + | 
|  | 112 | +## Testing | 
|  | 113 | + | 
|  | 114 | +Compiled executables can directly be run on QNX Neutrino. | 
|  | 115 | + | 
|  | 116 | +## Cross-compilation toolchains and C code | 
|  | 117 | + | 
|  | 118 | +Compiling C code requires the same environment variables to be set as compiling the Rust toolchain (see above), to ensure `qcc` is used with proper arguments. To ensure compatibility, do not specify any further arguments that for example change calling conventions or memory layout. | 
0 commit comments