summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorbors-servo <lbergstrom+bors@mozilla.com>2017-02-15 18:01:25 -0800
committerGitHub <noreply@github.com>2017-02-15 18:01:25 -0800
commit6774efe9af2182e31ba1e11e14eee51ec63f5ab9 (patch)
tree5876846cf34e77bfc688b3f684615858e727b25d /src
parentac4971778b5823f94cbaf0188464790006e407c8 (diff)
parent70c61e1ebd1b0270953b8e33b74bfff578ccc82f (diff)
Auto merge of #518 - pornel:typedefstruct, r=emilio
typedef struct {} name Fixes #427 It looks like clang is doing the hard work of getting the right name from the typedef, but it falls back to arbitrary pretty-printed descriptions if it can't find a typedef. I couldn't find an API to check whether the name comes from a typedef, so I just filter out non-ident-like spellings.
Diffstat (limited to 'src')
-rw-r--r--src/ir/ty.rs37
1 files changed, 28 insertions, 9 deletions
diff --git a/src/ir/ty.rs b/src/ir/ty.rs
index ec168f02..332ad236 100644
--- a/src/ir/ty.rs
+++ b/src/ir/ty.rs
@@ -311,19 +311,21 @@ impl Type {
match self.kind {
TypeKind::Named => {
let name = self.name().expect("Unnamed named type?");
- let mut chars = name.chars();
- let first = chars.next().unwrap();
- let mut remaining = chars;
-
- let valid = (first.is_alphabetic() || first == '_') &&
- remaining.all(|c| c.is_alphanumeric() || c == '_');
-
- !valid
+ !Self::is_valid_identifier(&name)
}
_ => false,
}
}
+ /// Checks whether the name looks like an identifier,
+ /// i.e. is alphanumeric (including '_') and does not start with a digit.
+ pub fn is_valid_identifier(name: &str) -> bool {
+ let mut chars = name.chars();
+ let first_valid = chars.next().map(|c| c.is_alphabetic() || c == '_').unwrap_or(false);
+
+ first_valid && chars.all(|c| c.is_alphanumeric() || c == '_')
+ }
+
/// See safe_canonical_type.
pub fn canonical_type<'tr>(&'tr self,
ctx: &'tr BindgenContext)
@@ -454,7 +456,6 @@ fn is_invalid_named_type_unnamed() {
}
#[test]
-#[should_panic]
fn is_invalid_named_type_empty_name() {
let ty = Type::new(Some("".into()), None, TypeKind::Named, false);
assert!(ty.is_invalid_named_type())
@@ -1074,12 +1075,30 @@ impl Type {
}
CXType_Enum => {
let enum_ = Enum::from_ty(ty, ctx).expect("Not an enum?");
+
+ if name.is_empty() {
+ let pretty_name = ty.spelling();
+ if Self::is_valid_identifier(&pretty_name) {
+ name = pretty_name;
+ }
+ }
+
TypeKind::Enum(enum_)
}
CXType_Record => {
let complex =
CompInfo::from_ty(potential_id, ty, location, ctx)
.expect("Not a complex type?");
+
+ if name.is_empty() {
+ // The pretty-printed name may contain typedefed name,
+ // but may also be "struct (anonymous at .h:1)"
+ let pretty_name = ty.spelling();
+ if Self::is_valid_identifier(&pretty_name) {
+ name = pretty_name;
+ }
+ }
+
TypeKind::Comp(complex)
}
// FIXME: We stub vectors as arrays since in 99% of the cases the