aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid LeGare <legare@google.com>2022-03-02 21:48:47 +0000
committerAutomerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>2022-03-02 21:48:47 +0000
commit9462220143e9a759de1a3e30f6c2f92e5d42d4bf (patch)
tree66ee953affacd8924e3499ef6e55bb58871733ab
parent753c0498a954a000638b16c023f89e5347fd9978 (diff)
parent06227d3ba6dc639fd974cfce199d604400056019 (diff)
downloadbindgen-android13-dev.tar.gz
Update bindgen to 0.59.2 am: 19fbac68e6 am: 22c064f569 am: 06227d3ba6t_frc_odp_330442040t_frc_odp_330442000t_frc_ase_330444010android-13.0.0_r83android-13.0.0_r82android-13.0.0_r81android-13.0.0_r80android-13.0.0_r79android-13.0.0_r78android-13.0.0_r77android-13.0.0_r76android-13.0.0_r75android-13.0.0_r74android-13.0.0_r73android-13.0.0_r72android-13.0.0_r71android-13.0.0_r70android-13.0.0_r69android-13.0.0_r68android-13.0.0_r67android-13.0.0_r66android-13.0.0_r65android-13.0.0_r64android-13.0.0_r63android-13.0.0_r62android-13.0.0_r61android-13.0.0_r60android-13.0.0_r59android-13.0.0_r58android-13.0.0_r57android-13.0.0_r56android-13.0.0_r55android-13.0.0_r54android-13.0.0_r53android-13.0.0_r52android-13.0.0_r51android-13.0.0_r50android-13.0.0_r49android-13.0.0_r48android-13.0.0_r47android-13.0.0_r46android-13.0.0_r45android-13.0.0_r44android-13.0.0_r43android-13.0.0_r42android-13.0.0_r41android-13.0.0_r40android-13.0.0_r39android-13.0.0_r38android-13.0.0_r37android-13.0.0_r36android-13.0.0_r35android-13.0.0_r34android-13.0.0_r33android-13.0.0_r32android-13.0.0_r30android-13.0.0_r29android-13.0.0_r28android-13.0.0_r27android-13.0.0_r24android-13.0.0_r23android-13.0.0_r22android-13.0.0_r21android-13.0.0_r20android-13.0.0_r19android-13.0.0_r18android-13.0.0_r17android-13.0.0_r16aml_go_odp_330912000aml_go_ads_330915100aml_go_ads_330915000aml_go_ads_330913000android13-qpr3-s9-releaseandroid13-qpr3-s8-releaseandroid13-qpr3-s7-releaseandroid13-qpr3-s6-releaseandroid13-qpr3-s5-releaseandroid13-qpr3-s4-releaseandroid13-qpr3-s3-releaseandroid13-qpr3-s2-releaseandroid13-qpr3-s14-releaseandroid13-qpr3-s13-releaseandroid13-qpr3-s12-releaseandroid13-qpr3-s11-releaseandroid13-qpr3-s10-releaseandroid13-qpr3-s1-releaseandroid13-qpr3-releaseandroid13-qpr3-c-s8-releaseandroid13-qpr3-c-s7-releaseandroid13-qpr3-c-s6-releaseandroid13-qpr3-c-s5-releaseandroid13-qpr3-c-s4-releaseandroid13-qpr3-c-s3-releaseandroid13-qpr3-c-s2-releaseandroid13-qpr3-c-s12-releaseandroid13-qpr3-c-s11-releaseandroid13-qpr3-c-s10-releaseandroid13-qpr3-c-s1-releaseandroid13-qpr2-s9-releaseandroid13-qpr2-s8-releaseandroid13-qpr2-s7-releaseandroid13-qpr2-s6-releaseandroid13-qpr2-s5-releaseandroid13-qpr2-s3-releaseandroid13-qpr2-s2-releaseandroid13-qpr2-s12-releaseandroid13-qpr2-s11-releaseandroid13-qpr2-s10-releaseandroid13-qpr2-s1-releaseandroid13-qpr2-releaseandroid13-qpr2-b-s1-releaseandroid13-qpr1-s8-releaseandroid13-qpr1-s7-releaseandroid13-qpr1-s6-releaseandroid13-qpr1-s5-releaseandroid13-qpr1-s4-releaseandroid13-qpr1-s3-releaseandroid13-qpr1-s2-releaseandroid13-qpr1-s1-releaseandroid13-qpr1-releaseandroid13-mainline-go-adservices-releaseandroid13-frc-odp-releaseandroid13-devandroid13-d4-s2-releaseandroid13-d4-s1-releaseandroid13-d4-releaseandroid13-d3-s1-releaseandroid13-d2-release
Original change: https://android-review.googlesource.com/c/platform/external/rust/crates/bindgen/+/2005111 Change-Id: Idebbfdaba156a78c76936407abf7f5c36c579d90
-rw-r--r--.cargo_vcs_info.json2
-rw-r--r--Android.bp4
-rw-r--r--Cargo.lock171
-rw-r--r--Cargo.toml17
-rw-r--r--Cargo.toml.orig8
-rw-r--r--METADATA10
-rw-r--r--README.md2
-rw-r--r--src/clang.rs77
-rw-r--r--src/codegen/helpers.rs6
-rw-r--r--src/codegen/impl_debug.rs37
-rw-r--r--src/codegen/impl_partialeq.rs5
-rw-r--r--src/codegen/mod.rs142
-rw-r--r--src/codegen/struct_layout.rs7
-rw-r--r--src/features.rs18
-rw-r--r--src/ir/analysis/derive.rs76
-rw-r--r--src/ir/analysis/has_destructor.rs18
-rw-r--r--src/ir/analysis/has_vtable.rs14
-rw-r--r--src/ir/analysis/mod.rs4
-rw-r--r--src/ir/analysis/sizedness.rs20
-rw-r--r--src/ir/analysis/template_params.rs86
-rw-r--r--src/ir/annotations.rs29
-rw-r--r--src/ir/comment.rs6
-rw-r--r--src/ir/comp.rs130
-rw-r--r--src/ir/context.rs187
-rw-r--r--src/ir/enum_ty.rs4
-rw-r--r--src/ir/function.rs22
-rw-r--r--src/ir/item.rs94
-rw-r--r--src/ir/layout.rs2
-rw-r--r--src/ir/module.rs6
-rw-r--r--src/ir/objc.rs69
-rw-r--r--src/ir/template.rs4
-rw-r--r--src/ir/traversal.rs14
-rw-r--r--src/ir/ty.rs131
-rw-r--r--src/ir/var.rs11
-rw-r--r--src/lib.rs95
-rw-r--r--src/log_stubs.rs24
-rw-r--r--src/main.rs6
-rw-r--r--src/options.rs31
38 files changed, 798 insertions, 791 deletions
diff --git a/.cargo_vcs_info.json b/.cargo_vcs_info.json
index 7298dd9..f1c8552 100644
--- a/.cargo_vcs_info.json
+++ b/.cargo_vcs_info.json
@@ -1,5 +1,5 @@
{
"git": {
- "sha1": "9a9438f3d6a3523c69d7bc890e8608b63dbe38a5"
+ "sha1": "89032649044d875983a851fff6fbde2d4e2ceaeb"
}
}
diff --git a/Android.bp b/Android.bp
index 3696cbb..9166c33 100644
--- a/Android.bp
+++ b/Android.bp
@@ -46,7 +46,7 @@ rust_binary_host {
// has rustc warnings
crate_name: "bindgen",
cargo_env_compat: true,
- cargo_pkg_version: "0.59.1",
+ cargo_pkg_version: "0.59.2",
srcs: [
"src/main.rs",
":copy_bindgen_build_out",
@@ -82,7 +82,7 @@ rust_library_host {
// has rustc warnings
crate_name: "bindgen",
cargo_env_compat: true,
- cargo_pkg_version: "0.59.1",
+ cargo_pkg_version: "0.59.2",
srcs: [
"src/lib.rs",
":copy_bindgen_build_out",
diff --git a/Cargo.lock b/Cargo.lock
index 0e93f41..d79a408 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -33,7 +33,7 @@ dependencies = [
[[package]]
name = "bindgen"
-version = "0.59.1"
+version = "0.59.2"
dependencies = [
"bitflags",
"cexpr",
@@ -61,43 +61,25 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cf1de2fe8c75bc145a2f577add951f8134889b4795d47466a54a5c846d691693"
[[package]]
-name = "bitvec"
-version = "0.19.5"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "8942c8d352ae1838c9dda0b0ca2ab657696ef2232a20147cf1b30ae1a9cb4321"
-dependencies = [
- "funty",
- "radium",
- "tap",
- "wyz",
-]
-
-[[package]]
name = "cexpr"
-version = "0.5.0"
+version = "0.6.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "db507a7679252d2276ed0dd8113c6875ec56d3089f9225b2b42c30cc1f8e5c89"
+checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766"
dependencies = [
"nom",
]
[[package]]
name = "cfg-if"
-version = "0.1.10"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822"
-
-[[package]]
-name = "cfg-if"
version = "1.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
[[package]]
name = "clang-sys"
-version = "1.0.3"
+version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "0659001ab56b791be01d4b729c44376edc6718cf389a502e579b77b758f3296c"
+checksum = "853eda514c284c2287f4bf20ae614f8781f40a81d32ecda6e91449304dfe077c"
dependencies = [
"glob",
"libc",
@@ -126,10 +108,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0e25ea47919b1560c4e3b7fe0aaab9becf5b84a10325ddf7db0f0ba5e1026499"
[[package]]
+name = "either"
+version = "1.6.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "e78d4f1cc4ae33bbfc157ed5d5a5ef3bc29227303d595861deb238fcec4e9457"
+
+[[package]]
name = "env_logger"
-version = "0.8.1"
+version = "0.9.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "54532e3223c5af90a6a757c90b5c5521564b07e5e7a958681bcd2afad421cdcd"
+checksum = "0b2cf0344971ee6c64c31be0d530793fba457d322dfec2810c453d0ef228f9c3"
dependencies = [
"atty",
"humantime",
@@ -139,18 +127,12 @@ dependencies = [
]
[[package]]
-name = "funty"
-version = "1.1.0"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "fed34cd105917e91daa4da6b3728c47b068749d6a62c59811f06ed2ac71d9da7"
-
-[[package]]
name = "getrandom"
-version = "0.2.2"
+version = "0.2.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "c9495705279e7140bf035dde1f6e750c162df8b625267cd52cc44e0b156732c8"
+checksum = "7fcd999463524c52659517fe2cea98493cfe485d10565e7b0fb07dbba7ad2753"
dependencies = [
- "cfg-if 1.0.0",
+ "cfg-if",
"libc",
"wasi",
]
@@ -163,18 +145,18 @@ checksum = "9b919933a397b79c37e33b77bb2aa3dc8eb6e165ad809e58ff75bc7db2e34574"
[[package]]
name = "hermit-abi"
-version = "0.1.17"
+version = "0.1.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "5aca5565f760fb5b220e499d72710ed156fdb74e631659e99377d9ebfbd13ae8"
+checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33"
dependencies = [
"libc",
]
[[package]]
name = "humantime"
-version = "2.0.1"
+version = "2.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "3c1ad908cc71012b7bea4d0c53ba96a8cba9962f048fa68d143376143d863b7a"
+checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4"
[[package]]
name = "lazy_static"
@@ -190,27 +172,27 @@ checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55"
[[package]]
name = "libc"
-version = "0.2.80"
+version = "0.2.98"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "4d58d1b70b004888f764dfbf6a26a3b0342a1632d33968e4a179d8011c760614"
+checksum = "320cfe77175da3a483efed4bc0adc1968ca050b098ce4f2f1c13a56626128790"
[[package]]
name = "libloading"
-version = "0.6.5"
+version = "0.7.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "1090080fe06ec2648d0da3881d9453d97e71a45f00eb179af7fdd7e3f686fdb0"
+checksum = "6f84d96438c15fcd6c3f244c8fce01d1e2b9c6b5623e9c711dc9286d8fc92d6a"
dependencies = [
- "cfg-if 1.0.0",
+ "cfg-if",
"winapi",
]
[[package]]
name = "log"
-version = "0.4.11"
+version = "0.4.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "4fabed175da42fed1fa0746b0ea71f412aa9d35e76e95e59b192c64b9dc2bf8b"
+checksum = "51b9bbe6c47d51fc3e1a9b945965946b4c44142ab8792c50835a980d362c2710"
dependencies = [
- "cfg-if 0.1.10",
+ "cfg-if",
]
[[package]]
@@ -220,14 +202,19 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0ee1c47aaa256ecabcaea351eae4a9b01ef39ed810004e298d2511ed284b1525"
[[package]]
+name = "minimal-lexical"
+version = "0.1.4"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "9c64630dcdd71f1a64c435f54885086a0de5d6a12d104d69b165fb7d5286d677"
+
+[[package]]
name = "nom"
-version = "6.2.1"
+version = "7.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "9c5c51b9083a3c620fa67a2a635d1ce7d95b897e957d6b28ff9a5da960a103a6"
+checksum = "7ffd9d26838a953b4af82cbeb9f1592c6798916983959be223a7124e992742c1"
dependencies = [
- "bitvec",
- "funty",
"memchr",
+ "minimal-lexical",
"version_check",
]
@@ -245,33 +232,27 @@ checksum = "ac74c624d6b2d21f425f752262f42188365d7b8ff1aff74c82e45136510a4857"
[[package]]
name = "proc-macro2"
-version = "1.0.24"
+version = "1.0.28"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "1e0704ee1a7e00d7bb417d0770ea303c1bccbabf0ef1667dae92b5967f5f8a71"
+checksum = "5c7ed8b8c7b886ea3ed7dde405212185f423ab44682667c8c6dd14aa1d9f6612"
dependencies = [
"unicode-xid",
]
[[package]]
name = "quote"
-version = "1.0.7"
+version = "1.0.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "aa563d17ecb180e500da1cfd2b028310ac758de548efdd203e18f283af693f37"
+checksum = "c3d0b9745dc2debf507c8422de05d7226cc1f0644216dfdfead988f9b1ab32a7"
dependencies = [
"proc-macro2",
]
[[package]]
-name = "radium"
-version = "0.5.3"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "941ba9d78d8e2f7ce474c015eea4d9c6d25b6a3327f9832ee29a4de27f91bbb8"
-
-[[package]]
name = "rand"
-version = "0.8.3"
+version = "0.8.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "0ef9e7e66b4468674bfcb0c81af8b7fa0bb154fa9f28eb840da5c447baeb8d7e"
+checksum = "2e7573632e6454cf6b99d7aac4ccca54be06da05aca2ef7423d22d27d4d4bcd8"
dependencies = [
"libc",
"rand_chacha",
@@ -281,9 +262,9 @@ dependencies = [
[[package]]
name = "rand_chacha"
-version = "0.3.0"
+version = "0.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "e12735cf05c9e10bf21534da50a147b924d555dc7a547c42e6bb2d5b6017ae0d"
+checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88"
dependencies = [
"ppv-lite86",
"rand_core",
@@ -291,48 +272,47 @@ dependencies = [
[[package]]
name = "rand_core"
-version = "0.6.2"
+version = "0.6.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "34cf66eb183df1c5876e2dcf6b13d57340741e8dc255b48e40a26de954d06ae7"
+checksum = "d34f1408f55294453790c48b2f1ebbb1c5b4b7563eb1f418bcfcfdbb06ebb4e7"
dependencies = [
"getrandom",
]
[[package]]
name = "rand_hc"
-version = "0.3.0"
+version = "0.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "3190ef7066a446f2e7f42e239d161e905420ccab01eb967c9eb27d21b2322a73"
+checksum = "d51e9f596de227fda2ea6c84607f5558e196eeaf43c986b724ba4fb8fdf497e7"
dependencies = [
"rand_core",
]
[[package]]
name = "redox_syscall"
-version = "0.2.5"
+version = "0.2.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "94341e4e44e24f6b591b59e47a8a027df12e008d73fd5672dbea9cc22f4507d9"
+checksum = "5ab49abadf3f9e1c4bc499e8845e152ad87d2ad2d30371841171169e9d75feee"
dependencies = [
"bitflags",
]
[[package]]
name = "regex"
-version = "1.4.2"
+version = "1.4.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "38cf2c13ed4745de91a5eb834e11c00bcc3709e773173b2ce4c56c9fbde04b9c"
+checksum = "2a26af418b574bd56588335b3a3659a65725d4e636eb1016c2f9e3b38c7cc759"
dependencies = [
"aho-corasick",
"memchr",
"regex-syntax",
- "thread_local",
]
[[package]]
name = "regex-syntax"
-version = "0.6.21"
+version = "0.6.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "3b181ba2dcf07aaccad5448e8ead58db5b742cf85dfe035e2227f137a539a189"
+checksum = "f497285884f3fcff424ffc933e56d7cbca511def0c9831a7f9b5f6153e3cc89b"
[[package]]
name = "remove_dir_all"
@@ -362,18 +342,12 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8ea5119cdb4c55b55d432abb513a0429384878c15dde60cc77b1c99de1a95a6a"
[[package]]
-name = "tap"
-version = "1.0.1"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "55937e1799185b12863d447f42597ed69d9928686b8d88a1df17376a097d8369"
-
-[[package]]
name = "tempfile"
version = "3.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dac1c663cfc93810f88aed9b8941d48cabf856a1b111c29a40439018d870eb22"
dependencies = [
- "cfg-if 1.0.0",
+ "cfg-if",
"libc",
"rand",
"redox_syscall",
@@ -383,9 +357,9 @@ dependencies = [
[[package]]
name = "termcolor"
-version = "1.1.0"
+version = "1.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "bb6bfa289a4d7c5766392812c0a1f4c1ba45afa1ad47803c11e1f407d846d75f"
+checksum = "2dfed899f0eb03f32ee8c6a0aabdb8a7949659e3466561fc0adf54e26d88c5f4"
dependencies = [
"winapi-util",
]
@@ -400,15 +374,6 @@ dependencies = [
]
[[package]]
-name = "thread_local"
-version = "1.0.1"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "d40c6d1b69745a6ec6fb1ca717914848da4b44ae29d9b3080cbee91d72a69b14"
-dependencies = [
- "lazy_static",
-]
-
-[[package]]
name = "unicode-width"
version = "0.1.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
@@ -416,9 +381,9 @@ checksum = "9337591893a19b88d8d87f2cec1e73fad5cdfd10e5a6f349f498ad6ea2ffb1e3"
[[package]]
name = "unicode-xid"
-version = "0.2.1"
+version = "0.2.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "f7fe0bb3479651439c9112f72b6c505038574c9fbb575ed1bf3b797fa39dd564"
+checksum = "8ccb82d61f80a663efe1f787a51b16b5a51e3314d6ac365b08639f52387b33f3"
[[package]]
name = "vec_map"
@@ -428,9 +393,9 @@ checksum = "f1bddf1187be692e79c5ffeab891132dfb0f236ed36a43c7ed39f1165ee20191"
[[package]]
name = "version_check"
-version = "0.9.2"
+version = "0.9.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "b5a972e5669d67ba988ce3dc826706fb0a8b01471c088cb0b6110b805cc36aed"
+checksum = "5fecdca9a5291cc2b8dcf7dc02453fee791a280f3743cb0905f8822ae463b3fe"
[[package]]
name = "wasi"
@@ -440,10 +405,12 @@ checksum = "fd6fbd9a79829dd1ad0cc20627bf1ed606756a7f77edff7b66b7064f9cb327c6"
[[package]]
name = "which"
-version = "3.1.1"
+version = "4.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "d011071ae14a2f6671d0b74080ae0cd8ebf3a6f8c9589a2cd45f23126fe29724"
+checksum = "7cc009ab82a2afc94b9e467ab4214aee9cad1356cd9191264203d7d72006e00d"
dependencies = [
+ "either",
+ "lazy_static",
"libc",
]
@@ -477,9 +444,3 @@ name = "winapi-x86_64-pc-windows-gnu"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
-
-[[package]]
-name = "wyz"
-version = "0.2.0"
-source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "85e60b0d1b5f99db2556934e21937020776a5d31520bf169e851ac44e6420214"
diff --git a/Cargo.toml b/Cargo.toml
index 08e2383..8b8853a 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -3,17 +3,16 @@
# When uploading crates to the registry Cargo will automatically
# "normalize" Cargo.toml files for maximal compatibility
# with all versions of Cargo and also rewrite `path` dependencies
-# to registry (e.g., crates.io) dependencies
+# to registry (e.g., crates.io) dependencies.
#
-# If you believe there's an error in this file please file an
-# issue against the rust-lang/cargo repository. If you're
-# editing this file be aware that the upstream Cargo.toml
-# will likely look very different (and much more reasonable)
+# If you are reading this file be aware that the original Cargo.toml
+# will likely look very different (and much more reasonable).
+# See Cargo.toml.orig for the original contents.
[package]
edition = "2018"
name = "bindgen"
-version = "0.59.1"
+version = "0.59.2"
authors = ["Jyun-Yan You <jyyou.tw@gmail.com>", "Emilio Cobos Álvarez <emilio@crisal.io>", "Nick Fitzgerald <fitzgen@gmail.com>", "The Servo project developers"]
build = "build.rs"
include = ["LICENSE", "README.md", "Cargo.toml", "build.rs", "src/*.rs", "src/**/*.rs"]
@@ -38,7 +37,7 @@ required-features = ["clap"]
version = "1.0.3"
[dependencies.cexpr]
-version = "0.5"
+version = "0.6"
[dependencies.clang-sys]
version = "1"
@@ -49,7 +48,7 @@ version = "2"
optional = true
[dependencies.env_logger]
-version = "0.8"
+version = "0.9.0"
optional = true
[dependencies.lazy_static]
@@ -85,7 +84,7 @@ version = "1.0.1"
version = "1"
[dependencies.which]
-version = "3.0"
+version = "4.2.1"
optional = true
default-features = false
[dev-dependencies.clap]
diff --git a/Cargo.toml.orig b/Cargo.toml.orig
index 7cf5953..ba41a22 100644
--- a/Cargo.toml.orig
+++ b/Cargo.toml.orig
@@ -14,7 +14,7 @@ readme = "README.md"
repository = "https://github.com/rust-lang/rust-bindgen"
documentation = "https://docs.rs/bindgen"
homepage = "https://rust-lang.github.io/rust-bindgen/"
-version = "0.59.1"
+version = "0.59.2"
edition = "2018"
build = "build.rs"
@@ -47,7 +47,7 @@ tempfile = "3"
[dependencies]
bitflags = "1.0.3"
-cexpr = "0.5"
+cexpr = "0.6"
# This kinda sucks: https://github.com/rust-lang/cargo/issues/1982
clap = { version = "2", optional = true }
clang-sys = { version = "1", features = ["clang_6_0"] }
@@ -56,14 +56,14 @@ lazy_static = "1"
peeking_take_while = "0.1.2"
quote = { version = "1", default-features = false }
regex = { version = "1.0", default-features = false , features = [ "std", "unicode"]}
-which = { version = "3.0", optional = true, default-features = false }
+which = { version = "4.2.1", optional = true, default-features = false }
shlex = "1"
rustc-hash = "1.0.1"
proc-macro2 = { version = "1", default-features = false }
[dependencies.env_logger]
optional = true
-version = "0.8"
+version = "0.9.0"
[dependencies.log]
optional = true
diff --git a/METADATA b/METADATA
index 87aa75a..85b1cce 100644
--- a/METADATA
+++ b/METADATA
@@ -7,13 +7,13 @@ third_party {
}
url {
type: ARCHIVE
- value: "https://static.crates.io/crates/bindgen/bindgen-0.59.1.crate"
+ value: "https://static.crates.io/crates/bindgen/bindgen-0.59.2.crate"
}
- version: "0.59.1"
+ version: "0.59.2"
license_type: NOTICE
last_upgrade_date {
- year: 2021
- month: 8
- day: 9
+ year: 2022
+ month: 3
+ day: 1
}
}
diff --git a/README.md b/README.md
index 00f66eb..7b2dbbc 100644
--- a/README.md
+++ b/README.md
@@ -39,7 +39,7 @@ extern "C" {
## MSRV
-The minimum supported Rust version is **1.44**.
+The minimum supported Rust version is **1.46**.
No MSRV bump policy has been established yet, so MSRV may increase in any release.
diff --git a/src/clang.rs b/src/clang.rs
index db6467e..074d459 100644
--- a/src/clang.rs
+++ b/src/clang.rs
@@ -4,9 +4,7 @@
#![allow(non_upper_case_globals, dead_code)]
use crate::ir::context::BindgenContext;
-use cexpr;
use clang_sys::*;
-use regex;
use std::ffi::{CStr, CString};
use std::fmt;
use std::hash::Hash;
@@ -85,7 +83,7 @@ impl Cursor {
let mut result = Vec::with_capacity(count);
for i in 0..count {
- let string_ptr = (*manglings).Strings.offset(i as isize);
+ let string_ptr = (*manglings).Strings.add(i);
result.push(cxstring_to_string_leaky(*string_ptr));
}
clang_disposeStringSet(manglings);
@@ -223,12 +221,12 @@ impl Cursor {
/// not tracking the type declaration but the location of the cursor, given
/// clang doesn't expose a proper declaration for these types.
pub fn is_template_like(&self) -> bool {
- match self.kind() {
+ matches!(
+ self.kind(),
CXCursor_ClassTemplate |
- CXCursor_ClassTemplatePartialSpecialization |
- CXCursor_TypeAliasTemplateDecl => true,
- _ => false,
- }
+ CXCursor_ClassTemplatePartialSpecialization |
+ CXCursor_TypeAliasTemplateDecl
+ )
}
/// Is this Cursor pointing to a function-like macro definition?
@@ -275,7 +273,7 @@ impl Cursor {
return parent.is_in_non_fully_specialized_template();
}
- return true;
+ true
}
/// Is this cursor pointing a valid referent?
@@ -402,12 +400,9 @@ impl Cursor {
where
Visitor: FnMut(Cursor) -> CXChildVisitResult,
{
+ let data = &mut visitor as *mut Visitor;
unsafe {
- clang_visitChildren(
- self.x,
- visit_children::<Visitor>,
- mem::transmute(&mut visitor),
- );
+ clang_visitChildren(self.x, visit_children::<Visitor>, data.cast());
}
}
@@ -900,7 +895,7 @@ extern "C" fn visit_children<Visitor>(
where
Visitor: FnMut(Cursor) -> CXChildVisitResult,
{
- let func: &mut Visitor = unsafe { mem::transmute(data) };
+ let func: &mut Visitor = unsafe { &mut *(data as *mut Visitor) };
let child = Cursor { x: cur };
(*func)(child)
@@ -1027,7 +1022,7 @@ impl Type {
let s = unsafe { cxstring_into_string(clang_getTypeSpelling(self.x)) };
// Clang 5.0 introduced changes in the spelling API so it returned the
// full qualified name. Let's undo that here.
- if s.split("::").all(|s| is_valid_identifier(s)) {
+ if s.split("::").all(is_valid_identifier) {
if let Some(s) = s.split("::").last() {
return s.to_owned();
}
@@ -1055,7 +1050,7 @@ impl Type {
ctx.target_pointer_size() as c_longlong
}
// Work-around https://bugs.llvm.org/show_bug.cgi?id=40813
- CXType_Auto if self.is_non_deductible_auto_type() => return -6,
+ CXType_Auto if self.is_non_deductible_auto_type() => -6,
_ => unsafe { clang_Type_getSizeOf(self.x) },
}
}
@@ -1068,7 +1063,7 @@ impl Type {
ctx.target_pointer_size() as c_longlong
}
// Work-around https://bugs.llvm.org/show_bug.cgi?id=40813
- CXType_Auto if self.is_non_deductible_auto_type() => return -6,
+ CXType_Auto if self.is_non_deductible_auto_type() => -6,
_ => unsafe { clang_Type_getAlignOf(self.x) },
}
}
@@ -1286,12 +1281,12 @@ impl Type {
// nasty... But can happen in <type_traits>. Unfortunately I couldn't
// reduce it enough :(
self.template_args().map_or(false, |args| args.len() > 0) &&
- match self.declaration().kind() {
+ !matches!(
+ self.declaration().kind(),
CXCursor_ClassTemplatePartialSpecialization |
- CXCursor_TypeAliasTemplateDecl |
- CXCursor_TemplateTemplateParameter => false,
- _ => true,
- }
+ CXCursor_TypeAliasTemplateDecl |
+ CXCursor_TemplateTemplateParameter
+ )
}
/// Is this type an associated template type? Eg `T::Associated` in
@@ -1406,6 +1401,12 @@ impl fmt::Display for SourceLocation {
}
}
+impl fmt::Debug for SourceLocation {
+ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+ write!(f, "{}", self)
+ }
+}
+
/// A comment in the source text.
///
/// Comments are sort of parsed by Clang, and have a tree structure.
@@ -1704,11 +1705,7 @@ impl UnsavedFile {
Contents: contents.as_ptr(),
Length: contents.as_bytes().len() as c_ulong,
};
- UnsavedFile {
- x: x,
- name: name,
- contents: contents,
- }
+ UnsavedFile { x, name, contents }
}
}
@@ -1819,7 +1816,7 @@ pub fn ast_dump(c: &Cursor, depth: isize) -> CXChildVisitResult {
if let Some(refd) = c.referenced() {
if refd != *c {
- println!("");
+ println!();
print_cursor(
depth,
String::from(prefix) + "referenced.",
@@ -1830,7 +1827,7 @@ pub fn ast_dump(c: &Cursor, depth: isize) -> CXChildVisitResult {
let canonical = c.canonical();
if canonical != *c {
- println!("");
+ println!();
print_cursor(
depth,
String::from(prefix) + "canonical.",
@@ -1840,7 +1837,7 @@ pub fn ast_dump(c: &Cursor, depth: isize) -> CXChildVisitResult {
if let Some(specialized) = c.specialized() {
if specialized != *c {
- println!("");
+ println!();
print_cursor(
depth,
String::from(prefix) + "specialized.",
@@ -1850,7 +1847,7 @@ pub fn ast_dump(c: &Cursor, depth: isize) -> CXChildVisitResult {
}
if let Some(parent) = c.fallible_semantic_parent() {
- println!("");
+ println!();
print_cursor(
depth,
String::from(prefix) + "semantic-parent.",
@@ -1898,34 +1895,34 @@ pub fn ast_dump(c: &Cursor, depth: isize) -> CXChildVisitResult {
let canonical = ty.canonical_type();
if canonical != *ty {
- println!("");
+ println!();
print_type(depth, String::from(prefix) + "canonical.", &canonical);
}
if let Some(pointee) = ty.pointee_type() {
if pointee != *ty {
- println!("");
+ println!();
print_type(depth, String::from(prefix) + "pointee.", &pointee);
}
}
if let Some(elem) = ty.elem_type() {
if elem != *ty {
- println!("");
+ println!();
print_type(depth, String::from(prefix) + "elements.", &elem);
}
}
if let Some(ret) = ty.ret_type() {
if ret != *ty {
- println!("");
+ println!();
print_type(depth, String::from(prefix) + "return.", &ret);
}
}
let named = ty.named();
if named != *ty && named.is_valid() {
- println!("");
+ println!();
print_type(depth, String::from(prefix) + "named.", &named);
}
}
@@ -1933,13 +1930,13 @@ pub fn ast_dump(c: &Cursor, depth: isize) -> CXChildVisitResult {
print_indent(depth, "(");
print_cursor(depth, "", c);
- println!("");
+ println!();
let ty = c.cur_type();
print_type(depth, "type.", &ty);
let declaration = ty.declaration();
if declaration != *c && declaration.kind() != CXCursor_NoDeclFound {
- println!("");
+ println!();
print_cursor(depth, "type.declaration.", &declaration);
}
@@ -1947,7 +1944,7 @@ pub fn ast_dump(c: &Cursor, depth: isize) -> CXChildVisitResult {
let mut found_children = false;
c.visit(|s| {
if !found_children {
- println!("");
+ println!();
found_children = true;
}
ast_dump(&s, depth + 1)
diff --git a/src/codegen/helpers.rs b/src/codegen/helpers.rs
index 205995b..2ce6894 100644
--- a/src/codegen/helpers.rs
+++ b/src/codegen/helpers.rs
@@ -230,14 +230,14 @@ pub mod ast_ty {
}
pub fn byte_array_expr(bytes: &[u8]) -> TokenStream {
- let mut bytes: Vec<_> = bytes.iter().cloned().collect();
+ let mut bytes: Vec<_> = bytes.to_vec();
bytes.push(0);
quote! { [ #(#bytes),* ] }
}
pub fn cstr_expr(mut string: String) -> TokenStream {
string.push('\0');
- let b = proc_macro2::Literal::byte_string(&string.as_bytes());
+ let b = proc_macro2::Literal::byte_string(string.as_bytes());
quote! {
#b
}
@@ -271,7 +271,7 @@ pub mod ast_ty {
}
warn!("Unknown non-finite float number: {:?}", f);
- return Err(());
+ Err(())
}
pub fn arguments_from_signature(
diff --git a/src/codegen/impl_debug.rs b/src/codegen/impl_debug.rs
index 661711e..0e2cd33 100644
--- a/src/codegen/impl_debug.rs
+++ b/src/codegen/impl_debug.rs
@@ -2,7 +2,6 @@ use crate::ir::comp::{BitfieldUnit, CompKind, Field, FieldData, FieldMethods};
use crate::ir::context::BindgenContext;
use crate::ir::item::{HasTypeParamInArray, IsOpaque, Item, ItemCanonicalName};
use crate::ir::ty::{TypeKind, RUST_DERIVE_IN_ARRAY_LIMIT};
-use proc_macro2;
pub fn gen_debug_impl(
ctx: &BindgenContext,
@@ -23,8 +22,8 @@ pub fn gen_debug_impl(
}
CompKind::Struct => {
let processed_fields = fields.iter().filter_map(|f| match f {
- &Field::DataMember(ref fd) => fd.impl_debug(ctx, ()),
- &Field::Bitfields(ref bu) => bu.impl_debug(ctx, ()),
+ Field::DataMember(ref fd) => fd.impl_debug(ctx, ()),
+ Field::Bitfields(ref bu) => bu.impl_debug(ctx, ()),
});
for (i, (fstring, toks)) in processed_fields.enumerate() {
@@ -186,24 +185,22 @@ impl<'a> ImplDebug<'a> for Item {
{
// The simple case
debug_print(name, quote! { #name_ident })
+ } else if ctx.options().use_core {
+ // There is no String in core; reducing field visibility to avoid breaking
+ // no_std setups.
+ Some((format!("{}: [...]", name), vec![]))
} else {
- if ctx.options().use_core {
- // There is no String in core; reducing field visibility to avoid breaking
- // no_std setups.
- Some((format!("{}: [...]", name), vec![]))
- } else {
- // Let's implement our own print function
- Some((
- format!("{}: [{{}}]", name),
- vec![quote! {
- self.#name_ident
- .iter()
- .enumerate()
- .map(|(i, v)| format!("{}{:?}", if i > 0 { ", " } else { "" }, v))
- .collect::<String>()
- }],
- ))
- }
+ // Let's implement our own print function
+ Some((
+ format!("{}: [{{}}]", name),
+ vec![quote! {
+ self.#name_ident
+ .iter()
+ .enumerate()
+ .map(|(i, v)| format!("{}{:?}", if i > 0 { ", " } else { "" }, v))
+ .collect::<String>()
+ }],
+ ))
}
}
TypeKind::Vector(_, len) => {
diff --git a/src/codegen/impl_partialeq.rs b/src/codegen/impl_partialeq.rs
index 5a1ba3f..960306f 100644
--- a/src/codegen/impl_partialeq.rs
+++ b/src/codegen/impl_partialeq.rs
@@ -2,7 +2,6 @@ use crate::ir::comp::{CompInfo, CompKind, Field, FieldMethods};
use crate::ir::context::BindgenContext;
use crate::ir::item::{IsOpaque, Item};
use crate::ir::ty::{TypeKind, RUST_DERIVE_IN_ARRAY_LIMIT};
-use proc_macro2;
/// Generate a manual implementation of `PartialEq` trait for the
/// specified compound type.
@@ -51,7 +50,7 @@ pub fn gen_partialeq_impl(
}
Field::Bitfields(ref bu) => {
for bitfield in bu.bitfields() {
- if let Some(_) = bitfield.name() {
+ if bitfield.name().is_some() {
let getter_name = bitfield.getter_name();
let name_ident = ctx.rust_ident_raw(getter_name);
tokens.push(quote! {
@@ -104,7 +103,7 @@ fn gen_field(
TypeKind::Opaque => quote_equals(name_ident),
TypeKind::TemplateInstantiation(ref inst) => {
- if inst.is_opaque(ctx, &ty_item) {
+ if inst.is_opaque(ctx, ty_item) {
quote! {
&self. #name_ident [..] == &other. #name_ident [..]
}
diff --git a/src/codegen/mod.rs b/src/codegen/mod.rs
index 0f3337a..19886e3 100644
--- a/src/codegen/mod.rs
+++ b/src/codegen/mod.rs
@@ -48,7 +48,6 @@ use proc_macro2::{self, Ident, Span};
use quote::TokenStreamExt;
use crate::{Entry, HashMap, HashSet};
-use std;
use std::borrow::Cow;
use std::cell::Cell;
use std::collections::VecDeque;
@@ -58,7 +57,7 @@ use std::ops;
use std::str::FromStr;
// Name of type defined in constified enum module
-pub static CONSTIFIED_ENUM_MODULE_REPR_NAME: &'static str = "Type";
+pub static CONSTIFIED_ENUM_MODULE_REPR_NAME: &str = "Type";
fn top_level_path(
ctx: &BindgenContext,
@@ -666,10 +665,21 @@ impl CodeGenerator for Var {
match String::from_utf8(bytes.clone()) {
Ok(string) => {
let cstr = helpers::ast_ty::cstr_expr(string);
- result.push(quote! {
- #(#attrs)*
- pub const #canonical_ident : &'static #ty = #cstr ;
- });
+ if ctx
+ .options()
+ .rust_features
+ .static_lifetime_elision
+ {
+ result.push(quote! {
+ #(#attrs)*
+ pub const #canonical_ident : &#ty = #cstr ;
+ });
+ } else {
+ result.push(quote! {
+ #(#attrs)*
+ pub const #canonical_ident : &'static #ty = #cstr ;
+ });
+ }
}
Err(..) => {
let bytes = helpers::ast_ty::byte_array_expr(bytes);
@@ -681,12 +691,11 @@ impl CodeGenerator for Var {
}
}
VarType::Float(f) => {
- match helpers::ast_ty::float_expr(ctx, f) {
- Ok(expr) => result.push(quote! {
+ if let Ok(expr) = helpers::ast_ty::float_expr(ctx, f) {
+ result.push(quote! {
#(#attrs)*
pub const #canonical_ident : #ty = #expr ;
- }),
- Err(..) => return,
+ });
}
}
VarType::Char(c) => {
@@ -698,7 +707,7 @@ impl CodeGenerator for Var {
}
} else {
// If necessary, apply a `#[link_name]` attribute
- let link_name = self.mangled_name().unwrap_or(self.name());
+ let link_name = self.mangled_name().unwrap_or_else(|| self.name());
if !utils::names_will_be_identical_after_mangling(
&canonical_name,
link_name,
@@ -756,7 +765,6 @@ impl CodeGenerator for Type {
// converted to rust types in fields, arguments, and such.
// NOTE(emilio): If you add to this list, make sure to also add
// it to BindgenContext::compute_allowlisted_and_codegen_items.
- return;
}
TypeKind::TemplateInstantiation(ref inst) => {
inst.codegen(ctx, result, item)
@@ -886,12 +894,9 @@ impl CodeGenerator for Type {
// We prefer using `pub use` over `pub type` because of:
// https://github.com/rust-lang/rust/issues/26264
- if inner_rust_type.to_string().chars().all(|c| match c {
- // These are the only characters allowed in simple
- // paths, eg `good::dogs::Bront`.
- 'A'..='Z' | 'a'..='z' | '0'..='9' | ':' | '_' | ' ' => true,
- _ => false,
- }) && outer_params.is_empty() &&
+ // These are the only characters allowed in simple
+ // paths, eg `good::dogs::Bront`.
+ if inner_rust_type.to_string().chars().all(|c| matches!(c, 'A'..='Z' | 'a'..='z' | '0'..='9' | ':' | '_' | ' ')) && outer_params.is_empty() &&
!is_opaque &&
alias_style == AliasVariation::TypeAlias &&
inner_item.expect_type().canonical_type(ctx).is_enum()
@@ -1767,7 +1772,7 @@ impl CodeGenerator for CompInfo {
let inner_item = ctx.resolve_item(base.ty);
let mut inner = inner_item.to_rust_ty_or_opaque(ctx, &());
- inner.append_implicit_template_params(ctx, &inner_item);
+ inner.append_implicit_template_params(ctx, inner_item);
let field_name = ctx.rust_ident(&base.field_name);
struct_layout.saw_base(inner_item.expect_type());
@@ -2023,6 +2028,11 @@ impl CodeGenerator for CompInfo {
attributes.push(attributes::derives(&derives))
}
+ if item.annotations().must_use_type() || ctx.must_use_type_by_name(item)
+ {
+ attributes.push(attributes::must_use());
+ }
+
let mut tokens = if is_union && struct_layout.is_rust_union() {
quote! {
#( #attributes )*
@@ -2121,11 +2131,11 @@ impl CodeGenerator for CompInfo {
})
.flat_map(|field| {
let name = field.name().unwrap();
- field.offset().and_then(|offset| {
+ field.offset().map(|offset| {
let field_offset = offset / 8;
let field_name = ctx.rust_ident(name);
- Some(quote! {
+ quote! {
assert_eq!(
unsafe {
&(*(::#prefix::ptr::null::<#canonical_ident>())).#field_name as *const _ as usize
@@ -2133,7 +2143,7 @@ impl CodeGenerator for CompInfo {
#field_offset,
concat!("Offset of field: ", stringify!(#canonical_ident), "::", stringify!(#field_name))
);
- })
+ }
})
})
.collect::<Vec<proc_macro2::TokenStream>>();
@@ -2343,7 +2353,7 @@ impl MethodCodegen for Method {
return;
}
let function = function_item.expect_function();
- let times_seen = function.codegen(ctx, result, &function_item);
+ let times_seen = function.codegen(ctx, result, function_item);
let times_seen = match times_seen {
Some(seen) => seen,
None => return,
@@ -2409,7 +2419,7 @@ impl MethodCodegen for Method {
}
let mut exprs =
- helpers::ast_ty::arguments_from_signature(&signature, ctx);
+ helpers::ast_ty::arguments_from_signature(signature, ctx);
let mut stmts = vec![];
@@ -2466,8 +2476,7 @@ impl MethodCodegen for Method {
#( #stmts );*
};
- let mut attrs = vec![];
- attrs.push(attributes::inline());
+ let mut attrs = vec![attributes::inline()];
if signature.must_use() &&
ctx.options().rust_features().must_use_function
@@ -2508,19 +2517,13 @@ pub enum EnumVariation {
impl EnumVariation {
fn is_rust(&self) -> bool {
- match *self {
- EnumVariation::Rust { .. } => true,
- _ => false,
- }
+ matches!(*self, EnumVariation::Rust { .. })
}
/// Both the `Const` and `ModuleConsts` variants will cause this to return
/// true.
fn is_const(&self) -> bool {
- match *self {
- EnumVariation::Consts | EnumVariation::ModuleConsts => true,
- _ => false,
- }
+ matches!(*self, EnumVariation::Consts | EnumVariation::ModuleConsts)
}
}
@@ -2598,10 +2601,7 @@ impl<'a> EnumBuilder<'a> {
/// Returns true if the builder is for a rustified enum.
fn is_rust_enum(&self) -> bool {
- match *self {
- EnumBuilder::Rust { .. } => true,
- _ => false,
- }
+ matches!(*self, EnumBuilder::Rust { .. })
}
/// Create a new enum given an item builder, a canonical name, a name for
@@ -2998,18 +2998,43 @@ impl CodeGenerator for Enum {
attrs.push(attributes::doc(comment));
}
+ if item.annotations().must_use_type() || ctx.must_use_type_by_name(item)
+ {
+ attrs.push(attributes::must_use());
+ }
+
if !variation.is_const() {
let mut derives = derives_of_item(item, ctx);
- // For backwards compat, enums always derive Clone/Eq/PartialEq/Hash, even
+ // For backwards compat, enums always derive Debug/Clone/Eq/PartialEq/Hash, even
// if we don't generate those by default.
+ if !item.annotations().disallow_debug() {
+ derives.insert(DerivableTraits::DEBUG);
+ }
+ if !item.annotations().disallow_copy() {
+ derives.insert(DerivableTraits::COPY);
+ }
derives.insert(
DerivableTraits::CLONE |
- DerivableTraits::COPY |
DerivableTraits::HASH |
DerivableTraits::PARTIAL_EQ |
DerivableTraits::EQ,
);
- let derives: Vec<_> = derives.into();
+ let mut derives: Vec<_> = derives.into();
+ for derive in item.annotations().derives().iter() {
+ if !derives.contains(&derive.as_str()) {
+ derives.push(derive);
+ }
+ }
+
+ // The custom derives callback may return a list of derive attributes;
+ // add them to the end of the list.
+ let custom_derives;
+ if let Some(cb) = &ctx.options().parse_callbacks {
+ custom_derives = cb.add_derives(&name);
+ // In most cases this will be a no-op, since custom_derives will be empty.
+ derives.extend(custom_derives.iter().map(|s| s.as_str()));
+ };
+
attrs.push(attributes::derives(&derives));
}
@@ -3067,7 +3092,7 @@ impl CodeGenerator for Enum {
let constant_mangling_prefix = if ctx.options().prepend_enum_name {
if enum_ty.name().is_none() {
- parent_canonical_name.as_ref().map(|n| &**n)
+ parent_canonical_name.as_deref()
} else {
Some(&*name)
}
@@ -3626,13 +3651,12 @@ impl TryToRustTy for Type {
let void = c_void(ctx);
return Ok(void.to_ptr(/* is_const = */ false));
}
- let template_params = item
- .used_template_params(ctx)
- .into_iter()
- .filter(|param| param.is_template_param(ctx, &()))
- .collect::<Vec<_>>();
- if item.is_opaque(ctx, &()) && !template_params.is_empty() {
+ if item.is_opaque(ctx, &()) &&
+ item.used_template_params(ctx)
+ .into_iter()
+ .any(|param| param.is_template_param(ctx, &()))
+ {
self.try_to_opaque(ctx, item)
} else if let Some(ty) = self
.name()
@@ -3661,10 +3685,8 @@ impl TryToRustTy for Type {
inner.into_resolver().through_type_refs().resolve(ctx);
let inner_ty = inner.expect_type();
- let is_objc_pointer = match inner_ty.kind() {
- TypeKind::ObjCInterface(..) => true,
- _ => false,
- };
+ let is_objc_pointer =
+ matches!(inner_ty.kind(), TypeKind::ObjCInterface(..));
// Regardless if we can properly represent the inner type, we
// should always generate a proper pointer here, so use
@@ -3797,8 +3819,8 @@ impl TryToRustTy for FunctionSig {
_: &(),
) -> error::Result<proc_macro2::TokenStream> {
// TODO: we might want to consider ignoring the reference return value.
- let ret = utils::fnsig_return_ty(ctx, &self);
- let arguments = utils::fnsig_arguments(ctx, &self);
+ let ret = utils::fnsig_return_ty(ctx, self);
+ let arguments = utils::fnsig_arguments(ctx, self);
let abi = self.abi();
match abi {
@@ -4040,12 +4062,12 @@ impl CodeGenerator for ObjCInterface {
impl_items.push(impl_item);
}
- let instance_method_names: Vec<_> =
- self.methods().iter().map(|m| m.rust_name()).collect();
-
for class_method in self.class_methods() {
- let ambiquity =
- instance_method_names.contains(&class_method.rust_name());
+ let ambiquity = self
+ .methods()
+ .iter()
+ .map(|m| m.rust_name())
+ .any(|x| x == class_method.rust_name());
let prefix = if ambiquity { "class_" } else { "" };
let impl_item = objc_method_codegen(
ctx,
@@ -4637,7 +4659,7 @@ pub mod utils {
TypeKind::Array(t, _) => {
let stream =
if ctx.options().array_pointers_in_arguments {
- arg_ty.to_rust_ty_or_opaque(ctx, &arg_item)
+ arg_ty.to_rust_ty_or_opaque(ctx, arg_item)
} else {
t.to_rust_ty_or_opaque(ctx, &())
};
diff --git a/src/codegen/struct_layout.rs b/src/codegen/struct_layout.rs
index 1c6b977..657be0b 100644
--- a/src/codegen/struct_layout.rs
+++ b/src/codegen/struct_layout.rs
@@ -279,6 +279,11 @@ impl<'a> StructLayoutTracker<'a> {
return None;
}
+ // Padding doesn't make sense for rust unions.
+ if self.is_rust_union {
+ return None;
+ }
+
if self.latest_offset == comp_layout.size {
// This struct does not contain tail padding.
return None;
@@ -428,6 +433,6 @@ impl<'a> StructLayoutTracker<'a> {
// Else, just align the obvious way.
self.latest_offset += self.padding_bytes(layout);
- return false;
+ false
}
}
diff --git a/src/features.rs b/src/features.rs
index 99b789e..a786f07 100644
--- a/src/features.rs
+++ b/src/features.rs
@@ -87,8 +87,9 @@ macro_rules! rust_target_base {
$x_macro!(
/// Rust stable 1.0
=> Stable_1_0 => 1.0;
- /// Rust stable 1.1
- => Stable_1_1 => 1.1;
+ /// Rust stable 1.17
+ /// * Static lifetime elision ([RFC 1623](https://github.com/rust-lang/rfcs/blob/master/text/1623-static.md))
+ => Stable_1_17 => 1.17;
/// Rust stable 1.19
/// * Untagged unions ([RFC 1444](https://github.com/rust-lang/rfcs/blob/master/text/1444-union.md))
=> Stable_1_19 => 1.19;
@@ -191,6 +192,9 @@ macro_rules! rust_feature_def {
// documentation for the relevant variant in the rust_target_base macro
// definition.
rust_feature_def!(
+ Stable_1_17 {
+ => static_lifetime_elision;
+ }
Stable_1_19 {
=> untagged_union;
}
@@ -249,7 +253,8 @@ mod test {
fn target_features() {
let f_1_0 = RustFeatures::from(RustTarget::Stable_1_0);
assert!(
- !f_1_0.core_ffi_c_void &&
+ !f_1_0.static_lifetime_elision &&
+ !f_1_0.core_ffi_c_void &&
!f_1_0.untagged_union &&
!f_1_0.associated_const &&
!f_1_0.builtin_clone_impls &&
@@ -258,7 +263,8 @@ mod test {
);
let f_1_21 = RustFeatures::from(RustTarget::Stable_1_21);
assert!(
- !f_1_21.core_ffi_c_void &&
+ f_1_21.static_lifetime_elision &&
+ !f_1_21.core_ffi_c_void &&
f_1_21.untagged_union &&
f_1_21.associated_const &&
f_1_21.builtin_clone_impls &&
@@ -267,7 +273,8 @@ mod test {
);
let f_nightly = RustFeatures::from(RustTarget::Nightly);
assert!(
- f_nightly.core_ffi_c_void &&
+ f_nightly.static_lifetime_elision &&
+ f_nightly.core_ffi_c_void &&
f_nightly.untagged_union &&
f_nightly.associated_const &&
f_nightly.builtin_clone_impls &&
@@ -286,6 +293,7 @@ mod test {
#[test]
fn str_to_target() {
test_target("1.0", RustTarget::Stable_1_0);
+ test_target("1.17", RustTarget::Stable_1_17);
test_target("1.19", RustTarget::Stable_1_19);
test_target("1.21", RustTarget::Stable_1_21);
test_target("1.25", RustTarget::Stable_1_25);
diff --git a/src/ir/analysis/derive.rs b/src/ir/analysis/derive.rs
index 44e6702..f63458e 100644
--- a/src/ir/analysis/derive.rs
+++ b/src/ir/analysis/derive.rs
@@ -9,6 +9,7 @@ use crate::ir::context::{BindgenContext, ItemId};
use crate::ir::derive::CanDerive;
use crate::ir::function::FunctionSig;
use crate::ir::item::{IsOpaque, Item};
+use crate::ir::layout::Layout;
use crate::ir::template::TemplateParameters;
use crate::ir::traversal::{EdgeKind, Trace};
use crate::ir::ty::RUST_DERIVE_IN_ARRAY_LIMIT;
@@ -159,7 +160,7 @@ impl<'ctx> CannotDerive<'ctx> {
return can_derive;
}
- if self.derive_trait.not_by_name(self.ctx, &item) {
+ if self.derive_trait.not_by_name(self.ctx, item) {
trace!(
" cannot derive {} for explicitly excluded type",
self.derive_trait
@@ -223,13 +224,13 @@ impl<'ctx> CannotDerive<'ctx> {
let inner_type =
self.ctx.resolve_type(inner).canonical_type(self.ctx);
if let TypeKind::Function(ref sig) = *inner_type.kind() {
- return self.derive_trait.can_derive_fnptr(sig);
+ self.derive_trait.can_derive_fnptr(sig)
} else {
- return self.derive_trait.can_derive_pointer();
+ self.derive_trait.can_derive_pointer()
}
}
TypeKind::Function(ref sig) => {
- return self.derive_trait.can_derive_fnptr(sig)
+ self.derive_trait.can_derive_fnptr(sig)
}
// Complex cases need more information
@@ -255,7 +256,7 @@ impl<'ctx> CannotDerive<'ctx> {
return CanDerive::No;
}
- if self.derive_trait.can_derive_large_array(&self.ctx) {
+ if self.derive_trait.can_derive_large_array(self.ctx) {
trace!(" array can derive {}", self.derive_trait);
return CanDerive::Yes;
}
@@ -270,7 +271,7 @@ impl<'ctx> CannotDerive<'ctx> {
" array is small enough to derive {}",
self.derive_trait
);
- return CanDerive::Yes;
+ CanDerive::Yes
}
TypeKind::Vector(t, len) => {
let inner_type =
@@ -285,7 +286,7 @@ impl<'ctx> CannotDerive<'ctx> {
return CanDerive::No;
}
assert_ne!(len, 0, "vectors cannot have zero length");
- return self.derive_trait.can_derive_vector();
+ self.derive_trait.can_derive_vector()
}
TypeKind::Comp(ref info) => {
@@ -377,7 +378,7 @@ impl<'ctx> CannotDerive<'ctx> {
// Bitfield units are always represented as arrays of u8, but
// they're not traced as arrays, so we need to check here
// instead.
- if !self.derive_trait.can_derive_large_array(&self.ctx) &&
+ if !self.derive_trait.can_derive_large_array(self.ctx) &&
info.has_too_large_bitfield_unit() &&
!item.is_opaque(self.ctx, &())
{
@@ -389,7 +390,7 @@ impl<'ctx> CannotDerive<'ctx> {
}
let pred = self.derive_trait.consider_edge_comp();
- return self.constrain_join(item, pred);
+ self.constrain_join(item, pred)
}
TypeKind::ResolvedTypeRef(..) |
@@ -397,12 +398,12 @@ impl<'ctx> CannotDerive<'ctx> {
TypeKind::Alias(..) |
TypeKind::BlockPointer(..) => {
let pred = self.derive_trait.consider_edge_typeref();
- return self.constrain_join(item, pred);
+ self.constrain_join(item, pred)
}
TypeKind::TemplateInstantiation(..) => {
let pred = self.derive_trait.consider_edge_tmpl_inst();
- return self.constrain_join(item, pred);
+ self.constrain_join(item, pred)
}
TypeKind::Opaque => unreachable!(
@@ -470,10 +471,7 @@ impl DeriveTrait {
fn consider_edge_comp(&self) -> EdgePredicate {
match self {
DeriveTrait::PartialEqOrPartialOrd => consider_edge_default,
- _ => |kind| match kind {
- EdgeKind::BaseMember | EdgeKind::Field => true,
- _ => false,
- },
+ _ => |kind| matches!(kind, EdgeKind::BaseMember | EdgeKind::Field),
}
}
@@ -498,53 +496,35 @@ impl DeriveTrait {
fn can_derive_large_array(&self, ctx: &BindgenContext) -> bool {
if ctx.options().rust_features().larger_arrays {
- match self {
- DeriveTrait::Default => false,
- _ => true,
- }
+ !matches!(self, DeriveTrait::Default)
} else {
- match self {
- DeriveTrait::Copy => true,
- _ => false,
- }
+ matches!(self, DeriveTrait::Copy)
}
}
fn can_derive_union(&self) -> bool {
- match self {
- DeriveTrait::Copy => true,
- _ => false,
- }
+ matches!(self, DeriveTrait::Copy)
}
fn can_derive_compound_with_destructor(&self) -> bool {
- match self {
- DeriveTrait::Copy => false,
- _ => true,
- }
+ !matches!(self, DeriveTrait::Copy)
}
fn can_derive_compound_with_vtable(&self) -> bool {
- match self {
- DeriveTrait::Default => false,
- _ => true,
- }
+ !matches!(self, DeriveTrait::Default)
}
fn can_derive_compound_forward_decl(&self) -> bool {
- match self {
- DeriveTrait::Copy | DeriveTrait::Debug => true,
- _ => false,
- }
+ matches!(self, DeriveTrait::Copy | DeriveTrait::Debug)
}
fn can_derive_incomplete_array(&self) -> bool {
- match self {
+ !matches!(
+ self,
DeriveTrait::Copy |
- DeriveTrait::Hash |
- DeriveTrait::PartialEqOrPartialOrd => false,
- _ => true,
- }
+ DeriveTrait::Hash |
+ DeriveTrait::PartialEqOrPartialOrd
+ )
}
fn can_derive_fnptr(&self, f: &FunctionSig) -> CanDerive {
@@ -693,10 +673,10 @@ impl<'ctx> MonotoneFramework for CannotDerive<'ctx> {
Some(ty) => {
let mut can_derive = self.constrain_type(item, ty);
if let CanDerive::Yes = can_derive {
- if !self.derive_trait.can_derive_large_array(&self.ctx) &&
- ty.layout(self.ctx).map_or(false, |l| {
- l.align > RUST_DERIVE_IN_ARRAY_LIMIT
- })
+ let is_reached_limit =
+ |l: Layout| l.align > RUST_DERIVE_IN_ARRAY_LIMIT;
+ if !self.derive_trait.can_derive_large_array(self.ctx) &&
+ ty.layout(self.ctx).map_or(false, is_reached_limit)
{
// We have to be conservative: the struct *could* have enough
// padding that we emit an array that is longer than
diff --git a/src/ir/analysis/has_destructor.rs b/src/ir/analysis/has_destructor.rs
index 5fa22e3..74fd73d 100644
--- a/src/ir/analysis/has_destructor.rs
+++ b/src/ir/analysis/has_destructor.rs
@@ -41,16 +41,16 @@ pub struct HasDestructorAnalysis<'ctx> {
impl<'ctx> HasDestructorAnalysis<'ctx> {
fn consider_edge(kind: EdgeKind) -> bool {
- match kind {
- // These are the only edges that can affect whether a type has a
- // destructor or not.
+ // These are the only edges that can affect whether a type has a
+ // destructor or not.
+ matches!(
+ kind,
EdgeKind::TypeReference |
- EdgeKind::BaseMember |
- EdgeKind::Field |
- EdgeKind::TemplateArgument |
- EdgeKind::TemplateDeclaration => true,
- _ => false,
- }
+ EdgeKind::BaseMember |
+ EdgeKind::Field |
+ EdgeKind::TemplateArgument |
+ EdgeKind::TemplateDeclaration
+ )
}
fn insert<Id: Into<ItemId>>(&mut self, id: Id) -> ConstrainResult {
diff --git a/src/ir/analysis/has_vtable.rs b/src/ir/analysis/has_vtable.rs
index 7f5f911..8ac47a6 100644
--- a/src/ir/analysis/has_vtable.rs
+++ b/src/ir/analysis/has_vtable.rs
@@ -79,14 +79,14 @@ pub struct HasVtableAnalysis<'ctx> {
impl<'ctx> HasVtableAnalysis<'ctx> {
fn consider_edge(kind: EdgeKind) -> bool {
- match kind {
- // These are the only edges that can affect whether a type has a
- // vtable or not.
+ // These are the only edges that can affect whether a type has a
+ // vtable or not.
+ matches!(
+ kind,
EdgeKind::TypeReference |
- EdgeKind::BaseMember |
- EdgeKind::TemplateDeclaration => true,
- _ => false,
- }
+ EdgeKind::BaseMember |
+ EdgeKind::TemplateDeclaration
+ )
}
fn insert<Id: Into<ItemId>>(
diff --git a/src/ir/analysis/mod.rs b/src/ir/analysis/mod.rs
index ec4d20f..eb9a1c0 100644
--- a/src/ir/analysis/mod.rs
+++ b/src/ir/analysis/mod.rs
@@ -184,7 +184,7 @@ where
let mut dependencies = HashMap::default();
for &item in ctx.allowlisted_items() {
- dependencies.entry(item).or_insert(vec![]);
+ dependencies.entry(item).or_insert_with(Vec::new);
{
// We reverse our natural IR graph edges to find dependencies
@@ -197,7 +197,7 @@ where
{
dependencies
.entry(sub_item)
- .or_insert(vec![])
+ .or_insert_with(Vec::new)
.push(item);
}
},
diff --git a/src/ir/analysis/sizedness.rs b/src/ir/analysis/sizedness.rs
index a3ef753..251c374 100644
--- a/src/ir/analysis/sizedness.rs
+++ b/src/ir/analysis/sizedness.rs
@@ -112,17 +112,17 @@ pub struct SizednessAnalysis<'ctx> {
impl<'ctx> SizednessAnalysis<'ctx> {
fn consider_edge(kind: EdgeKind) -> bool {
- match kind {
- // These are the only edges that can affect whether a type is
- // zero-sized or not.
+ // These are the only edges that can affect whether a type is
+ // zero-sized or not.
+ matches!(
+ kind,
EdgeKind::TemplateArgument |
- EdgeKind::TemplateParameterDefinition |
- EdgeKind::TemplateDeclaration |
- EdgeKind::TypeReference |
- EdgeKind::BaseMember |
- EdgeKind::Field => true,
- _ => false,
- }
+ EdgeKind::TemplateParameterDefinition |
+ EdgeKind::TemplateDeclaration |
+ EdgeKind::TypeReference |
+ EdgeKind::BaseMember |
+ EdgeKind::Field
+ )
}
/// Insert an incremental result, and return whether this updated our
diff --git a/src/ir/analysis/template_params.rs b/src/ir/analysis/template_params.rs
index c2f18b1..e88b774 100644
--- a/src/ir/analysis/template_params.rs
+++ b/src/ir/analysis/template_params.rs
@@ -239,7 +239,7 @@ impl<'ctx> UsedTemplateParameters<'ctx> {
let args = instantiation
.template_arguments()
- .into_iter()
+ .iter()
.map(|a| {
a.into_resolver()
.through_type_refs()
@@ -399,8 +399,8 @@ impl<'ctx> MonotoneFramework for UsedTemplateParameters<'ctx> {
.collect();
for item in allowlisted_and_blocklisted_items {
- dependencies.entry(item).or_insert(vec![]);
- used.entry(item).or_insert(Some(ItemSet::new()));
+ dependencies.entry(item).or_insert_with(Vec::new);
+ used.entry(item).or_insert_with(|| Some(ItemSet::new()));
{
// We reverse our natural IR graph edges to find dependencies
@@ -408,10 +408,11 @@ impl<'ctx> MonotoneFramework for UsedTemplateParameters<'ctx> {
item.trace(
ctx,
&mut |sub_item: ItemId, _| {
- used.entry(sub_item).or_insert(Some(ItemSet::new()));
+ used.entry(sub_item)
+ .or_insert_with(|| Some(ItemSet::new()));
dependencies
.entry(sub_item)
- .or_insert(vec![])
+ .or_insert_with(Vec::new)
.push(item);
},
&(),
@@ -421,39 +422,42 @@ impl<'ctx> MonotoneFramework for UsedTemplateParameters<'ctx> {
// Additionally, whether a template instantiation's template
// arguments are used depends on whether the template declaration's
// generic template parameters are used.
- ctx.resolve_item(item).as_type().map(|ty| match ty.kind() {
- &TypeKind::TemplateInstantiation(ref inst) => {
- let decl = ctx.resolve_type(inst.template_definition());
- let args = inst.template_arguments();
-
- // Although template definitions should always have
- // template parameters, there is a single exception:
- // opaque templates. Hence the unwrap_or.
- let params = decl.self_template_params(ctx);
-
- for (arg, param) in args.iter().zip(params.iter()) {
- let arg = arg
- .into_resolver()
- .through_type_aliases()
- .through_type_refs()
- .resolve(ctx)
- .id();
-
- let param = param
- .into_resolver()
- .through_type_aliases()
- .through_type_refs()
- .resolve(ctx)
- .id();
-
- used.entry(arg).or_insert(Some(ItemSet::new()));
- used.entry(param).or_insert(Some(ItemSet::new()));
-
- dependencies.entry(arg).or_insert(vec![]).push(param);
- }
+ let item_kind =
+ ctx.resolve_item(item).as_type().map(|ty| ty.kind());
+ if let Some(&TypeKind::TemplateInstantiation(ref inst)) = item_kind
+ {
+ let decl = ctx.resolve_type(inst.template_definition());
+ let args = inst.template_arguments();
+
+ // Although template definitions should always have
+ // template parameters, there is a single exception:
+ // opaque templates. Hence the unwrap_or.
+ let params = decl.self_template_params(ctx);
+
+ for (arg, param) in args.iter().zip(params.iter()) {
+ let arg = arg
+ .into_resolver()
+ .through_type_aliases()
+ .through_type_refs()
+ .resolve(ctx)
+ .id();
+
+ let param = param
+ .into_resolver()
+ .through_type_aliases()
+ .through_type_refs()
+ .resolve(ctx)
+ .id();
+
+ used.entry(arg).or_insert_with(|| Some(ItemSet::new()));
+ used.entry(param).or_insert_with(|| Some(ItemSet::new()));
+
+ dependencies
+ .entry(arg)
+ .or_insert_with(Vec::new)
+ .push(param);
}
- _ => {}
- });
+ }
}
if cfg!(feature = "testing_only_extra_assertions") {
@@ -482,10 +486,10 @@ impl<'ctx> MonotoneFramework for UsedTemplateParameters<'ctx> {
}
UsedTemplateParameters {
- ctx: ctx,
- used: used,
- dependencies: dependencies,
- allowlisted_items: allowlisted_items,
+ ctx,
+ used,
+ dependencies,
+ allowlisted_items,
}
}
diff --git a/src/ir/annotations.rs b/src/ir/annotations.rs
index 12664f6..9bcda50 100644
--- a/src/ir/annotations.rs
+++ b/src/ir/annotations.rs
@@ -25,7 +25,7 @@ pub enum FieldAccessorKind {
/// documentation:
///
/// http://www.stack.nl/~dimitri/doxygen/manual/docblocks.html
-#[derive(Clone, PartialEq, Debug)]
+#[derive(Default, Clone, PartialEq, Debug)]
pub struct Annotations {
/// Whether this item is marked as opaque. Only applies to types.
opaque: bool,
@@ -42,6 +42,8 @@ pub struct Annotations {
disallow_debug: bool,
/// Manually disable deriving/implement default on this type.
disallow_default: bool,
+ /// Whether to add a #[must_use] annotation to this type.
+ must_use_type: bool,
/// Whether fields should be marked as private or not. You can set this on
/// structs (it will apply to all the fields), or individual fields.
private_fields: Option<bool>,
@@ -75,23 +77,6 @@ fn parse_accessor(s: &str) -> FieldAccessorKind {
}
}
-impl Default for Annotations {
- fn default() -> Self {
- Annotations {
- opaque: false,
- hide: false,
- use_instead_of: None,
- disallow_copy: false,
- disallow_debug: false,
- disallow_default: false,
- private_fields: None,
- accessor_kind: None,
- constify_enum_variant: false,
- derives: vec![],
- }
- }
-}
-
impl Annotations {
/// Construct new annotations for the given cursor and its bindgen comments
/// (if any).
@@ -140,7 +125,7 @@ impl Annotations {
///
/// That is, code for `Foo` is used to generate `Bar`.
pub fn use_instead_of(&self) -> Option<&[String]> {
- self.use_instead_of.as_ref().map(|s| &**s)
+ self.use_instead_of.as_deref()
}
/// The list of derives that have been specified in this annotation.
@@ -163,6 +148,11 @@ impl Annotations {
self.disallow_default
}
+ /// Should this type get a `#[must_use]` annotation?
+ pub fn must_use_type(&self) -> bool {
+ self.must_use_type
+ }
+
/// Should the fields be private?
pub fn private_fields(&self) -> Option<bool> {
self.private_fields
@@ -190,6 +180,7 @@ impl Annotations {
"nocopy" => self.disallow_copy = true,
"nodebug" => self.disallow_debug = true,
"nodefault" => self.disallow_default = true,
+ "mustusetype" => self.must_use_type = true,
"replaces" => {
self.use_instead_of = Some(
attr.value.split("::").map(Into::into).collect(),
diff --git a/src/ir/comment.rs b/src/ir/comment.rs
index 4ebe19a..c96e3eb 100644
--- a/src/ir/comment.rs
+++ b/src/ir/comment.rs
@@ -1,7 +1,5 @@
//! Utilities for manipulating C/C++ comments.
-use std::iter;
-
/// The type of a comment.
#[derive(Debug, PartialEq, Eq)]
enum Kind {
@@ -15,7 +13,7 @@ enum Kind {
/// Preprocesses a C/C++ comment so that it is a valid Rust comment.
pub fn preprocess(comment: &str, indent: usize) -> String {
- match self::kind(&comment) {
+ match self::kind(comment) {
Some(Kind::SingleLines) => preprocess_single_lines(comment, indent),
Some(Kind::MultiLine) => preprocess_multi_line(comment, indent),
None => comment.to_owned(),
@@ -35,7 +33,7 @@ fn kind(comment: &str) -> Option<Kind> {
fn make_indent(indent: usize) -> String {
const RUST_INDENTATION: usize = 4;
- iter::repeat(' ').take(indent * RUST_INDENTATION).collect()
+ " ".repeat(indent * RUST_INDENTATION)
}
/// Preprocesses multiple single line comments.
diff --git a/src/ir/comp.rs b/src/ir/comp.rs
index e554f9a..a221e52 100644
--- a/src/ir/comp.rs
+++ b/src/ir/comp.rs
@@ -111,11 +111,10 @@ impl Method {
/// Is this a virtual method?
pub fn is_virtual(&self) -> bool {
- match self.kind {
- MethodKind::Virtual { .. } |
- MethodKind::VirtualDestructor { .. } => true,
- _ => false,
- }
+ matches!(
+ self.kind,
+ MethodKind::Virtual { .. } | MethodKind::VirtualDestructor { .. }
+ )
}
/// Is this a static method?
@@ -630,7 +629,7 @@ where
bitfield_unit_count,
unit_size_in_bits,
unit_align,
- mem::replace(&mut bitfields_in_unit, vec![]),
+ mem::take(&mut bitfields_in_unit),
packed,
);
@@ -639,15 +638,12 @@ where
offset = 0;
unit_align = 0;
}
- } else {
- if offset != 0 &&
- (bitfield_width == 0 ||
- (offset & (bitfield_align * 8 - 1)) +
- bitfield_width >
- bitfield_size * 8)
- {
- offset = align_to(offset, bitfield_align * 8);
- }
+ } else if offset != 0 &&
+ (bitfield_width == 0 ||
+ (offset & (bitfield_align * 8 - 1)) + bitfield_width >
+ bitfield_size * 8)
+ {
+ offset = align_to(offset, bitfield_align * 8);
}
}
@@ -706,24 +702,24 @@ where
/// after.
#[derive(Debug)]
enum CompFields {
- BeforeComputingBitfieldUnits(Vec<RawField>),
- AfterComputingBitfieldUnits {
+ Before(Vec<RawField>),
+ After {
fields: Vec<Field>,
has_bitfield_units: bool,
},
- ErrorComputingBitfieldUnits,
+ Error,
}
impl Default for CompFields {
fn default() -> CompFields {
- CompFields::BeforeComputingBitfieldUnits(vec![])
+ CompFields::Before(vec![])
}
}
impl CompFields {
fn append_raw_field(&mut self, raw: RawField) {
match *self {
- CompFields::BeforeComputingBitfieldUnits(ref mut raws) => {
+ CompFields::Before(ref mut raws) => {
raws.push(raw);
}
_ => {
@@ -736,9 +732,7 @@ impl CompFields {
fn compute_bitfield_units(&mut self, ctx: &BindgenContext, packed: bool) {
let raws = match *self {
- CompFields::BeforeComputingBitfieldUnits(ref mut raws) => {
- mem::replace(raws, vec![])
- }
+ CompFields::Before(ref mut raws) => mem::take(raws),
_ => {
panic!("Already computed bitfield units");
}
@@ -748,25 +742,23 @@ impl CompFields {
match result {
Ok((fields, has_bitfield_units)) => {
- *self = CompFields::AfterComputingBitfieldUnits {
+ *self = CompFields::After {
fields,
has_bitfield_units,
};
}
Err(()) => {
- *self = CompFields::ErrorComputingBitfieldUnits;
+ *self = CompFields::Error;
}
}
}
fn deanonymize_fields(&mut self, ctx: &BindgenContext, methods: &[Method]) {
let fields = match *self {
- CompFields::AfterComputingBitfieldUnits {
- ref mut fields, ..
- } => fields,
+ CompFields::After { ref mut fields, .. } => fields,
// Nothing to do here.
- CompFields::ErrorComputingBitfieldUnits => return,
- CompFields::BeforeComputingBitfieldUnits(_) => {
+ CompFields::Error => return,
+ CompFields::Before(_) => {
panic!("Not yet computed bitfield units.");
}
};
@@ -778,7 +770,7 @@ impl CompFields {
) -> bool {
methods.iter().any(|method| {
let method_name = ctx.resolve_func(method.signature()).name();
- method_name == name || ctx.rust_mangle(&method_name) == name
+ method_name == name || ctx.rust_mangle(method_name) == name
})
}
@@ -820,7 +812,7 @@ impl CompFields {
for field in fields.iter_mut() {
match *field {
Field::DataMember(FieldData { ref mut name, .. }) => {
- if let Some(_) = *name {
+ if name.is_some() {
continue;
}
@@ -858,13 +850,13 @@ impl Trace for CompFields {
T: Tracer,
{
match *self {
- CompFields::ErrorComputingBitfieldUnits => {}
- CompFields::BeforeComputingBitfieldUnits(ref fields) => {
+ CompFields::Error => {}
+ CompFields::Before(ref fields) => {
for f in fields {
tracer.visit_kind(f.ty().into(), EdgeKind::Field);
}
}
- CompFields::AfterComputingBitfieldUnits { ref fields, .. } => {
+ CompFields::After { ref fields, .. } => {
for f in fields {
f.trace(context, tracer, &());
}
@@ -900,7 +892,7 @@ pub struct FieldData {
impl FieldMethods for FieldData {
fn name(&self) -> Option<&str> {
- self.name.as_ref().map(|n| &**n)
+ self.name.as_deref()
}
fn ty(&self) -> TypeId {
@@ -908,7 +900,7 @@ impl FieldMethods for FieldData {
}
fn comment(&self) -> Option<&str> {
- self.comment.as_ref().map(|c| &**c)
+ self.comment.as_deref()
}
fn bitfield_width(&self) -> Option<u32> {
@@ -1131,11 +1123,9 @@ impl CompInfo {
/// Get this type's set of fields.
pub fn fields(&self) -> &[Field] {
match self.fields {
- CompFields::ErrorComputingBitfieldUnits => &[],
- CompFields::AfterComputingBitfieldUnits { ref fields, .. } => {
- fields
- }
- CompFields::BeforeComputingBitfieldUnits(..) => {
+ CompFields::Error => &[],
+ CompFields::After { ref fields, .. } => fields,
+ CompFields::Before(..) => {
panic!("Should always have computed bitfield units first");
}
}
@@ -1143,13 +1133,9 @@ impl CompInfo {
fn has_fields(&self) -> bool {
match self.fields {
- CompFields::ErrorComputingBitfieldUnits => false,
- CompFields::AfterComputingBitfieldUnits { ref fields, .. } => {
- !fields.is_empty()
- }
- CompFields::BeforeComputingBitfieldUnits(ref raw_fields) => {
- !raw_fields.is_empty()
- }
+ CompFields::Error => false,
+ CompFields::After { ref fields, .. } => !fields.is_empty(),
+ CompFields::Before(ref raw_fields) => !raw_fields.is_empty(),
}
}
@@ -1159,15 +1145,15 @@ impl CompInfo {
mut callback: impl FnMut(Layout),
) {
match self.fields {
- CompFields::ErrorComputingBitfieldUnits => return,
- CompFields::AfterComputingBitfieldUnits { ref fields, .. } => {
+ CompFields::Error => {}
+ CompFields::After { ref fields, .. } => {
for field in fields.iter() {
if let Some(layout) = field.layout(ctx) {
callback(layout);
}
}
}
- CompFields::BeforeComputingBitfieldUnits(ref raw_fields) => {
+ CompFields::Before(ref raw_fields) => {
for field in raw_fields.iter() {
let field_ty = ctx.resolve_type(field.0.ty);
if let Some(layout) = field_ty.layout(ctx) {
@@ -1180,12 +1166,11 @@ impl CompInfo {
fn has_bitfields(&self) -> bool {
match self.fields {
- CompFields::ErrorComputingBitfieldUnits => false,
- CompFields::AfterComputingBitfieldUnits {
- has_bitfield_units,
- ..
+ CompFields::Error => false,
+ CompFields::After {
+ has_bitfield_units, ..
} => has_bitfield_units,
- CompFields::BeforeComputingBitfieldUnits(_) => {
+ CompFields::Before(_) => {
panic!("Should always have computed bitfield units first");
}
}
@@ -1408,21 +1393,26 @@ impl CompInfo {
let inner = Item::parse(cur, Some(potential_id), ctx)
.expect("Inner ClassDecl");
- let inner = inner.expect_type_id(ctx);
+ // If we avoided recursion parsing this type (in
+ // `Item::from_ty_with_id()`), then this might not be a
+ // valid type ID, so check and gracefully handle this.
+ if ctx.resolve_item_fallible(inner).is_some() {
+ let inner = inner.expect_type_id(ctx);
- ci.inner_types.push(inner);
+ ci.inner_types.push(inner);
- // A declaration of an union or a struct without name could
- // also be an unnamed field, unfortunately.
- if cur.spelling().is_empty() &&
- cur.kind() != CXCursor_EnumDecl
- {
- let ty = cur.cur_type();
- let public = cur.public_accessible();
- let offset = cur.offset_of_field().ok();
+ // A declaration of an union or a struct without name
+ // could also be an unnamed field, unfortunately.
+ if cur.spelling().is_empty() &&
+ cur.kind() != CXCursor_EnumDecl
+ {
+ let ty = cur.cur_type();
+ let public = cur.public_accessible();
+ let offset = cur.offset_of_field().ok();
- maybe_anonymous_struct_field =
- Some((inner, ty, public, offset));
+ maybe_anonymous_struct_field =
+ Some((inner, ty, public, offset));
+ }
}
}
CXCursor_PackedAttr => {
@@ -1771,7 +1761,7 @@ impl IsOpaque for CompInfo {
// is a type parameter), then we can't compute bitfield units. We are
// left with no choice but to make the whole struct opaque, or else we
// might generate structs with incorrect sizes and alignments.
- if let CompFields::ErrorComputingBitfieldUnits = self.fields {
+ if let CompFields::Error = self.fields {
return true;
}
diff --git a/src/ir/context.rs b/src/ir/context.rs
index 72ce06b..a9e19fb 100644
--- a/src/ir/context.rs
+++ b/src/ir/context.rs
@@ -299,7 +299,7 @@ where
/// types.
#[derive(Eq, PartialEq, Hash, Debug)]
enum TypeKey {
- USR(String),
+ Usr(String),
Declaration(Cursor),
}
@@ -640,7 +640,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
/// Get the user-provided callbacks by reference, if any.
pub fn parse_callbacks(&self) -> Option<&dyn ParseCallbacks> {
- self.options().parse_callbacks.as_ref().map(|t| &**t)
+ self.options().parse_callbacks.as_deref()
}
/// Add another path to the set of included files.
@@ -702,8 +702,10 @@ If you encounter an error missing from this list, please file an issue or a PR!"
// Unnamed items can have an USR, but they can't be referenced from
// other sites explicitly and the USR can match if the unnamed items are
// nested, so don't bother tracking them.
- if is_type && !is_template_instantiation && declaration.is_some() {
- let mut declaration = declaration.unwrap();
+ if !is_type || is_template_instantiation {
+ return;
+ }
+ if let Some(mut declaration) = declaration {
if !declaration.is_valid() {
if let Some(location) = location {
if location.is_template_like() {
@@ -732,7 +734,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
let key = if is_unnamed {
TypeKey::Declaration(declaration)
} else if let Some(usr) = declaration.usr() {
- TypeKey::USR(usr)
+ TypeKey::Usr(usr)
} else {
warn!(
"Valid declaration with no USR: {:?}, {:?}",
@@ -829,31 +831,32 @@ If you encounter an error missing from this list, please file an issue or a PR!"
// TODO: Move all this syntax crap to other part of the code.
/// Mangles a name so it doesn't conflict with any keyword.
+ #[rustfmt::skip]
pub fn rust_mangle<'a>(&self, name: &'a str) -> Cow<'a, str> {
- if name.contains("@") ||
- name.contains("?") ||
- name.contains("$") ||
- match name {
+ if name.contains('@') ||
+ name.contains('?') ||
+ name.contains('$') ||
+ matches!(
+ name,
"abstract" | "alignof" | "as" | "async" | "become" |
- "box" | "break" | "const" | "continue" | "crate" | "do" |
- "dyn" | "else" | "enum" | "extern" | "false" | "final" |
- "fn" | "for" | "if" | "impl" | "in" | "let" | "loop" |
- "macro" | "match" | "mod" | "move" | "mut" | "offsetof" |
- "override" | "priv" | "proc" | "pub" | "pure" | "ref" |
- "return" | "Self" | "self" | "sizeof" | "static" |
- "struct" | "super" | "trait" | "true" | "type" | "typeof" |
- "unsafe" | "unsized" | "use" | "virtual" | "where" |
- "while" | "yield" | "str" | "bool" | "f32" | "f64" |
- "usize" | "isize" | "u128" | "i128" | "u64" | "i64" |
- "u32" | "i32" | "u16" | "i16" | "u8" | "i8" | "_" => true,
- _ => false,
- }
+ "box" | "break" | "const" | "continue" | "crate" | "do" |
+ "dyn" | "else" | "enum" | "extern" | "false" | "final" |
+ "fn" | "for" | "if" | "impl" | "in" | "let" | "loop" |
+ "macro" | "match" | "mod" | "move" | "mut" | "offsetof" |
+ "override" | "priv" | "proc" | "pub" | "pure" | "ref" |
+ "return" | "Self" | "self" | "sizeof" | "static" |
+ "struct" | "super" | "trait" | "true" | "try" | "type" | "typeof" |
+ "unsafe" | "unsized" | "use" | "virtual" | "where" |
+ "while" | "yield" | "str" | "bool" | "f32" | "f64" |
+ "usize" | "isize" | "u128" | "i128" | "u64" | "i64" |
+ "u32" | "i32" | "u16" | "i16" | "u8" | "i8" | "_"
+ )
{
let mut s = name.to_owned();
s = s.replace("@", "_");
s = s.replace("?", "_");
s = s.replace("$", "_");
- s.push_str("_");
+ s.push('_');
return Cow::Owned(s);
}
Cow::Borrowed(name)
@@ -903,11 +906,10 @@ If you encounter an error missing from this list, please file an issue or a PR!"
None => continue,
};
- match *ty.kind() {
- TypeKind::UnresolvedTypeRef(ref ty, loc, parent_id) => {
- typerefs.push((id, ty.clone(), loc, parent_id));
- }
- _ => {}
+ if let TypeKind::UnresolvedTypeRef(ref ty, loc, parent_id) =
+ *ty.kind()
+ {
+ typerefs.push((id, *ty, loc, parent_id));
};
}
typerefs
@@ -978,7 +980,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
assert!(self.collected_typerefs());
let need_bitfield_allocation =
- mem::replace(&mut self.need_bitfield_allocation, vec![]);
+ mem::take(&mut self.need_bitfield_allocation);
for id in need_bitfield_allocation {
self.with_loaned_item(id, |ctx, item| {
let ty = item.kind_mut().as_type_mut().unwrap();
@@ -1121,7 +1123,8 @@ If you encounter an error missing from this list, please file an issue or a PR!"
.ancestors(immut_self)
.find(|id| immut_self.resolve_item(*id).is_module())
};
- let new_module = new_module.unwrap_or(self.root_module.into());
+ let new_module =
+ new_module.unwrap_or_else(|| self.root_module.into());
if new_module == old_module {
// Already in the correct module.
@@ -1329,12 +1332,12 @@ If you encounter an error missing from this list, please file an issue or a PR!"
// any sense of template parameter usage, and you're on your own.
let mut used_params = HashMap::default();
for &id in self.allowlisted_items() {
- used_params.entry(id).or_insert(
+ used_params.entry(id).or_insert_with(|| {
id.self_template_params(self)
.into_iter()
.map(|p| p.into())
- .collect(),
- );
+ .collect()
+ });
}
self.used_template_parameters = Some(used_params);
}
@@ -1420,7 +1423,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
fn build_root_module(id: ItemId) -> Item {
let module = Module::new(Some("root".into()), ModuleKind::Normal);
- Item::new(id, None, None, id, ItemKind::Module(module))
+ Item::new(id, None, None, id, ItemKind::Module(module), None)
}
/// Get the root module.
@@ -1730,6 +1733,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
None,
self.current_module.into(),
ItemKind::Type(sub_ty),
+ Some(child.location()),
);
// Bypass all the validations in add_item explicitly.
@@ -1794,6 +1798,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
None,
self.current_module.into(),
ItemKind::Type(ty),
+ Some(location.location()),
);
// Bypass all the validations in add_item explicitly.
@@ -1815,7 +1820,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
.or_else(|| {
decl.cursor()
.usr()
- .and_then(|usr| self.types.get(&TypeKey::USR(usr)))
+ .and_then(|usr| self.types.get(&TypeKey::Usr(usr)))
})
.cloned()
}
@@ -1848,32 +1853,32 @@ If you encounter an error missing from this list, please file an issue or a PR!"
// of it, or
// * we have already parsed and resolved this type, and
// there's nothing left to do.
- if decl.cursor().is_template_like() &&
- *ty != decl.cursor().cur_type() &&
- location.is_some()
- {
- let location = location.unwrap();
-
- // For specialized type aliases, there's no way to get the
- // template parameters as of this writing (for a struct
- // specialization we wouldn't be in this branch anyway).
- //
- // Explicitly return `None` if there aren't any
- // unspecialized parameters (contains any `TypeRef`) so we
- // resolve the canonical type if there is one and it's
- // exposed.
- //
- // This is _tricky_, I know :(
- if decl.cursor().kind() == CXCursor_TypeAliasTemplateDecl &&
- !location.contains_cursor(CXCursor_TypeRef) &&
- ty.canonical_type().is_valid_and_exposed()
+ if let Some(location) = location {
+ if decl.cursor().is_template_like() &&
+ *ty != decl.cursor().cur_type()
{
- return None;
- }
+ // For specialized type aliases, there's no way to get the
+ // template parameters as of this writing (for a struct
+ // specialization we wouldn't be in this branch anyway).
+ //
+ // Explicitly return `None` if there aren't any
+ // unspecialized parameters (contains any `TypeRef`) so we
+ // resolve the canonical type if there is one and it's
+ // exposed.
+ //
+ // This is _tricky_, I know :(
+ if decl.cursor().kind() ==
+ CXCursor_TypeAliasTemplateDecl &&
+ !location.contains_cursor(CXCursor_TypeRef) &&
+ ty.canonical_type().is_valid_and_exposed()
+ {
+ return None;
+ }
- return self
- .instantiate_template(with_id, id, ty, location)
- .or_else(|| Some(id));
+ return self
+ .instantiate_template(with_id, id, ty, location)
+ .or(Some(id));
+ }
}
return Some(self.build_ty_wrapper(with_id, id, parent_id, ty));
@@ -1927,14 +1932,16 @@ If you encounter an error missing from this list, please file an issue or a PR!"
) -> TypeId {
let spelling = ty.spelling();
let layout = ty.fallible_layout(self).ok();
+ let location = ty.declaration().location();
let type_kind = TypeKind::ResolvedTypeRef(wrapped_id);
let ty = Type::new(Some(spelling), layout, type_kind, is_const);
let item = Item::new(
with_id,
None,
None,
- parent_id.unwrap_or(self.current_module.into()),
+ parent_id.unwrap_or_else(|| self.current_module.into()),
ItemKind::Type(ty),
+ Some(location),
);
self.add_builtin_item(item);
with_id.as_type_id_unchecked()
@@ -1995,6 +2002,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
let spelling = ty.spelling();
let is_const = ty.is_const();
let layout = ty.fallible_layout(self).ok();
+ let location = ty.declaration().location();
let ty = Type::new(Some(spelling), layout, type_kind, is_const);
let id = self.next_item_id();
let item = Item::new(
@@ -2003,6 +2011,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
None,
self.root_module.into(),
ItemKind::Type(ty),
+ Some(location),
);
self.add_builtin_item(item);
Some(id.as_type_id_unchecked())
@@ -2074,10 +2083,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
id: Id,
) -> bool {
let id = id.into();
- match self.replacements.get(path) {
- Some(replaced_by) if *replaced_by != id => true,
- _ => false,
- }
+ matches!(self.replacements.get(path), Some(replaced_by) if *replaced_by != id)
}
/// Is the type with the given `name` marked as opaque?
@@ -2112,11 +2118,9 @@ If you encounter an error missing from this list, please file an issue or a PR!"
module_name = Some(spelling)
}
- let tokens = cursor.tokens();
- let mut iter = tokens.iter();
let mut kind = ModuleKind::Normal;
let mut found_namespace_keyword = false;
- while let Some(token) = iter.next() {
+ for token in cursor.tokens().iter() {
match token.spelling() {
b"inline" => {
assert!(!found_namespace_keyword);
@@ -2196,6 +2200,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
None,
self.current_module.into(),
ItemKind::Module(module),
+ Some(cursor.location()),
);
let module_id = module.id().as_module_id_unchecked();
@@ -2243,11 +2248,6 @@ If you encounter an error missing from this list, please file an issue or a PR!"
assert!(self.in_codegen_phase());
assert!(self.current_module == self.root_module);
- let cb = match self.options.parse_callbacks {
- Some(ref cb) => cb,
- None => return CanDerive::No,
- };
-
*self
.blocklisted_types_implement_traits
.borrow_mut()
@@ -2257,8 +2257,27 @@ If you encounter an error missing from this list, please file an issue or a PR!"
.or_insert_with(|| {
item.expect_type()
.name()
- .and_then(|name| {
- cb.blocklisted_type_implements_trait(name, derive_trait)
+ .and_then(|name| match self.options.parse_callbacks {
+ Some(ref cb) => cb.blocklisted_type_implements_trait(
+ name,
+ derive_trait,
+ ),
+ // Sized integer types from <stdint.h> get mapped to Rust primitive
+ // types regardless of whether they are blocklisted, so ensure that
+ // standard traits are considered derivable for them too.
+ None => match name {
+ "int8_t" | "uint8_t" | "int16_t" | "uint16_t" |
+ "int32_t" | "uint32_t" | "int64_t" |
+ "uint64_t" | "uintptr_t" | "intptr_t" |
+ "ptrdiff_t" => Some(CanDerive::Yes),
+ "size_t" if self.options.size_t_is_usize => {
+ Some(CanDerive::Yes)
+ }
+ "ssize_t" if self.options.size_t_is_usize => {
+ Some(CanDerive::Yes)
+ }
+ _ => Some(CanDerive::No),
+ },
})
.unwrap_or(CanDerive::No)
})
@@ -2399,7 +2418,7 @@ If you encounter an error missing from this list, please file an issue or a PR!"
let codegen_items = if self.options().allowlist_recursively {
AllowlistedItemsTraversal::new(
self,
- roots.clone(),
+ roots,
traversal::codegen_edges,
)
.collect::<ItemSet>()
@@ -2663,6 +2682,12 @@ If you encounter an error missing from this list, please file an issue or a PR!"
let name = item.path_for_allowlisting(self)[1..].join("::");
self.options().no_hash_types.matches(&name)
}
+
+ /// Check if `--must-use-type` flag is enabled for this item.
+ pub fn must_use_type_by_name(&self, item: &Item) -> bool {
+ let name = item.path_for_allowlisting(self)[1..].join("::");
+ self.options().must_use_types.matches(&name)
+ }
}
/// A builder struct for configuring item resolution options.
@@ -2694,7 +2719,7 @@ impl ItemResolver {
pub fn new<Id: Into<ItemId>>(id: Id) -> ItemResolver {
let id = id.into();
ItemResolver {
- id: id,
+ id,
through_type_refs: false,
through_type_aliases: false,
}
@@ -2717,8 +2742,16 @@ impl ItemResolver {
assert!(ctx.collected_typerefs());
let mut id = self.id;
+ let mut seen_ids = HashSet::default();
loop {
let item = ctx.resolve_item(id);
+
+ // Detect cycles and bail out. These can happen in certain cases
+ // involving incomplete qualified dependent types (#2085).
+ if !seen_ids.insert(id) {
+ return item;
+ }
+
let ty_kind = item.as_type().map(|t| t.kind());
match ty_kind {
Some(&TypeKind::ResolvedTypeRef(next_id))
@@ -2753,7 +2786,7 @@ impl PartialType {
/// Construct a new `PartialType`.
pub fn new(decl: Cursor, id: ItemId) -> PartialType {
// assert!(decl == decl.canonical());
- PartialType { decl: decl, id: id }
+ PartialType { decl, id }
}
/// The cursor pointing to this partial type's declaration location.
diff --git a/src/ir/enum_ty.rs b/src/ir/enum_ty.rs
index 15d4136..97455c9 100644
--- a/src/ir/enum_ty.rs
+++ b/src/ir/enum_ty.rs
@@ -86,7 +86,7 @@ impl Enum {
} else {
Some(type_name)
};
- let type_name = type_name.as_ref().map(String::as_str);
+ let type_name = type_name.as_deref();
let definition = declaration.definition().unwrap_or(declaration);
definition.visit(|cursor| {
@@ -286,7 +286,7 @@ impl EnumVariant {
/// Get this variant's documentation.
pub fn comment(&self) -> Option<&str> {
- self.comment.as_ref().map(|s| &**s)
+ self.comment.as_deref()
}
/// Returns whether this variant should be enforced to be a constant by code
diff --git a/src/ir/function.rs b/src/ir/function.rs
index 661ee59..a3a2bbf 100644
--- a/src/ir/function.rs
+++ b/src/ir/function.rs
@@ -123,7 +123,7 @@ impl Function {
/// Get this function's name.
pub fn mangled_name(&self) -> Option<&str> {
- self.mangled_name.as_ref().map(|n| &**n)
+ self.mangled_name.as_deref()
}
/// Get this function's signature type.
@@ -187,10 +187,7 @@ pub enum Abi {
impl Abi {
/// Returns whether this Abi is known or not.
fn is_unknown(&self) -> bool {
- match *self {
- Abi::Unknown(..) => true,
- _ => false,
- }
+ matches!(*self, Abi::Unknown(..))
}
}
@@ -340,7 +337,7 @@ fn args_from_ty_and_cursor(
});
let cursor = arg_cur.unwrap_or(*cursor);
- let ty = arg_ty.unwrap_or(cursor.cur_type());
+ let ty = arg_ty.unwrap_or_else(|| cursor.cur_type());
(name, Item::from_ty_or_ref(ty, cursor, None, ctx))
})
.collect()
@@ -360,7 +357,7 @@ impl FunctionSig {
argument_types,
is_variadic,
must_use,
- abi: abi,
+ abi,
}
}
@@ -411,7 +408,7 @@ impl FunctionSig {
CXCursor_CXXMethod |
CXCursor_ObjCInstanceMethodDecl |
CXCursor_ObjCClassMethodDecl => {
- args_from_ty_and_cursor(&ty, &cursor, ctx)
+ args_from_ty_and_cursor(ty, &cursor, ctx)
}
_ => {
// For non-CXCursor_FunctionDecl, visiting the cursor's children
@@ -434,7 +431,7 @@ impl FunctionSig {
// right AST for functions tagged as stdcall and such...
//
// https://bugs.llvm.org/show_bug.cgi?id=45919
- args_from_ty_and_cursor(&ty, &cursor, ctx)
+ args_from_ty_and_cursor(ty, &cursor, ctx)
} else {
args
}
@@ -522,7 +519,7 @@ impl FunctionSig {
warn!("Unknown calling convention: {:?}", call_conv);
}
- Ok(Self::new(ret.into(), args, ty.is_variadic(), must_use, abi))
+ Ok(Self::new(ret, args, ty.is_variadic(), must_use, abi))
}
/// Get this function signature's return type.
@@ -567,10 +564,7 @@ impl FunctionSig {
return false;
}
- match self.abi {
- Abi::C | Abi::Unknown(..) => true,
- _ => false,
- }
+ matches!(self.abi, Abi::C | Abi::Unknown(..))
}
}
diff --git a/src/ir/item.rs b/src/ir/item.rs
index 4e0ba80..8692575 100644
--- a/src/ir/item.rs
+++ b/src/ir/item.rs
@@ -417,6 +417,8 @@ pub struct Item {
parent_id: ItemId,
/// The item kind.
kind: ItemKind,
+ /// The source location of the item.
+ location: Option<clang::SourceLocation>,
}
impl AsRef<ItemId> for Item {
@@ -433,18 +435,20 @@ impl Item {
annotations: Option<Annotations>,
parent_id: ItemId,
kind: ItemKind,
+ location: Option<clang::SourceLocation>,
) -> Self {
debug_assert!(id != parent_id || kind.is_module());
Item {
- id: id,
+ id,
local_id: LazyCell::new(),
next_child_local_id: Cell::new(1),
canonical_name: LazyCell::new(),
path_for_allowlisting: LazyCell::new(),
- parent_id: parent_id,
- comment: comment,
+ parent_id,
+ comment,
annotations: annotations.unwrap_or_default(),
- kind: kind,
+ kind,
+ location,
}
}
@@ -454,10 +458,15 @@ impl Item {
ty: &clang::Type,
ctx: &mut BindgenContext,
) -> TypeId {
+ let location = ty.declaration().location();
let ty = Opaque::from_clang_ty(ty, ctx);
let kind = ItemKind::Type(ty);
let parent = ctx.root_module().into();
- ctx.add_item(Item::new(with_id, None, None, parent, kind), None, None);
+ ctx.add_item(
+ Item::new(with_id, None, None, parent, kind, Some(location)),
+ None,
+ None,
+ );
with_id.as_type_id_unchecked()
}
@@ -612,10 +621,7 @@ impl Item {
/// Is this item a module?
pub fn is_module(&self) -> bool {
- match self.kind {
- ItemKind::Module(..) => true,
- _ => false,
- }
+ matches!(self.kind, ItemKind::Module(..))
}
/// Get this item's annotations.
@@ -635,13 +641,24 @@ impl Item {
return true;
}
+ if !ctx.options().blocklisted_files.is_empty() {
+ if let Some(location) = &self.location {
+ let (file, _, _, _) = location.location();
+ if let Some(filename) = file.name() {
+ if ctx.options().blocklisted_files.matches(&filename) {
+ return true;
+ }
+ }
+ }
+ }
+
let path = self.path_for_allowlisting(ctx);
let name = path[1..].join("::");
ctx.options().blocklisted_items.matches(&name) ||
match self.kind {
ItemKind::Type(..) => {
ctx.options().blocklisted_types.matches(&name) ||
- ctx.is_replaced_type(&path, self.id)
+ ctx.is_replaced_type(path, self.id)
}
ItemKind::Function(..) => {
ctx.options().blocklisted_functions.matches(&name)
@@ -658,10 +675,7 @@ impl Item {
/// Is this item a var type?
pub fn is_var(&self) -> bool {
- match *self.kind() {
- ItemKind::Var(..) => true,
- _ => false,
- }
+ matches!(*self.kind(), ItemKind::Var(..))
}
/// Take out item NameOptions
@@ -722,7 +736,7 @@ impl Item {
.through_type_refs()
.resolve(ctx)
.push_disambiguated_name(ctx, to, level + 1);
- to.push_str("_");
+ to.push('_');
}
to.push_str(&format!("close{}", level));
}
@@ -835,7 +849,7 @@ impl Item {
if ctx.options().enable_cxx_namespaces {
return path.last().unwrap().clone();
}
- return path.join("_").to_owned();
+ return path.join("_");
}
let base_name = target.base_name(ctx);
@@ -873,7 +887,7 @@ impl Item {
// If target is anonymous we need find its first named ancestor.
if target.is_anon() {
- while let Some(id) = ids_iter.next() {
+ for id in ids_iter.by_ref() {
ids.push(id);
if !ctx.resolve_item(id).is_anon() {
@@ -1104,7 +1118,7 @@ impl IsOpaque for Item {
);
self.annotations.opaque() ||
self.as_type().map_or(false, |ty| ty.is_opaque(ctx, self)) ||
- ctx.opaque_by_name(&self.path_for_allowlisting(ctx))
+ ctx.opaque_by_name(self.path_for_allowlisting(ctx))
}
}
@@ -1114,20 +1128,16 @@ where
{
fn has_vtable(&self, ctx: &BindgenContext) -> bool {
let id: ItemId = (*self).into();
- id.as_type_id(ctx)
- .map_or(false, |id| match ctx.lookup_has_vtable(id) {
- HasVtableResult::No => false,
- _ => true,
- })
+ id.as_type_id(ctx).map_or(false, |id| {
+ !matches!(ctx.lookup_has_vtable(id), HasVtableResult::No)
+ })
}
fn has_vtable_ptr(&self, ctx: &BindgenContext) -> bool {
let id: ItemId = (*self).into();
- id.as_type_id(ctx)
- .map_or(false, |id| match ctx.lookup_has_vtable(id) {
- HasVtableResult::SelfHasVtable => true,
- _ => false,
- })
+ id.as_type_id(ctx).map_or(false, |id| {
+ matches!(ctx.lookup_has_vtable(id), HasVtableResult::SelfHasVtable)
+ })
}
}
@@ -1307,7 +1317,7 @@ impl ClangItemParser for Item {
let id = ctx.next_item_id();
let module = ctx.root_module().into();
ctx.add_item(
- Item::new(id, None, None, module, ItemKind::Type(ty)),
+ Item::new(id, None, None, module, ItemKind::Type(ty), None),
None,
None,
);
@@ -1345,6 +1355,7 @@ impl ClangItemParser for Item {
annotations,
relevant_parent_id,
ItemKind::$what(item),
+ Some(cursor.location()),
),
declaration,
Some(cursor),
@@ -1392,7 +1403,7 @@ impl ClangItemParser for Item {
}
ctx.known_semantic_parent(definition)
.or(parent_id)
- .unwrap_or(ctx.current_module().into())
+ .unwrap_or_else(|| ctx.current_module().into())
}
None => relevant_parent_id,
};
@@ -1524,8 +1535,9 @@ impl ClangItemParser for Item {
potential_id,
None,
None,
- parent_id.unwrap_or(current_module.into()),
+ parent_id.unwrap_or_else(|| current_module.into()),
ItemKind::Type(Type::new(None, None, kind, is_const)),
+ Some(location.location()),
),
None,
None,
@@ -1594,8 +1606,8 @@ impl ClangItemParser for Item {
}
let decl = {
- let decl = ty.declaration();
- decl.definition().unwrap_or(decl)
+ let canonical_def = ty.canonical_type().declaration().definition();
+ canonical_def.unwrap_or_else(|| ty.declaration())
};
let comment = decl.raw_comment().or_else(|| location.raw_comment());
@@ -1603,7 +1615,7 @@ impl ClangItemParser for Item {
Annotations::new(&decl).or_else(|| Annotations::new(&location));
if let Some(ref annotations) = annotations {
- if let Some(ref replaced) = annotations.use_instead_of() {
+ if let Some(replaced) = annotations.use_instead_of() {
ctx.replace(replaced, id);
}
}
@@ -1657,6 +1669,7 @@ impl ClangItemParser for Item {
annotations,
relevant_parent_id,
ItemKind::Type(item),
+ Some(location.location()),
),
declaration,
Some(location),
@@ -1851,11 +1864,7 @@ impl ClangItemParser for Item {
clang_sys::CXChildVisit_Continue
});
- if let Some(def) = definition {
- def
- } else {
- return None;
- }
+ definition?
};
assert!(is_template_with_spelling(&definition, &ty_spelling));
@@ -1889,6 +1898,7 @@ impl ClangItemParser for Item {
None,
parent,
ItemKind::Type(Type::named(name)),
+ Some(location.location()),
);
ctx.add_type_param(item, definition);
Some(id.as_type_id_unchecked())
@@ -1939,7 +1949,7 @@ impl ItemCanonicalPath for Item {
path.push(CONSTIFIED_ENUM_MODULE_REPR_NAME.into());
}
- return path;
+ path
}
fn canonical_path(&self, ctx: &BindgenContext) -> Vec<String> {
@@ -1972,8 +1982,8 @@ impl<'a> NameOptions<'a> {
/// Construct a new `NameOptions`
pub fn new(item: &'a Item, ctx: &'a BindgenContext) -> Self {
NameOptions {
- item: item,
- ctx: ctx,
+ item,
+ ctx,
within_namespaces: false,
user_mangled: UserMangled::Yes,
}
diff --git a/src/ir/layout.rs b/src/ir/layout.rs
index 28a6604..6cf9113 100644
--- a/src/ir/layout.rs
+++ b/src/ir/layout.rs
@@ -64,7 +64,7 @@ impl Layout {
next_align *= 2;
}
Layout {
- size: size,
+ size,
align: next_align / 2,
packed: false,
}
diff --git a/src/ir/module.rs b/src/ir/module.rs
index 13b7c19..d5aca94 100644
--- a/src/ir/module.rs
+++ b/src/ir/module.rs
@@ -32,15 +32,15 @@ impl Module {
/// Construct a new `Module`.
pub fn new(name: Option<String>, kind: ModuleKind) -> Self {
Module {
- name: name,
- kind: kind,
+ name,
+ kind,
children: ItemSet::new(),
}
}
/// Get this module's name.
pub fn name(&self) -> Option<&str> {
- self.name.as_ref().map(|n| &**n)
+ self.name.as_deref()
}
/// Get a mutable reference to this module's children.
diff --git a/src/ir/objc.rs b/src/ir/objc.rs
index 91855c6..0845ad0 100644
--- a/src/ir/objc.rs
+++ b/src/ir/objc.rs
@@ -89,12 +89,10 @@ impl ObjCInterface {
pub fn rust_name(&self) -> String {
if let Some(ref cat) = self.category {
format!("{}_{}", self.name(), cat)
+ } else if self.is_protocol {
+ format!("P{}", self.name())
} else {
- if self.is_protocol {
- format!("P{}", self.name())
- } else {
- format!("I{}", self.name().to_owned())
- }
+ format!("I{}", self.name().to_owned())
}
}
@@ -149,28 +147,34 @@ impl ObjCInterface {
// Gather protocols this interface conforms to
let needle = format!("P{}", c.spelling());
let items_map = ctx.items();
- debug!("Interface {} conforms to {}, find the item", interface.name, needle);
+ debug!(
+ "Interface {} conforms to {}, find the item",
+ interface.name, needle
+ );
- for (id, item) in items_map
- {
+ for (id, item) in items_map {
if let Some(ty) = item.as_type() {
- match *ty.kind() {
- TypeKind::ObjCInterface(ref protocol) => {
- if protocol.is_protocol
- {
- debug!("Checking protocol {}, ty.name {:?}", protocol.name, ty.name());
- if Some(needle.as_ref()) == ty.name() {
- debug!("Found conforming protocol {:?}", item);
- interface.conforms_to.push(id);
- break;
- }
+ if let TypeKind::ObjCInterface(ref protocol) =
+ *ty.kind()
+ {
+ if protocol.is_protocol {
+ debug!(
+ "Checking protocol {}, ty.name {:?}",
+ protocol.name,
+ ty.name()
+ );
+ if Some(needle.as_ref()) == ty.name() {
+ debug!(
+ "Found conforming protocol {:?}",
+ item
+ );
+ interface.conforms_to.push(id);
+ break;
}
}
- _ => {}
}
}
}
-
}
CXCursor_ObjCInstanceMethodDecl |
CXCursor_ObjCClassMethodDecl => {
@@ -178,8 +182,10 @@ impl ObjCInterface {
let signature =
FunctionSig::from_ty(&c.cur_type(), &c, ctx)
.expect("Invalid function sig");
- let is_class_method = c.kind() == CXCursor_ObjCClassMethodDecl;
- let method = ObjCMethod::new(&name, signature, is_class_method);
+ let is_class_method =
+ c.kind() == CXCursor_ObjCClassMethodDecl;
+ let method =
+ ObjCMethod::new(&name, signature, is_class_method);
interface.add_method(method);
}
CXCursor_TemplateTypeParameter => {
@@ -189,7 +195,7 @@ impl ObjCInterface {
CXCursor_ObjCSuperClassRef => {
let item = Item::from_ty_or_ref(c.cur_type(), c, None, ctx);
interface.parent_class = Some(item.into());
- },
+ }
_ => {}
}
CXChildVisit_Continue
@@ -218,7 +224,7 @@ impl ObjCMethod {
ObjCMethod {
name: name.to_owned(),
- rust_name: rust_name.to_owned(),
+ rust_name,
signature,
is_class_method,
}
@@ -261,7 +267,7 @@ impl ObjCMethod {
.collect();
// No arguments
- if args.len() == 0 && split_name.len() == 1 {
+ if args.is_empty() && split_name.len() == 1 {
let name = &split_name[0];
return quote! {
#name
@@ -269,13 +275,12 @@ impl ObjCMethod {
}
// Check right amount of arguments
- if args.len() != split_name.len() - 1 {
- panic!(
- "Incorrect method name or arguments for objc method, {:?} vs {:?}",
- args,
- split_name,
- );
- }
+ assert!(
+ args.len() == split_name.len() - 1,
+ "Incorrect method name or arguments for objc method, {:?} vs {:?}",
+ args,
+ split_name
+ );
// Get arguments without type signatures to pass to `msg_send!`
let mut args_without_types = vec![];
diff --git a/src/ir/template.rs b/src/ir/template.rs
index b519fff..8b06748 100644
--- a/src/ir/template.rs
+++ b/src/ir/template.rs
@@ -134,10 +134,10 @@ pub trait TemplateParameters: Sized {
where
Self: ItemAncestors,
{
- let ancestors: Vec<_> = self.ancestors(ctx).collect();
+ let mut ancestors: Vec<_> = self.ancestors(ctx).collect();
+ ancestors.reverse();
ancestors
.into_iter()
- .rev()
.flat_map(|id| id.self_template_params(ctx).into_iter())
.collect()
}
diff --git a/src/ir/traversal.rs b/src/ir/traversal.rs
index 430dd02..088e744 100644
--- a/src/ir/traversal.rs
+++ b/src/ir/traversal.rs
@@ -24,9 +24,9 @@ impl Edge {
}
}
-impl Into<ItemId> for Edge {
- fn into(self) -> ItemId {
- self.to
+impl From<Edge> for ItemId {
+ fn from(val: Edge) -> Self {
+ val.to
}
}
@@ -424,10 +424,10 @@ where
}
ItemTraversal {
- ctx: ctx,
- seen: seen,
- queue: queue,
- predicate: predicate,
+ ctx,
+ seen,
+ queue,
+ predicate,
currently_traversing: None,
}
}
diff --git a/src/ir/ty.rs b/src/ir/ty.rs
index e049ed6..d573408 100644
--- a/src/ir/ty.rs
+++ b/src/ir/ty.rs
@@ -87,23 +87,17 @@ impl Type {
/// Get this type's name.
pub fn name(&self) -> Option<&str> {
- self.name.as_ref().map(|name| &**name)
+ self.name.as_deref()
}
/// Whether this is a block pointer type.
pub fn is_block_pointer(&self) -> bool {
- match self.kind {
- TypeKind::BlockPointer(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::BlockPointer(..))
}
/// Is this a compound type?
pub fn is_comp(&self) -> bool {
- match self.kind {
- TypeKind::Comp(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::Comp(..))
}
/// Is this a union?
@@ -116,58 +110,43 @@ impl Type {
/// Is this type of kind `TypeKind::TypeParam`?
pub fn is_type_param(&self) -> bool {
- match self.kind {
- TypeKind::TypeParam => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::TypeParam)
}
/// Is this a template instantiation type?
pub fn is_template_instantiation(&self) -> bool {
- match self.kind {
- TypeKind::TemplateInstantiation(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::TemplateInstantiation(..))
}
/// Is this a template alias type?
pub fn is_template_alias(&self) -> bool {
- match self.kind {
- TypeKind::TemplateAlias(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::TemplateAlias(..))
}
/// Is this a function type?
pub fn is_function(&self) -> bool {
- match self.kind {
- TypeKind::Function(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::Function(..))
}
/// Is this an enum type?
pub fn is_enum(&self) -> bool {
- match self.kind {
- TypeKind::Enum(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::Enum(..))
}
/// Is this either a builtin or named type?
pub fn is_builtin_or_type_param(&self) -> bool {
- match self.kind {
+ matches!(
+ self.kind,
TypeKind::Void |
- TypeKind::NullPtr |
- TypeKind::Function(..) |
- TypeKind::Array(..) |
- TypeKind::Reference(..) |
- TypeKind::Pointer(..) |
- TypeKind::Int(..) |
- TypeKind::Float(..) |
- TypeKind::TypeParam => true,
- _ => false,
- }
+ TypeKind::NullPtr |
+ TypeKind::Function(..) |
+ TypeKind::Array(..) |
+ TypeKind::Reference(..) |
+ TypeKind::Pointer(..) |
+ TypeKind::Int(..) |
+ TypeKind::Float(..) |
+ TypeKind::TypeParam
+ )
}
/// Creates a new named type, with name `name`.
@@ -178,26 +157,17 @@ impl Type {
/// Is this a floating point type?
pub fn is_float(&self) -> bool {
- match self.kind {
- TypeKind::Float(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::Float(..))
}
/// Is this a boolean type?
pub fn is_bool(&self) -> bool {
- match self.kind {
- TypeKind::Int(IntKind::Bool) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::Int(IntKind::Bool))
}
/// Is this an integer type?
pub fn is_integer(&self) -> bool {
- match self.kind {
- TypeKind::Int(..) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::Int(..))
}
/// Cast this type to an integer kind, or `None` if it is not an integer
@@ -216,19 +186,15 @@ impl Type {
/// Is this a reference to another type?
pub fn is_type_ref(&self) -> bool {
- match self.kind {
- TypeKind::ResolvedTypeRef(_) |
- TypeKind::UnresolvedTypeRef(_, _, _) => true,
- _ => false,
- }
+ matches!(
+ self.kind,
+ TypeKind::ResolvedTypeRef(_) | TypeKind::UnresolvedTypeRef(_, _, _)
+ )
}
/// Is this an unresolved reference?
pub fn is_unresolved_ref(&self) -> bool {
- match self.kind {
- TypeKind::UnresolvedTypeRef(_, _, _) => true,
- _ => false,
- }
+ matches!(self.kind, TypeKind::UnresolvedTypeRef(_, _, _))
}
/// Is this a incomplete array type?
@@ -278,14 +244,14 @@ impl Type {
match self.kind {
TypeKind::TypeParam => {
let name = self.name().expect("Unnamed named type?");
- !clang::is_valid_identifier(&name)
+ !clang::is_valid_identifier(name)
}
_ => false,
}
}
/// Takes `name`, and returns a suitable identifier representation for it.
- fn sanitize_name<'a>(name: &'a str) -> Cow<'a, str> {
+ fn sanitize_name(name: &str) -> Cow<str> {
if clang::is_valid_identifier(name) {
return Cow::Borrowed(name);
}
@@ -300,12 +266,8 @@ impl Type {
ctx: &BindgenContext,
) -> Option<Cow<'a, str>> {
let name_info = match *self.kind() {
- TypeKind::Pointer(inner) => {
- Some((inner.into(), Cow::Borrowed("ptr")))
- }
- TypeKind::Reference(inner) => {
- Some((inner.into(), Cow::Borrowed("ref")))
- }
+ TypeKind::Pointer(inner) => Some((inner, Cow::Borrowed("ptr"))),
+ TypeKind::Reference(inner) => Some((inner, Cow::Borrowed("ref"))),
TypeKind::Array(inner, length) => {
Some((inner, format!("array{}", length).into()))
}
@@ -375,16 +337,16 @@ impl Type {
/// There are some types we don't want to stop at when finding an opaque
/// item, so we can arrive to the proper item that needs to be generated.
pub fn should_be_traced_unconditionally(&self) -> bool {
- match self.kind {
+ matches!(
+ self.kind,
TypeKind::Comp(..) |
- TypeKind::Function(..) |
- TypeKind::Pointer(..) |
- TypeKind::Array(..) |
- TypeKind::Reference(..) |
- TypeKind::TemplateInstantiation(..) |
- TypeKind::ResolvedTypeRef(..) => true,
- _ => false,
- }
+ TypeKind::Function(..) |
+ TypeKind::Pointer(..) |
+ TypeKind::Array(..) |
+ TypeKind::Reference(..) |
+ TypeKind::TemplateInstantiation(..) |
+ TypeKind::ResolvedTypeRef(..)
+ )
}
}
@@ -791,7 +753,7 @@ impl Type {
(ty.template_args().is_some() && ty_kind != CXType_Typedef)
{
// This is a template instantiation.
- match TemplateInstantiation::from_ty(&ty, ctx) {
+ match TemplateInstantiation::from_ty(ty, ctx) {
Some(inst) => TypeKind::TemplateInstantiation(inst),
None => TypeKind::Opaque,
}
@@ -1120,7 +1082,16 @@ impl Type {
let inner = cursor.typedef_type().expect("Not valid Type?");
let inner =
Item::from_ty_or_ref(inner, location, None, ctx);
- TypeKind::Alias(inner)
+ if inner == potential_id {
+ warn!(
+ "Generating oqaque type instead of self-referential \
+ typedef");
+ // This can happen if we bail out of recursive situations
+ // within the clang parsing.
+ TypeKind::Opaque
+ } else {
+ TypeKind::Alias(inner)
+ }
}
CXType_Enum => {
let enum_ = Enum::from_ty(ty, ctx).expect("Not an enum?");
diff --git a/src/ir/var.rs b/src/ir/var.rs
index 49c4f30..cd17937 100644
--- a/src/ir/var.rs
+++ b/src/ir/var.rs
@@ -88,7 +88,7 @@ impl Var {
/// Get this variable's mangled name.
pub fn mangled_name(&self) -> Option<&str> {
- self.mangled_name.as_ref().map(|n| &**n)
+ self.mangled_name.as_deref()
}
}
@@ -282,7 +282,7 @@ impl ClangSubItemParser for Var {
.parse_callbacks()
.and_then(|c| c.int_macro(&name, value))
.unwrap_or_else(|| {
- default_macro_constant_type(&ctx, value)
+ default_macro_constant_type(ctx, value)
});
(TypeKind::Int(kind), VarType::Int(value))
@@ -398,11 +398,8 @@ fn parse_macro(
let parser = expr::IdentifierParser::new(ctx.parsed_macros());
- match parser.macro_definition(&cexpr_tokens) {
- Ok((_, (id, val))) => {
- return Some((id.into(), val));
- }
- _ => {}
+ if let Ok((_, (id, val))) = parser.macro_definition(&cexpr_tokens) {
+ return Some((id.into(), val));
}
// Try without the last token, to workaround a libclang bug in versions
diff --git a/src/lib.rs b/src/lib.rs
index 01adba3..9a90dac 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -89,7 +89,7 @@ type HashSet<K> = ::rustc_hash::FxHashSet<K>;
pub(crate) use std::collections::hash_map::Entry;
/// Default prefix for the anon fields.
-pub const DEFAULT_ANON_FIELDS_PREFIX: &'static str = "__bindgen_anon_";
+pub const DEFAULT_ANON_FIELDS_PREFIX: &str = "__bindgen_anon_";
fn file_is_cpp(name_file: &str) -> bool {
name_file.ends_with(".hpp") ||
@@ -308,6 +308,7 @@ impl Builder {
(&self.options.blocklisted_types, "--blocklist-type"),
(&self.options.blocklisted_functions, "--blocklist-function"),
(&self.options.blocklisted_items, "--blocklist-item"),
+ (&self.options.blocklisted_files, "--blocklist-file"),
(&self.options.opaque_types, "--opaque-type"),
(&self.options.allowlisted_functions, "--allowlist-function"),
(&self.options.allowlisted_types, "--allowlist-type"),
@@ -317,6 +318,7 @@ impl Builder {
(&self.options.no_debug_types, "--no-debug"),
(&self.options.no_default_types, "--no-default"),
(&self.options.no_hash_types, "--no-hash"),
+ (&self.options.must_use_types, "--must-use-type"),
];
for (set, flag) in regex_sets {
@@ -820,6 +822,13 @@ impl Builder {
self
}
+ /// Hide any contents of the given file from the generated bindings,
+ /// regardless of whether it's a type, function, module etc.
+ pub fn blocklist_file<T: AsRef<str>>(mut self, arg: T) -> Builder {
+ self.options.blocklisted_files.insert(arg);
+ self
+ }
+
/// Treat the given type as opaque in the generated bindings. Regular
/// expressions are supported.
///
@@ -1588,6 +1597,13 @@ impl Builder {
self
}
+ /// Add `#[must_use]` for the given type. Regular
+ /// expressions are supported.
+ pub fn must_use_type<T: Into<String>>(mut self, arg: T) -> Builder {
+ self.options.must_use_types.insert(arg.into());
+ self
+ }
+
/// Set whether `arr[size]` should be treated as `*mut T` or `*mut [T; size]` (same for mut)
pub fn array_pointers_in_arguments(mut self, doit: bool) -> Self {
self.options.array_pointers_in_arguments = doit;
@@ -1661,6 +1677,10 @@ struct BindgenOptions {
/// blocklisted and should not appear in the generated code.
blocklisted_items: RegexSet,
+ /// The set of files whose contents should be blocklisted and should not
+ /// appear in the generated code.
+ blocklisted_files: RegexSet,
+
/// The set of types that should be treated as opaque structures in the
/// generated code.
opaque_types: RegexSet,
@@ -1928,6 +1948,9 @@ struct BindgenOptions {
/// The set of types that we should not derive `Hash` for.
no_hash_types: RegexSet,
+ /// The set of types that we should be annotated with `#[must_use]`.
+ must_use_types: RegexSet,
+
/// Decide if C arrays should be regular pointers in rust or array pointers
array_pointers_in_arguments: bool,
@@ -1971,6 +1994,7 @@ impl BindgenOptions {
&mut self.blocklisted_types,
&mut self.blocklisted_functions,
&mut self.blocklisted_items,
+ &mut self.blocklisted_files,
&mut self.opaque_types,
&mut self.bitfield_enums,
&mut self.constified_enums,
@@ -1986,6 +2010,7 @@ impl BindgenOptions {
&mut self.no_debug_types,
&mut self.no_default_types,
&mut self.no_hash_types,
+ &mut self.must_use_types,
];
let record_matches = self.record_matches;
for regex_set in &mut regex_sets {
@@ -2017,6 +2042,7 @@ impl Default for BindgenOptions {
blocklisted_types: Default::default(),
blocklisted_functions: Default::default(),
blocklisted_items: Default::default(),
+ blocklisted_files: Default::default(),
opaque_types: Default::default(),
rustfmt_path: Default::default(),
depfile: Default::default(),
@@ -2090,6 +2116,7 @@ impl Default for BindgenOptions {
no_debug_types: Default::default(),
no_default_types: Default::default(),
no_hash_types: Default::default(),
+ must_use_types: Default::default(),
array_pointers_in_arguments: false,
wasm_import_module_name: None,
dynamic_library_name: None,
@@ -2135,7 +2162,7 @@ pub struct Bindings {
module: proc_macro2::TokenStream,
}
-pub(crate) const HOST_TARGET: &'static str =
+pub(crate) const HOST_TARGET: &str =
include_str!(concat!(env!("OUT_DIR"), "/host-target.txt"));
// Some architecture triplets are different between rust and libclang, see #1211
@@ -2143,7 +2170,8 @@ pub(crate) const HOST_TARGET: &'static str =
fn rust_to_clang_target(rust_target: &str) -> String {
if rust_target.starts_with("aarch64-apple-") {
let mut clang_target = "arm64-apple-".to_owned();
- clang_target.push_str(&rust_target["aarch64-apple-".len()..]);
+ clang_target
+ .push_str(rust_target.strip_prefix("aarch64-apple-").unwrap());
return clang_target;
}
rust_target.to_owned()
@@ -2265,10 +2293,7 @@ impl Bindings {
// Whether we are working with C or C++ inputs.
let is_cpp = args_are_cpp(&options.clang_args) ||
- options
- .input_header
- .as_ref()
- .map_or(false, |i| file_is_cpp(&i));
+ options.input_header.as_deref().map_or(false, file_is_cpp);
let search_paths = if is_cpp {
clang.cpp_search_paths
@@ -2356,15 +2381,6 @@ impl Bindings {
})
}
- /// Convert these bindings into source text (with raw lines prepended).
- pub fn to_string(&self) -> String {
- let mut bytes = vec![];
- self.write(Box::new(&mut bytes) as Box<dyn Write>)
- .expect("writing to a vec cannot fail");
- String::from_utf8(bytes)
- .expect("we should only write bindings that are valid utf-8")
- }
-
/// Write these bindings as source text to a file.
pub fn write_to_file<P: AsRef<Path>>(&self, path: P) -> io::Result<()> {
let file = OpenOptions::new()
@@ -2379,7 +2395,7 @@ impl Bindings {
/// Write these bindings as source text to the given `Write`able.
pub fn write<'a>(&self, mut writer: Box<dyn Write + 'a>) -> io::Result<()> {
if !self.options.disable_header_comment {
- let version = Some("0.59.1");
+ let version = Some("0.59.2");
let header = format!(
"/* automatically generated by rust-bindgen {} */\n\n",
version.unwrap_or("(unknown version)")
@@ -2414,7 +2430,7 @@ impl Bindings {
}
/// Gets the rustfmt path to rustfmt the generated bindings.
- fn rustfmt_path<'a>(&'a self) -> io::Result<Cow<'a, PathBuf>> {
+ fn rustfmt_path(&self) -> io::Result<Cow<PathBuf>> {
debug_assert!(self.options.rustfmt_bindings);
if let Some(ref p) = self.options.rustfmt_path {
return Ok(Cow::Borrowed(p));
@@ -2505,6 +2521,18 @@ impl Bindings {
}
}
+impl std::fmt::Display for Bindings {
+ fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
+ let mut bytes = vec![];
+ self.write(Box::new(&mut bytes) as Box<dyn Write>)
+ .expect("writing to a vec cannot fail");
+ f.write_str(
+ std::str::from_utf8(&bytes)
+ .expect("we should only write bindings that are valid utf-8"),
+ )
+ }
+}
+
/// Determines whether the given cursor is in any of the files matched by the
/// options.
fn filter_builtins(ctx: &BindgenContext, cursor: &clang::Cursor) -> bool {
@@ -2553,7 +2581,7 @@ fn parse(context: &mut BindgenContext) -> Result<(), ()> {
if context.options().emit_ast {
fn dump_if_not_builtin(cur: &clang::Cursor) -> CXChildVisitResult {
if !cur.is_builtin() {
- clang::ast_dump(&cur, 0)
+ clang::ast_dump(cur, 0)
} else {
CXChildVisit_Continue
}
@@ -2590,26 +2618,19 @@ pub fn clang_version() -> ClangVersion {
let raw_v: String = clang::extract_clang_version();
let split_v: Option<Vec<&str>> = raw_v
.split_whitespace()
- .filter(|t| t.chars().next().map_or(false, |v| v.is_ascii_digit()))
- .next()
+ .find(|t| t.chars().next().map_or(false, |v| v.is_ascii_digit()))
.map(|v| v.split('.').collect());
- match split_v {
- Some(v) => {
- if v.len() >= 2 {
- let maybe_major = v[0].parse::<u32>();
- let maybe_minor = v[1].parse::<u32>();
- match (maybe_major, maybe_minor) {
- (Ok(major), Ok(minor)) => {
- return ClangVersion {
- parsed: Some((major, minor)),
- full: raw_v.clone(),
- }
- }
- _ => {}
- }
+ if let Some(v) = split_v {
+ if v.len() >= 2 {
+ let maybe_major = v[0].parse::<u32>();
+ let maybe_minor = v[1].parse::<u32>();
+ if let (Ok(major), Ok(minor)) = (maybe_major, maybe_minor) {
+ return ClangVersion {
+ parsed: Some((major, minor)),
+ full: raw_v.clone(),
+ };
}
}
- None => {}
};
ClangVersion {
parsed: None,
@@ -2635,7 +2656,7 @@ fn get_target_dependent_env_var(var: &str) -> Option<String> {
/// A ParseCallbacks implementation that will act on file includes by echoing a rerun-if-changed
/// line
///
-/// When running in side a `build.rs` script, this can be used to make cargo invalidate the
+/// When running inside a `build.rs` script, this can be used to make cargo invalidate the
/// generated bindings whenever any of the files included from the header change:
/// ```
/// use bindgen::builder;
diff --git a/src/log_stubs.rs b/src/log_stubs.rs
index 4af496c..8315983 100644
--- a/src/log_stubs.rs
+++ b/src/log_stubs.rs
@@ -1,32 +1,32 @@
#![allow(unused)]
macro_rules! log {
- (target: $target:expr, $lvl:expr, $($arg:tt)+) => {
+ (target: $target:expr, $lvl:expr, $($arg:tt)+) => {{
let _ = $target;
let _ = log!($lvl, $($arg)+);
- };
+ }};
($lvl:expr, $($arg:tt)+) => {{
let _ = $lvl;
let _ = format_args!($($arg)+);
}};
}
macro_rules! error {
- (target: $target:expr, $($arg:tt)*) => { log!($target, $($arg)*); };
- ($($arg:tt)*) => { log!("", $($arg)*); };
+ (target: $target:expr, $($arg:tt)+) => { log!(target: $target, "", $($arg)+) };
+ ($($arg:tt)+) => { log!("", $($arg)+) };
}
macro_rules! warn {
- (target: $target:expr, $($arg:tt)*) => { log!($target, $($arg)*); };
- ($($arg:tt)*) => { log!("", $($arg)*); };
+ (target: $target:expr, $($arg:tt)*) => { log!(target: $target, "", $($arg)*) };
+ ($($arg:tt)*) => { log!("", $($arg)*) };
}
macro_rules! info {
- (target: $target:expr, $($arg:tt)*) => { log!($target, $($arg)*); };
- ($($arg:tt)*) => { log!("", $($arg)*); };
+ (target: $target:expr, $($arg:tt)+) => { log!(target: $target, "", $($arg)+) };
+ ($($arg:tt)+) => { log!("", $($arg)+) };
}
macro_rules! debug {
- (target: $target:expr, $($arg:tt)*) => { log!($target, $($arg)*); };
- ($($arg:tt)*) => { log!("", $($arg)*); };
+ (target: $target:expr, $($arg:tt)+) => { log!(target: $target, "", $($arg)+) };
+ ($($arg:tt)+) => { log!("", $($arg)+) };
}
macro_rules! trace {
- (target: $target:expr, $($arg:tt)*) => { log!($target, $($arg)*); };
- ($($arg:tt)*) => { log!("", $($arg)*); };
+ (target: $target:expr, $($arg:tt)+) => { log!(target: $target, "", $($arg)+) };
+ ($($arg:tt)+) => { log!("", $($arg)+) };
}
diff --git a/src/main.rs b/src/main.rs
index 1768ed8..f3398db 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -37,7 +37,7 @@ fn clang_version_check() {
);
if expected_version.is_some() {
- assert_eq!(version.parsed, version.parsed);
+ // assert_eq!(version.parsed, version.parsed);
}
}
@@ -45,9 +45,7 @@ pub fn main() {
#[cfg(feature = "logging")]
env_logger::init();
- let bind_args: Vec<_> = env::args().collect();
-
- match builder_from_flags(bind_args.into_iter()) {
+ match builder_from_flags(env::args()) {
Ok((builder, output, verbose)) => {
clang_version_check();
let builder_result = panic::catch_unwind(|| {
diff --git a/src/options.rs b/src/options.rs
index c02f275..94f3047 100644
--- a/src/options.rs
+++ b/src/options.rs
@@ -23,7 +23,7 @@ where
);
let matches = App::new("bindgen")
- .version(Some("0.59.1").unwrap_or("unknown"))
+ .version(Some("0.59.2").unwrap_or("unknown"))
.about("Generates Rust bindings from C/C++ headers.")
.usage("bindgen [FLAGS] [OPTIONS] <header> -- <clang-args>...")
.args(&[
@@ -164,6 +164,14 @@ where
.takes_value(true)
.multiple(true)
.number_of_values(1),
+ Arg::with_name("blocklist-file")
+ .alias("blacklist-file")
+ .long("blocklist-file")
+ .help("Mark all contents of <path> as hidden.")
+ .value_name("path")
+ .takes_value(true)
+ .multiple(true)
+ .number_of_values(1),
Arg::with_name("no-layout-tests")
.long("no-layout-tests")
.help("Avoid generating layout tests for any type."),
@@ -486,6 +494,13 @@ where
.takes_value(true)
.multiple(true)
.number_of_values(1),
+ Arg::with_name("must-use-type")
+ .long("must-use-type")
+ .help("Add #[must_use] annotation to types matching <regex>.")
+ .value_name("regex")
+ .takes_value(true)
+ .multiple(true)
+ .number_of_values(1),
Arg::with_name("enable-function-attribute-detection")
.long("enable-function-attribute-detection")
.help(
@@ -623,6 +638,12 @@ where
}
}
+ if let Some(hidden_files) = matches.values_of("blocklist-file") {
+ for file in hidden_files {
+ builder = builder.blocklist_file(file);
+ }
+ }
+
if matches.is_present("builtins") {
builder = builder.emit_builtins();
}
@@ -710,7 +731,7 @@ where
if let Some(what_to_generate) = matches.value_of("generate") {
let mut config = CodegenConfig::empty();
- for what in what_to_generate.split(",") {
+ for what in what_to_generate.split(',') {
match what {
"functions" => config.insert(CodegenConfig::FUNCTIONS),
"types" => config.insert(CodegenConfig::TYPES),
@@ -943,6 +964,12 @@ where
}
}
+ if let Some(must_use_type) = matches.values_of("must-use-type") {
+ for regex in must_use_type {
+ builder = builder.must_use_type(regex);
+ }
+ }
+
if let Some(dynamic_library_name) = matches.value_of("dynamic-loading") {
builder = builder.dynamic_library_name(dynamic_library_name);
}