Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for QNX Neutrino #507

Open
wants to merge 6 commits into
base: master
Choose a base branch
from

Conversation

gh-tr
Copy link

@gh-tr gh-tr commented Dec 22, 2022

Add support for QNX Neutrino.
-- Tested on a Neutrino target for both aarch64 and x86_64 running 7.1.

Change Description:

  • Splits the existing functionality (default) into one module and the nto into another
  • On QNX, there is a header in the pmap file so added functionality to skip the first line of the file /proc/self/pmap
  • Bumped libc version to the first version containing a Neutrino target.

@flba-eb
Copy link
Contributor

flba-eb commented Jan 9, 2023

@Veykril: Could you please take a look at this PR? Would it make sense to close #506 in favor of this PR?

…he automated build system is unhappy about naming conventions on 1.42.0
bors added a commit to rust-lang-ci/rust that referenced this pull request Mar 2, 2023
…gjubilee

Add support for QNX Neutrino to standard library

This change:

- adds standard library support for QNX Neutrino (7.1).
- upgrades `libc` to version `0.2.139` which supports QNX Neutrino

`@gh-tr`

⚠️ Backtraces on QNX require rust-lang/backtrace-rs#507 which is not yet merged! (But everything else works without these changes) ⚠️

Tested mainly with a x86_64 virtual machine (see qnx-nto.md) and partially with an aarch64 hardware (some tests fail due to constrained resources).
saethlin pushed a commit to saethlin/miri that referenced this pull request Mar 5, 2023
Add support for QNX Neutrino to standard library

This change:

- adds standard library support for QNX Neutrino (7.1).
- upgrades `libc` to version `0.2.139` which supports QNX Neutrino

`@gh-tr`

⚠️ Backtraces on QNX require rust-lang/backtrace-rs#507 which is not yet merged! (But everything else works without these changes) ⚠️

Tested mainly with a x86_64 virtual machine (see qnx-nto.md) and partially with an aarch64 hardware (some tests fail due to constrained resources).
thomcc pushed a commit to tcdi/postgrestd that referenced this pull request May 31, 2023
Add support for QNX Neutrino to standard library

This change:

- adds standard library support for QNX Neutrino (7.1).
- upgrades `libc` to version `0.2.139` which supports QNX Neutrino

`@gh-tr`

⚠️ Backtraces on QNX require rust-lang/backtrace-rs#507 which is not yet merged! (But everything else works without these changes) ⚠️

Tested mainly with a x86_64 virtual machine (see qnx-nto.md) and partially with an aarch64 hardware (some tests fail due to constrained resources).
Copy link
Member

@workingjubilee workingjubilee left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I had half-expected someone else with a bit more experience to come by and review this, so I kept my earlier comments minimal, but it looks like I probably now know the most about QNX Neutrino amongst the libs reviewers, so I might as well sit down with this. Sorry about the holdup.

Comment on lines +56 to +70
fn concat_str(a: &str, b: &str) -> String {
let mut e = String::from(a);
e += b;
e
}

fn read_file(file: &str) -> Result<String, String> {
let mut proc_self_maps =
File::open("/proc/self/maps").map_err(|_| "Couldn't open /proc/self/maps")?;
File::open(file).map_err(|_| concat_str("Couldn't open file: ", file))?;
let mut buf = String::new();
let _bytes_read = proc_self_maps
.read_to_string(&mut buf)
.map_err(|_| "Couldn't read /proc/self/maps")?;
for line in buf.lines() {
v.push(line.parse()?);
}
.map_err(|_| concat_str("Couldn't read file: ", file))?;
Ok(buf)
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This machinery is a reimplementation of fs::read_to_string. You can import fs by changing

- use super::mystd::fs::File;
+ use super::mystd::fs::{self, File};

If you must, you can use map_err for the Err variant.

Comment on lines +96 to +99
#[cfg(not(target_os = "nto"))]
pub fn config() -> (&'static str, usize) {
("/proc/self/maps", 0)
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This moves to runtime what can be known at compile-time. Please describe a static and a const instead, with appropriate names. If you wish, you can put them in a mod config {}.

Comment on lines +75 to +78
parse_maps_lines(&content, skip)
}

fn parse_maps_lines(content: &str, skip: usize) -> Result<Vec<MapsEntry>, String> {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe this is still functionally identical if we simply delete these lines?

Suggested change
parse_maps_lines(&content, skip)
}
fn parse_maps_lines(content: &str, skip: usize) -> Result<Vec<MapsEntry>, String> {

@@ -162,7 +243,7 @@ fn check_maps_entry_parsing_64bit() {

assert_eq!(
"7f5985f46000-7f5985f48000 rw-p 00039000 103:06 76021795 \
/usr/lib/x86_64-linux-gnu/ld-linux-x86-64.so.2"
/usr/lib/x86_64-linux-gnu/ld-linux-x86-64.so.2"
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there a reason for diffing this line?

#[test]
fn check_maps_entry_parsing_64bit() {
assert_eq!(
"ffffffffff600000-ffffffffff601000 --xp 00000000 00:00 0 \
[vsyscall]"
[vsyscall]"
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there a reason for diffing this line?

Comment on lines +179 to +190
let vaddr_str = parts.next().ok_or("Couldn't find virtual address")?;
let size_str = parts.next().ok_or("Couldn't find size")?;
let _flags_str = parts.next().ok_or("Couldn't find flags")?;
let prot_str = parts.next().ok_or("Couldn't find protection")?;
let _maxprot_str = parts.next().ok_or("Couldn't find maximum protection")?;
let dev_str = parts.next().ok_or("Couldn't find device")?;
let ino_str = parts.next().ok_or("Couldn't find inode")?;
let offset_str = parts.next().ok_or("Couldn't find offset")?;
let _rsv_str = parts.next().ok_or("Couldn't find reserved pages")?;
let _guardsize_str = parts.next().ok_or("Couldn't find guard size")?;
let _refcnt_str = parts.next().ok_or("Couldn't find reference count")?;
let _mapcnt_str = parts.next().ok_or("Couldn't find mapped count")?;
Copy link
Member

@workingjubilee workingjubilee Jun 22, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just to be clear, on QNX Neutrino these are all required fields? Is there somewhere this format is documented for Neutrino? It seems to be a superset of the other format described here?

Ok(v)
pub(super) fn parse_maps() -> Result<Vec<MapsEntry>, String> {
let (file, skip) = config();
let content = read_file(file)?;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
let content = read_file(file)?;
let content = fs::read_to_string(file).map_err(|e| e.to_string())?;

|s: &str| usize::from_str_radix(&s[2..], 16).map_err(|_| "Couldn't parse hex number");
let address = { (hex(vaddr_str)?, hex(vaddr_str)? + hex(size_str)?) };

// TODO: Probably a rust'ier way of doing this
Copy link
Member

@workingjubilee workingjubilee Jun 22, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You could probably cook something up using array::from_fn but I'm not going to block this on that. If you decide not to, though, please remove the TODO.

@workingjubilee workingjubilee self-assigned this Jun 22, 2023
RalfJung pushed a commit to RalfJung/rust-analyzer that referenced this pull request Apr 20, 2024
Add support for QNX Neutrino to standard library

This change:

- adds standard library support for QNX Neutrino (7.1).
- upgrades `libc` to version `0.2.139` which supports QNX Neutrino

`@gh-tr`

⚠️ Backtraces on QNX require rust-lang/backtrace-rs#507 which is not yet merged! (But everything else works without these changes) ⚠️

Tested mainly with a x86_64 virtual machine (see qnx-nto.md) and partially with an aarch64 hardware (some tests fail due to constrained resources).
RalfJung pushed a commit to RalfJung/rust-analyzer that referenced this pull request Apr 27, 2024
Add support for QNX Neutrino to standard library

This change:

- adds standard library support for QNX Neutrino (7.1).
- upgrades `libc` to version `0.2.139` which supports QNX Neutrino

`@gh-tr`

⚠️ Backtraces on QNX require rust-lang/backtrace-rs#507 which is not yet merged! (But everything else works without these changes) ⚠️

Tested mainly with a x86_64 virtual machine (see qnx-nto.md) and partially with an aarch64 hardware (some tests fail due to constrained resources).
@japaric
Copy link
Member

japaric commented Sep 23, 2024

this PR can be closed now that #648 has landed (648 adds support for both QNX 7.0 and 7.1)

@workingjubilee
Copy link
Member

@japaric The QNX /proc/self/maps format still isn't handled.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants