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

Parse negative integers appropriately #74

Merged
merged 2 commits into from Oct 4, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 1 addition & 0 deletions src/clang.rs
Expand Up @@ -735,6 +735,7 @@ impl Drop for Index {
}

// Token
#[derive(Debug)]
pub struct Token {
pub kind: CXTokenKind,
pub spelling: String,
Expand Down
41 changes: 26 additions & 15 deletions src/ir/var.rs
Expand Up @@ -64,7 +64,7 @@ impl ClangSubItemParser for Var {
use clangll::*;
match cursor.kind() {
CXCursor_MacroDefinition => {
let value = match parse_int_literal_tokens(&cursor, context.translation_unit(), 1) {
let value = match parse_int_literal_tokens(&cursor, context.translation_unit()) {
None => return Err(ParseError::Continue),
Some(v) => v,
};
Expand All @@ -81,7 +81,9 @@ impl ClangSubItemParser for Var {
}
context.note_parsed_macro(name.clone());

let ty = if value.abs() > u32::max_value() as i64 {
let ty = if value < 0 {
Item::builtin_type(TypeKind::Int(IntKind::Int), true, context)
} else if value.abs() > u32::max_value() as i64 {
Item::builtin_type(TypeKind::Int(IntKind::ULongLong), true, context)
} else {
Item::builtin_type(TypeKind::Int(IntKind::UInt), true, context)
Expand Down Expand Up @@ -114,10 +116,7 @@ impl ClangSubItemParser for Var {
// Try to parse a literal token value
cursor.visit(|c, _| {
if c.kind() == CXCursor_IntegerLiteral {
value =
parse_int_literal_tokens(&c,
context.translation_unit(),
0);
value = parse_int_literal_tokens(&c, context.translation_unit());
}
CXChildVisit_Continue
});
Expand All @@ -137,24 +136,36 @@ impl ClangSubItemParser for Var {
}
}

/// Try and parse the immediately found tokens from an unit (if any) to integers
fn parse_int_literal_tokens(cursor: &clang::Cursor,
unit: &clang::TranslationUnit,
which: usize) -> Option<i64> {
use clangll::CXToken_Literal;
unit: &clang::TranslationUnit) -> Option<i64> {
use clangll::{CXToken_Literal, CXToken_Punctuation};

let mut lit = String::new();
let tokens = match unit.tokens(cursor) {
None => return None,
Some(tokens) => tokens,
};

if tokens.len() <= which || tokens[which].kind != CXToken_Literal {
return None;
for token in tokens {
match token.kind {
CXToken_Punctuation if token.spelling == "-" => {
// If there's ever any punctuation, we only need to worry about
// unary minus '-' (for now)
lit.push_str(&token.spelling);
},
CXToken_Literal => {
lit.push_str(&token.spelling);
break
},
_ => (),
}
}

let s = &tokens[which].spelling;
// TODO: try to preserve hex literals?
if s.starts_with("0x") {
i64::from_str_radix(&s[2..], 16).ok()
if lit.starts_with("0x") {
i64::from_str_radix(&lit[2..], 16).ok()
} else {
s.parse().ok()
lit.parse().ok()
}
}
39 changes: 20 additions & 19 deletions tests/expectations/jsval_layout_opaque.rs
Expand Up @@ -24,6 +24,7 @@ impl <T> ::std::clone::Clone for __BindgenUnionField<T> {
fn clone(&self) -> Self { Self::new() }
}
impl <T> ::std::marker::Copy for __BindgenUnionField<T> { }
pub const JSVAL_ALIGNMENT: ::std::os::raw::c_uint = 8;
pub const JSVAL_TAG_SHIFT: ::std::os::raw::c_uint = 47;
#[repr(u8)]
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
Expand Down Expand Up @@ -93,8 +94,8 @@ pub enum JSWhyMagic {
#[derive(Debug, Copy)]
pub struct jsval_layout {
pub asBits: __BindgenUnionField<u64>,
pub debugView: __BindgenUnionField<jsval_layout__bindgen_ty_bindgen_id_89>,
pub s: __BindgenUnionField<jsval_layout__bindgen_ty_bindgen_id_96>,
pub debugView: __BindgenUnionField<jsval_layout__bindgen_ty_bindgen_id_90>,
pub s: __BindgenUnionField<jsval_layout__bindgen_ty_bindgen_id_97>,
pub asDouble: __BindgenUnionField<f64>,
pub asPtr: __BindgenUnionField<*mut ::std::os::raw::c_void>,
pub asWord: __BindgenUnionField<usize>,
Expand All @@ -103,20 +104,20 @@ pub struct jsval_layout {
}
#[repr(C)]
#[derive(Debug, Copy)]
pub struct jsval_layout__bindgen_ty_bindgen_id_89 {
pub struct jsval_layout__bindgen_ty_bindgen_id_90 {
pub _bitfield_1: u64,
}
#[test]
fn bindgen_test_layout_jsval_layout__bindgen_ty_bindgen_id_89() {
assert_eq!(::std::mem::size_of::<jsval_layout__bindgen_ty_bindgen_id_89>()
fn bindgen_test_layout_jsval_layout__bindgen_ty_bindgen_id_90() {
assert_eq!(::std::mem::size_of::<jsval_layout__bindgen_ty_bindgen_id_90>()
, 8usize);
assert_eq!(::std::mem::align_of::<jsval_layout__bindgen_ty_bindgen_id_89>()
assert_eq!(::std::mem::align_of::<jsval_layout__bindgen_ty_bindgen_id_90>()
, 8usize);
}
impl Clone for jsval_layout__bindgen_ty_bindgen_id_89 {
impl Clone for jsval_layout__bindgen_ty_bindgen_id_90 {
fn clone(&self) -> Self { *self }
}
impl jsval_layout__bindgen_ty_bindgen_id_89 {
impl jsval_layout__bindgen_ty_bindgen_id_90 {
#[inline]
pub fn payload47(&self) -> u64 {
unsafe {
Expand Down Expand Up @@ -149,36 +150,36 @@ impl jsval_layout__bindgen_ty_bindgen_id_89 {
}
#[repr(C)]
#[derive(Debug, Copy)]
pub struct jsval_layout__bindgen_ty_bindgen_id_96 {
pub payload: jsval_layout__bindgen_ty_bindgen_id_96__bindgen_ty_bindgen_id_97,
pub struct jsval_layout__bindgen_ty_bindgen_id_97 {
pub payload: jsval_layout__bindgen_ty_bindgen_id_97__bindgen_ty_bindgen_id_98,
}
#[repr(C)]
#[derive(Debug, Copy)]
pub struct jsval_layout__bindgen_ty_bindgen_id_96__bindgen_ty_bindgen_id_97 {
pub struct jsval_layout__bindgen_ty_bindgen_id_97__bindgen_ty_bindgen_id_98 {
pub i32: __BindgenUnionField<i32>,
pub u32: __BindgenUnionField<u32>,
pub why: __BindgenUnionField<JSWhyMagic>,
pub bindgen_union_field: u32,
}
#[test]
fn bindgen_test_layout_jsval_layout__bindgen_ty_bindgen_id_96__bindgen_ty_bindgen_id_97() {
assert_eq!(::std::mem::size_of::<jsval_layout__bindgen_ty_bindgen_id_96__bindgen_ty_bindgen_id_97>()
fn bindgen_test_layout_jsval_layout__bindgen_ty_bindgen_id_97__bindgen_ty_bindgen_id_98() {
assert_eq!(::std::mem::size_of::<jsval_layout__bindgen_ty_bindgen_id_97__bindgen_ty_bindgen_id_98>()
, 4usize);
assert_eq!(::std::mem::align_of::<jsval_layout__bindgen_ty_bindgen_id_96__bindgen_ty_bindgen_id_97>()
assert_eq!(::std::mem::align_of::<jsval_layout__bindgen_ty_bindgen_id_97__bindgen_ty_bindgen_id_98>()
, 4usize);
}
impl Clone for
jsval_layout__bindgen_ty_bindgen_id_96__bindgen_ty_bindgen_id_97 {
jsval_layout__bindgen_ty_bindgen_id_97__bindgen_ty_bindgen_id_98 {
fn clone(&self) -> Self { *self }
}
#[test]
fn bindgen_test_layout_jsval_layout__bindgen_ty_bindgen_id_96() {
assert_eq!(::std::mem::size_of::<jsval_layout__bindgen_ty_bindgen_id_96>()
fn bindgen_test_layout_jsval_layout__bindgen_ty_bindgen_id_97() {
assert_eq!(::std::mem::size_of::<jsval_layout__bindgen_ty_bindgen_id_97>()
, 4usize);
assert_eq!(::std::mem::align_of::<jsval_layout__bindgen_ty_bindgen_id_96>()
assert_eq!(::std::mem::align_of::<jsval_layout__bindgen_ty_bindgen_id_97>()
, 4usize);
}
impl Clone for jsval_layout__bindgen_ty_bindgen_id_96 {
impl Clone for jsval_layout__bindgen_ty_bindgen_id_97 {
fn clone(&self) -> Self { *self }
}
impl Clone for jsval_layout {
Expand Down
10 changes: 10 additions & 0 deletions tests/expectations/whitelist_vars.rs
@@ -0,0 +1,10 @@
/* automatically generated by rust-bindgen */


#![allow(non_snake_case)]


pub const NONE: ::std::os::raw::c_uint = 0;
pub const FOO: ::std::os::raw::c_uint = 5;
pub const FOOB: ::std::os::raw::c_int = -2;
pub const FOOBAR: ::std::os::raw::c_int = -10;
4 changes: 4 additions & 0 deletions tests/headers/whitelist_vars.h
@@ -0,0 +1,4 @@
#define NONE 0
#define FOO 5
#define FOOB -2
#define FOOBAR (-10)