mirror of
https://github.com/Dasharo/linux.git
synced 2026-03-06 15:25:10 -08:00
Merge tag 'rust-6.13' of https://github.com/Rust-for-Linux/linux
Pull rust updates from Miguel Ojeda:
"Toolchain and infrastructure:
- Enable a series of lints, including safety-related ones, e.g. the
compiler will now warn about missing safety comments, as well as
unnecessary ones. How safety documentation is organized is a
frequent source of review comments, thus having the compiler guide
new developers on where they are expected (and where not) is very
nice.
- Start using '#[expect]': an interesting feature in Rust (stabilized
in 1.81.0) that makes the compiler warn if an expected warning was
_not_ emitted. This is useful to avoid forgetting cleaning up
locally ignored diagnostics ('#[allow]'s).
- Introduce '.clippy.toml' configuration file for Clippy, the Rust
linter, which will allow us to tweak its behaviour. For instance,
our first use cases are declaring a disallowed macro and, more
importantly, enabling the checking of private items.
- Lints-related fixes and cleanups related to the items above.
- Migrate from 'receiver_trait' to 'arbitrary_self_types': to get the
kernel into stable Rust, one of the major pieces of the puzzle is
the support to write custom types that can be used as 'self', i.e.
as receivers, since the kernel needs to write types such as 'Arc'
that common userspace Rust would not. 'arbitrary_self_types' has
been accepted to become stable, and this is one of the steps
required to get there.
- Remove usage of the 'new_uninit' unstable feature.
- Use custom C FFI types. Includes a new 'ffi' crate to contain our
custom mapping, instead of using the standard library 'core::ffi'
one. The actual remapping will be introduced in a later cycle.
- Map '__kernel_{size_t,ssize_t,ptrdiff_t}' to 'usize'/'isize'
instead of 32/64-bit integers.
- Fix 'size_t' in bindgen generated prototypes of C builtins.
- Warn on bindgen < 0.69.5 and libclang >= 19.1 due to a double issue
in the projects, which we managed to trigger with the upcoming
tracepoint support. It includes a build test since some
distributions backported the fix (e.g. Debian -- thanks!). All
major distributions we list should be now OK except Ubuntu non-LTS.
'macros' crate:
- Adapt the build system to be able run the doctests there too; and
clean up and enable the corresponding doctests.
'kernel' crate:
- Add 'alloc' module with generic kernel allocator support and remove
the dependency on the Rust standard library 'alloc' and the
extension traits we used to provide fallible methods with flags.
Add the 'Allocator' trait and its implementations '{K,V,KV}malloc'.
Add the 'Box' type (a heap allocation for a single value of type
'T' that is also generic over an allocator and considers the
kernel's GFP flags) and its shorthand aliases '{K,V,KV}Box'. Add
'ArrayLayout' type. Add 'Vec' (a contiguous growable array type)
and its shorthand aliases '{K,V,KV}Vec', including iterator
support.
For instance, now we may write code such as:
let mut v = KVec::new();
v.push(1, GFP_KERNEL)?;
assert_eq!(&v, &[1]);
Treewide, move as well old users to these new types.
- 'sync' module: add global lock support, including the
'GlobalLockBackend' trait; the 'Global{Lock,Guard,LockedBy}' types
and the 'global_lock!' macro. Add the 'Lock::try_lock' method.
- 'error' module: optimize 'Error' type to use 'NonZeroI32' and make
conversion functions public.
- 'page' module: add 'page_align' function.
- Add 'transmute' module with the existing 'FromBytes' and 'AsBytes'
traits.
- 'block::mq::request' module: improve rendered documentation.
- 'types' module: extend 'Opaque' type documentation and add simple
examples for the 'Either' types.
drm/panic:
- Clean up a series of Clippy warnings.
Documentation:
- Add coding guidelines for lints and the '#[expect]' feature.
- Add Ubuntu to the list of distributions in the Quick Start guide.
MAINTAINERS:
- Add Danilo Krummrich as maintainer of the new 'alloc' module.
And a few other small cleanups and fixes"
* tag 'rust-6.13' of https://github.com/Rust-for-Linux/linux: (82 commits)
rust: alloc: Fix `ArrayLayout` allocations
docs: rust: remove spurious item in `expect` list
rust: allow `clippy::needless_lifetimes`
rust: warn on bindgen < 0.69.5 and libclang >= 19.1
rust: use custom FFI integer types
rust: map `__kernel_size_t` and friends also to usize/isize
rust: fix size_t in bindgen prototypes of C builtins
rust: sync: add global lock support
rust: macros: enable the rest of the tests
rust: macros: enable paste! use from macro_rules!
rust: enable macros::module! tests
rust: kbuild: expand rusttest target for macros
rust: types: extend `Opaque` documentation
rust: block: fix formatting of `kernel::block::mq::request` module
rust: macros: fix documentation of the paste! macro
rust: kernel: fix THIS_MODULE header path in ThisModule doc comment
rust: page: add Rust version of PAGE_ALIGN
rust: helpers: remove unnecessary header includes
rust: exports: improve grammar in commentary
drm/panic: allow verbose version check
...
This commit is contained in:
9
.clippy.toml
Normal file
9
.clippy.toml
Normal file
@@ -0,0 +1,9 @@
|
||||
# SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
check-private-items = true
|
||||
|
||||
disallowed-macros = [
|
||||
# The `clippy::dbg_macro` lint only works with `std::dbg!`, thus we simulate
|
||||
# it here, see: https://github.com/rust-lang/rust-clippy/issues/11303.
|
||||
{ path = "kernel::dbg", reason = "the `dbg!` macro is intended as a debugging tool" },
|
||||
]
|
||||
1
.gitignore
vendored
1
.gitignore
vendored
@@ -103,6 +103,7 @@ modules.order
|
||||
# We don't want to ignore the following even if they are dot-files
|
||||
#
|
||||
!.clang-format
|
||||
!.clippy.toml
|
||||
!.cocciconfig
|
||||
!.editorconfig
|
||||
!.get_maintainer.ignore
|
||||
|
||||
@@ -227,3 +227,149 @@ The equivalent in Rust may look like (ignoring documentation):
|
||||
That is, the equivalent of ``GPIO_LINE_DIRECTION_IN`` would be referred to as
|
||||
``gpio::LineDirection::In``. In particular, it should not be named
|
||||
``gpio::gpio_line_direction::GPIO_LINE_DIRECTION_IN``.
|
||||
|
||||
|
||||
Lints
|
||||
-----
|
||||
|
||||
In Rust, it is possible to ``allow`` particular warnings (diagnostics, lints)
|
||||
locally, making the compiler ignore instances of a given warning within a given
|
||||
function, module, block, etc.
|
||||
|
||||
It is similar to ``#pragma GCC diagnostic push`` + ``ignored`` + ``pop`` in C
|
||||
[#]_:
|
||||
|
||||
.. code-block:: c
|
||||
|
||||
#pragma GCC diagnostic push
|
||||
#pragma GCC diagnostic ignored "-Wunused-function"
|
||||
static void f(void) {}
|
||||
#pragma GCC diagnostic pop
|
||||
|
||||
.. [#] In this particular case, the kernel's ``__{always,maybe}_unused``
|
||||
attributes (C23's ``[[maybe_unused]]``) may be used; however, the example
|
||||
is meant to reflect the equivalent lint in Rust discussed afterwards.
|
||||
|
||||
But way less verbose:
|
||||
|
||||
.. code-block:: rust
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn f() {}
|
||||
|
||||
By that virtue, it makes it possible to comfortably enable more diagnostics by
|
||||
default (i.e. outside ``W=`` levels). In particular, those that may have some
|
||||
false positives but that are otherwise quite useful to keep enabled to catch
|
||||
potential mistakes.
|
||||
|
||||
On top of that, Rust provides the ``expect`` attribute which takes this further.
|
||||
It makes the compiler warn if the warning was not produced. For instance, the
|
||||
following will ensure that, when ``f()`` is called somewhere, we will have to
|
||||
remove the attribute:
|
||||
|
||||
.. code-block:: rust
|
||||
|
||||
#[expect(dead_code)]
|
||||
fn f() {}
|
||||
|
||||
If we do not, we get a warning from the compiler::
|
||||
|
||||
warning: this lint expectation is unfulfilled
|
||||
--> x.rs:3:10
|
||||
|
|
||||
3 | #[expect(dead_code)]
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
= note: `#[warn(unfulfilled_lint_expectations)]` on by default
|
||||
|
||||
This means that ``expect``\ s do not get forgotten when they are not needed, which
|
||||
may happen in several situations, e.g.:
|
||||
|
||||
- Temporary attributes added while developing.
|
||||
|
||||
- Improvements in lints in the compiler, Clippy or custom tools which may
|
||||
remove a false positive.
|
||||
|
||||
- When the lint is not needed anymore because it was expected that it would be
|
||||
removed at some point, such as the ``dead_code`` example above.
|
||||
|
||||
It also increases the visibility of the remaining ``allow``\ s and reduces the
|
||||
chance of misapplying one.
|
||||
|
||||
Thus prefer ``expect`` over ``allow`` unless:
|
||||
|
||||
- Conditional compilation triggers the warning in some cases but not others.
|
||||
|
||||
If there are only a few cases where the warning triggers (or does not
|
||||
trigger) compared to the total number of cases, then one may consider using
|
||||
a conditional ``expect`` (i.e. ``cfg_attr(..., expect(...))``). Otherwise,
|
||||
it is likely simpler to just use ``allow``.
|
||||
|
||||
- Inside macros, when the different invocations may create expanded code that
|
||||
triggers the warning in some cases but not in others.
|
||||
|
||||
- When code may trigger a warning for some architectures but not others, such
|
||||
as an ``as`` cast to a C FFI type.
|
||||
|
||||
As a more developed example, consider for instance this program:
|
||||
|
||||
.. code-block:: rust
|
||||
|
||||
fn g() {}
|
||||
|
||||
fn main() {
|
||||
#[cfg(CONFIG_X)]
|
||||
g();
|
||||
}
|
||||
|
||||
Here, function ``g()`` is dead code if ``CONFIG_X`` is not set. Can we use
|
||||
``expect`` here?
|
||||
|
||||
.. code-block:: rust
|
||||
|
||||
#[expect(dead_code)]
|
||||
fn g() {}
|
||||
|
||||
fn main() {
|
||||
#[cfg(CONFIG_X)]
|
||||
g();
|
||||
}
|
||||
|
||||
This would emit a lint if ``CONFIG_X`` is set, since it is not dead code in that
|
||||
configuration. Therefore, in cases like this, we cannot use ``expect`` as-is.
|
||||
|
||||
A simple possibility is using ``allow``:
|
||||
|
||||
.. code-block:: rust
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn g() {}
|
||||
|
||||
fn main() {
|
||||
#[cfg(CONFIG_X)]
|
||||
g();
|
||||
}
|
||||
|
||||
An alternative would be using a conditional ``expect``:
|
||||
|
||||
.. code-block:: rust
|
||||
|
||||
#[cfg_attr(not(CONFIG_X), expect(dead_code))]
|
||||
fn g() {}
|
||||
|
||||
fn main() {
|
||||
#[cfg(CONFIG_X)]
|
||||
g();
|
||||
}
|
||||
|
||||
This would ensure that, if someone introduces another call to ``g()`` somewhere
|
||||
(e.g. unconditionally), then it would be spotted that it is not dead code
|
||||
anymore. However, the ``cfg_attr`` is more complex than a simple ``allow``.
|
||||
|
||||
Therefore, it is likely that it is not worth using conditional ``expect``\ s when
|
||||
more than one or two configurations are involved or when the lint may be
|
||||
triggered due to non-local changes (such as ``dead_code``).
|
||||
|
||||
For more information about diagnostics in Rust, please see:
|
||||
|
||||
https://doc.rust-lang.org/stable/reference/attributes/diagnostics.html
|
||||
|
||||
@@ -87,6 +87,23 @@ they should generally work out of the box, e.g.::
|
||||
zypper install rust rust1.79-src rust-bindgen clang
|
||||
|
||||
|
||||
Ubuntu
|
||||
******
|
||||
|
||||
Ubuntu LTS and non-LTS (interim) releases provide recent Rust releases and thus
|
||||
they should generally work out of the box, e.g.::
|
||||
|
||||
apt install rustc-1.80 rust-1.80-src bindgen-0.65 rustfmt-1.80 rust-1.80-clippy
|
||||
|
||||
``RUST_LIB_SRC`` needs to be set when using the versioned packages, e.g.::
|
||||
|
||||
RUST_LIB_SRC=/usr/src/rustc-$(rustc-1.80 --version | cut -d' ' -f2)/library
|
||||
|
||||
In addition, ``bindgen-0.65`` is available in newer releases (24.04 LTS and
|
||||
24.10), but it may not be available in older ones (20.04 LTS and 22.04 LTS),
|
||||
thus ``bindgen`` may need to be built manually (please see below).
|
||||
|
||||
|
||||
Requirements: Building
|
||||
----------------------
|
||||
|
||||
|
||||
@@ -20368,6 +20368,7 @@ B: https://github.com/Rust-for-Linux/linux/issues
|
||||
C: zulip://rust-for-linux.zulipchat.com
|
||||
P: https://rust-for-linux.com/contributing
|
||||
T: git https://github.com/Rust-for-Linux/linux.git rust-next
|
||||
F: .clippy.toml
|
||||
F: Documentation/rust/
|
||||
F: include/trace/events/rust_sample.h
|
||||
F: rust/
|
||||
@@ -20376,6 +20377,13 @@ F: scripts/*rust*
|
||||
F: tools/testing/selftests/rust/
|
||||
K: \b(?i:rust)\b
|
||||
|
||||
RUST [ALLOC]
|
||||
M: Danilo Krummrich <dakr@kernel.org>
|
||||
L: rust-for-linux@vger.kernel.org
|
||||
S: Maintained
|
||||
F: rust/kernel/alloc.rs
|
||||
F: rust/kernel/alloc/
|
||||
|
||||
RXRPC SOCKETS (AF_RXRPC)
|
||||
M: David Howells <dhowells@redhat.com>
|
||||
M: Marc Dionne <marc.dionne@auristor.com>
|
||||
|
||||
16
Makefile
16
Makefile
@@ -446,18 +446,23 @@ KBUILD_USERLDFLAGS := $(USERLDFLAGS)
|
||||
export rust_common_flags := --edition=2021 \
|
||||
-Zbinary_dep_depinfo=y \
|
||||
-Astable_features \
|
||||
-Dunsafe_op_in_unsafe_fn \
|
||||
-Dnon_ascii_idents \
|
||||
-Dunsafe_op_in_unsafe_fn \
|
||||
-Wmissing_docs \
|
||||
-Wrust_2018_idioms \
|
||||
-Wunreachable_pub \
|
||||
-Wmissing_docs \
|
||||
-Wrustdoc::missing_crate_level_docs \
|
||||
-Wclippy::all \
|
||||
-Wclippy::ignored_unit_patterns \
|
||||
-Wclippy::mut_mut \
|
||||
-Wclippy::needless_bitwise_bool \
|
||||
-Wclippy::needless_continue \
|
||||
-Aclippy::needless_lifetimes \
|
||||
-Wclippy::no_mangle_with_rust_abi \
|
||||
-Wclippy::dbg_macro
|
||||
-Wclippy::undocumented_unsafe_blocks \
|
||||
-Wclippy::unnecessary_safety_comment \
|
||||
-Wclippy::unnecessary_safety_doc \
|
||||
-Wrustdoc::missing_crate_level_docs \
|
||||
-Wrustdoc::unescaped_backticks
|
||||
|
||||
KBUILD_HOSTCFLAGS := $(KBUILD_USERHOSTCFLAGS) $(HOST_LFS_CFLAGS) \
|
||||
$(HOSTCFLAGS) -I $(srctree)/scripts/include
|
||||
@@ -582,6 +587,9 @@ endif
|
||||
# Allows the usage of unstable features in stable compilers.
|
||||
export RUSTC_BOOTSTRAP := 1
|
||||
|
||||
# Allows finding `.clippy.toml` in out-of-srctree builds.
|
||||
export CLIPPY_CONF_DIR := $(srctree)
|
||||
|
||||
export ARCH SRCARCH CONFIG_SHELL BASH HOSTCC KBUILD_HOSTCFLAGS CROSS_COMPILE LD CC HOSTPKG_CONFIG
|
||||
export RUSTC RUSTDOC RUSTFMT RUSTC_OR_CLIPPY_QUIET RUSTC_OR_CLIPPY BINDGEN
|
||||
export HOSTRUSTC KBUILD_HOSTRUSTFLAGS
|
||||
|
||||
@@ -32,7 +32,7 @@ module! {
|
||||
}
|
||||
|
||||
struct NullBlkModule {
|
||||
_disk: Pin<Box<Mutex<GenDisk<NullBlkDevice>>>>,
|
||||
_disk: Pin<KBox<Mutex<GenDisk<NullBlkDevice>>>>,
|
||||
}
|
||||
|
||||
impl kernel::Module for NullBlkModule {
|
||||
@@ -47,7 +47,7 @@ impl kernel::Module for NullBlkModule {
|
||||
.rotational(false)
|
||||
.build(format_args!("rnullb{}", 0), tagset)?;
|
||||
|
||||
let disk = Box::pin_init(new_mutex!(disk, "nullb:disk"), flags::GFP_KERNEL)?;
|
||||
let disk = KBox::pin_init(new_mutex!(disk, "nullb:disk"), flags::GFP_KERNEL)?;
|
||||
|
||||
Ok(Self { _disk: disk })
|
||||
}
|
||||
|
||||
@@ -209,12 +209,9 @@ const FORMAT_INFOS_QR_L: [u16; 8] = [
|
||||
impl Version {
|
||||
/// Returns the smallest QR version than can hold these segments.
|
||||
fn from_segments(segments: &[&Segment<'_>]) -> Option<Version> {
|
||||
for v in (1..=40).map(|k| Version(k)) {
|
||||
if v.max_data() * 8 >= segments.iter().map(|s| s.total_size_bits(v)).sum() {
|
||||
return Some(v);
|
||||
}
|
||||
}
|
||||
None
|
||||
(1..=40)
|
||||
.map(Version)
|
||||
.find(|&v| v.max_data() * 8 >= segments.iter().map(|s| s.total_size_bits(v)).sum())
|
||||
}
|
||||
|
||||
fn width(&self) -> u8 {
|
||||
@@ -242,7 +239,7 @@ impl Version {
|
||||
}
|
||||
|
||||
fn alignment_pattern(&self) -> &'static [u8] {
|
||||
&ALIGNMENT_PATTERNS[self.0 - 1]
|
||||
ALIGNMENT_PATTERNS[self.0 - 1]
|
||||
}
|
||||
|
||||
fn poly(&self) -> &'static [u8] {
|
||||
@@ -479,7 +476,7 @@ struct EncodedMsg<'a> {
|
||||
/// Data to be put in the QR code, with correct segment encoding, padding, and
|
||||
/// Error Code Correction.
|
||||
impl EncodedMsg<'_> {
|
||||
fn new<'a, 'b>(segments: &[&Segment<'b>], data: &'a mut [u8]) -> Option<EncodedMsg<'a>> {
|
||||
fn new<'a>(segments: &[&Segment<'_>], data: &'a mut [u8]) -> Option<EncodedMsg<'a>> {
|
||||
let version = Version::from_segments(segments)?;
|
||||
let ec_size = version.ec_size();
|
||||
let g1_blocks = version.g1_blocks();
|
||||
@@ -492,7 +489,7 @@ impl EncodedMsg<'_> {
|
||||
data.fill(0);
|
||||
|
||||
let mut em = EncodedMsg {
|
||||
data: data,
|
||||
data,
|
||||
ec_size,
|
||||
g1_blocks,
|
||||
g2_blocks,
|
||||
@@ -722,7 +719,10 @@ impl QrImage<'_> {
|
||||
|
||||
fn is_finder(&self, x: u8, y: u8) -> bool {
|
||||
let end = self.width - 8;
|
||||
(x < 8 && y < 8) || (x < 8 && y >= end) || (x >= end && y < 8)
|
||||
#[expect(clippy::nonminimal_bool)]
|
||||
{
|
||||
(x < 8 && y < 8) || (x < 8 && y >= end) || (x >= end && y < 8)
|
||||
}
|
||||
}
|
||||
|
||||
// Alignment pattern: 5x5 squares in a grid.
|
||||
@@ -979,10 +979,11 @@ pub unsafe extern "C" fn drm_panic_qr_generate(
|
||||
/// * `url_len`: Length of the URL.
|
||||
///
|
||||
/// * If `url_len` > 0, remove the 2 segments header/length and also count the
|
||||
/// conversion to numeric segments.
|
||||
/// conversion to numeric segments.
|
||||
/// * If `url_len` = 0, only removes 3 bytes for 1 binary segment.
|
||||
#[no_mangle]
|
||||
pub extern "C" fn drm_panic_qr_max_data_size(version: u8, url_len: usize) -> usize {
|
||||
#[expect(clippy::manual_range_contains)]
|
||||
if version < 1 || version > 40 {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -11,11 +11,12 @@ use kernel::prelude::*;
|
||||
/// drop the vector, and touch it.
|
||||
#[no_mangle]
|
||||
pub extern "C" fn kasan_test_rust_uaf() -> u8 {
|
||||
let mut v: Vec<u8> = Vec::new();
|
||||
let mut v: KVec<u8> = KVec::new();
|
||||
for _ in 0..4096 {
|
||||
v.push(0x42, GFP_KERNEL).unwrap();
|
||||
}
|
||||
let ptr: *mut u8 = addr_of_mut!(v[2048]);
|
||||
drop(v);
|
||||
// SAFETY: Incorrect, on purpose.
|
||||
unsafe { *ptr }
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
# Where to place rustdoc generated documentation
|
||||
rustdoc_output := $(objtree)/Documentation/output/rust/rustdoc
|
||||
|
||||
obj-$(CONFIG_RUST) += core.o compiler_builtins.o
|
||||
obj-$(CONFIG_RUST) += core.o compiler_builtins.o ffi.o
|
||||
always-$(CONFIG_RUST) += exports_core_generated.h
|
||||
|
||||
# Missing prototypes are expected in the helpers since these are exported
|
||||
@@ -15,8 +15,8 @@ always-$(CONFIG_RUST) += libmacros.so
|
||||
no-clean-files += libmacros.so
|
||||
|
||||
always-$(CONFIG_RUST) += bindings/bindings_generated.rs bindings/bindings_helpers_generated.rs
|
||||
obj-$(CONFIG_RUST) += alloc.o bindings.o kernel.o
|
||||
always-$(CONFIG_RUST) += exports_alloc_generated.h exports_helpers_generated.h \
|
||||
obj-$(CONFIG_RUST) += bindings.o kernel.o
|
||||
always-$(CONFIG_RUST) += exports_helpers_generated.h \
|
||||
exports_bindings_generated.h exports_kernel_generated.h
|
||||
|
||||
always-$(CONFIG_RUST) += uapi/uapi_generated.rs
|
||||
@@ -55,15 +55,10 @@ endif
|
||||
core-cfgs = \
|
||||
--cfg no_fp_fmt_parse
|
||||
|
||||
alloc-cfgs = \
|
||||
--cfg no_global_oom_handling \
|
||||
--cfg no_rc \
|
||||
--cfg no_sync
|
||||
|
||||
quiet_cmd_rustdoc = RUSTDOC $(if $(rustdoc_host),H, ) $<
|
||||
cmd_rustdoc = \
|
||||
OBJTREE=$(abspath $(objtree)) \
|
||||
$(RUSTDOC) $(if $(rustdoc_host),$(rust_common_flags),$(rust_flags)) \
|
||||
$(RUSTDOC) $(filter-out $(skip_flags),$(if $(rustdoc_host),$(rust_common_flags),$(rust_flags))) \
|
||||
$(rustc_target_flags) -L$(objtree)/$(obj) \
|
||||
-Zunstable-options --generate-link-to-definition \
|
||||
--output $(rustdoc_output) \
|
||||
@@ -83,7 +78,7 @@ quiet_cmd_rustdoc = RUSTDOC $(if $(rustdoc_host),H, ) $<
|
||||
# command-like flags to solve the issue. Meanwhile, we use the non-custom case
|
||||
# and then retouch the generated files.
|
||||
rustdoc: rustdoc-core rustdoc-macros rustdoc-compiler_builtins \
|
||||
rustdoc-alloc rustdoc-kernel
|
||||
rustdoc-kernel
|
||||
$(Q)cp $(srctree)/Documentation/images/logo.svg $(rustdoc_output)/static.files/
|
||||
$(Q)cp $(srctree)/Documentation/images/COPYING-logo $(rustdoc_output)/static.files/
|
||||
$(Q)find $(rustdoc_output) -name '*.html' -type f -print0 | xargs -0 sed -Ei \
|
||||
@@ -100,6 +95,9 @@ rustdoc-macros: private rustc_target_flags = --crate-type proc-macro \
|
||||
rustdoc-macros: $(src)/macros/lib.rs FORCE
|
||||
+$(call if_changed,rustdoc)
|
||||
|
||||
# Starting with Rust 1.82.0, skipping `-Wrustdoc::unescaped_backticks` should
|
||||
# not be needed -- see https://github.com/rust-lang/rust/pull/128307.
|
||||
rustdoc-core: private skip_flags = -Wrustdoc::unescaped_backticks
|
||||
rustdoc-core: private rustc_target_flags = $(core-cfgs)
|
||||
rustdoc-core: $(RUST_LIB_SRC)/core/src/lib.rs FORCE
|
||||
+$(call if_changed,rustdoc)
|
||||
@@ -107,20 +105,14 @@ rustdoc-core: $(RUST_LIB_SRC)/core/src/lib.rs FORCE
|
||||
rustdoc-compiler_builtins: $(src)/compiler_builtins.rs rustdoc-core FORCE
|
||||
+$(call if_changed,rustdoc)
|
||||
|
||||
# We need to allow `rustdoc::broken_intra_doc_links` because some
|
||||
# `no_global_oom_handling` functions refer to non-`no_global_oom_handling`
|
||||
# functions. Ideally `rustdoc` would have a way to distinguish broken links
|
||||
# due to things that are "configured out" vs. entirely non-existing ones.
|
||||
rustdoc-alloc: private rustc_target_flags = $(alloc-cfgs) \
|
||||
-Arustdoc::broken_intra_doc_links
|
||||
rustdoc-alloc: $(RUST_LIB_SRC)/alloc/src/lib.rs rustdoc-core rustdoc-compiler_builtins FORCE
|
||||
rustdoc-ffi: $(src)/ffi.rs rustdoc-core FORCE
|
||||
+$(call if_changed,rustdoc)
|
||||
|
||||
rustdoc-kernel: private rustc_target_flags = --extern alloc \
|
||||
rustdoc-kernel: private rustc_target_flags = --extern ffi \
|
||||
--extern build_error --extern macros=$(objtree)/$(obj)/libmacros.so \
|
||||
--extern bindings --extern uapi
|
||||
rustdoc-kernel: $(src)/kernel/lib.rs rustdoc-core rustdoc-macros \
|
||||
rustdoc-compiler_builtins rustdoc-alloc $(obj)/libmacros.so \
|
||||
rustdoc-kernel: $(src)/kernel/lib.rs rustdoc-core rustdoc-ffi rustdoc-macros \
|
||||
rustdoc-compiler_builtins $(obj)/libmacros.so \
|
||||
$(obj)/bindings.o FORCE
|
||||
+$(call if_changed,rustdoc)
|
||||
|
||||
@@ -137,19 +129,33 @@ quiet_cmd_rustc_test_library = RUSTC TL $<
|
||||
rusttestlib-build_error: $(src)/build_error.rs FORCE
|
||||
+$(call if_changed,rustc_test_library)
|
||||
|
||||
rusttestlib-ffi: $(src)/ffi.rs FORCE
|
||||
+$(call if_changed,rustc_test_library)
|
||||
|
||||
rusttestlib-macros: private rustc_target_flags = --extern proc_macro
|
||||
rusttestlib-macros: private rustc_test_library_proc = yes
|
||||
rusttestlib-macros: $(src)/macros/lib.rs FORCE
|
||||
+$(call if_changed,rustc_test_library)
|
||||
|
||||
rusttestlib-bindings: $(src)/bindings/lib.rs FORCE
|
||||
rusttestlib-kernel: private rustc_target_flags = --extern ffi \
|
||||
--extern build_error --extern macros \
|
||||
--extern bindings --extern uapi
|
||||
rusttestlib-kernel: $(src)/kernel/lib.rs \
|
||||
rusttestlib-bindings rusttestlib-uapi rusttestlib-build_error \
|
||||
$(obj)/libmacros.so $(obj)/bindings.o FORCE
|
||||
+$(call if_changed,rustc_test_library)
|
||||
|
||||
rusttestlib-uapi: $(src)/uapi/lib.rs FORCE
|
||||
rusttestlib-bindings: private rustc_target_flags = --extern ffi
|
||||
rusttestlib-bindings: $(src)/bindings/lib.rs rusttestlib-ffi FORCE
|
||||
+$(call if_changed,rustc_test_library)
|
||||
|
||||
rusttestlib-uapi: private rustc_target_flags = --extern ffi
|
||||
rusttestlib-uapi: $(src)/uapi/lib.rs rusttestlib-ffi FORCE
|
||||
+$(call if_changed,rustc_test_library)
|
||||
|
||||
quiet_cmd_rustdoc_test = RUSTDOC T $<
|
||||
cmd_rustdoc_test = \
|
||||
RUST_MODFILE=test.rs \
|
||||
OBJTREE=$(abspath $(objtree)) \
|
||||
$(RUSTDOC) --test $(rust_common_flags) \
|
||||
@$(objtree)/include/generated/rustc_cfg \
|
||||
@@ -164,7 +170,7 @@ quiet_cmd_rustdoc_test_kernel = RUSTDOC TK $<
|
||||
mkdir -p $(objtree)/$(obj)/test/doctests/kernel; \
|
||||
OBJTREE=$(abspath $(objtree)) \
|
||||
$(RUSTDOC) --test $(rust_flags) \
|
||||
-L$(objtree)/$(obj) --extern alloc --extern kernel \
|
||||
-L$(objtree)/$(obj) --extern ffi --extern kernel \
|
||||
--extern build_error --extern macros \
|
||||
--extern bindings --extern uapi \
|
||||
--no-run --crate-name kernel -Zunstable-options \
|
||||
@@ -194,19 +200,20 @@ quiet_cmd_rustc_test = RUSTC T $<
|
||||
|
||||
rusttest: rusttest-macros rusttest-kernel
|
||||
|
||||
rusttest-macros: private rustc_target_flags = --extern proc_macro
|
||||
rusttest-macros: private rustc_target_flags = --extern proc_macro \
|
||||
--extern macros --extern kernel
|
||||
rusttest-macros: private rustdoc_test_target_flags = --crate-type proc-macro
|
||||
rusttest-macros: $(src)/macros/lib.rs FORCE
|
||||
rusttest-macros: $(src)/macros/lib.rs \
|
||||
rusttestlib-macros rusttestlib-kernel FORCE
|
||||
+$(call if_changed,rustc_test)
|
||||
+$(call if_changed,rustdoc_test)
|
||||
|
||||
rusttest-kernel: private rustc_target_flags = --extern alloc \
|
||||
rusttest-kernel: private rustc_target_flags = --extern ffi \
|
||||
--extern build_error --extern macros --extern bindings --extern uapi
|
||||
rusttest-kernel: $(src)/kernel/lib.rs \
|
||||
rusttest-kernel: $(src)/kernel/lib.rs rusttestlib-ffi rusttestlib-kernel \
|
||||
rusttestlib-build_error rusttestlib-macros rusttestlib-bindings \
|
||||
rusttestlib-uapi FORCE
|
||||
+$(call if_changed,rustc_test)
|
||||
+$(call if_changed,rustc_test_library)
|
||||
|
||||
ifdef CONFIG_CC_IS_CLANG
|
||||
bindgen_c_flags = $(c_flags)
|
||||
@@ -267,12 +274,16 @@ else
|
||||
bindgen_c_flags_lto = $(bindgen_c_flags)
|
||||
endif
|
||||
|
||||
bindgen_c_flags_final = $(bindgen_c_flags_lto) -D__BINDGEN__
|
||||
# `-fno-builtin` is passed to avoid `bindgen` from using `clang` builtin
|
||||
# prototypes for functions like `memcpy` -- if this flag is not passed,
|
||||
# `bindgen`-generated prototypes use `c_ulong` or `c_uint` depending on
|
||||
# architecture instead of generating `usize`.
|
||||
bindgen_c_flags_final = $(bindgen_c_flags_lto) -fno-builtin -D__BINDGEN__
|
||||
|
||||
quiet_cmd_bindgen = BINDGEN $@
|
||||
cmd_bindgen = \
|
||||
$(BINDGEN) $< $(bindgen_target_flags) \
|
||||
--use-core --with-derive-default --ctypes-prefix core::ffi --no-layout-tests \
|
||||
--use-core --with-derive-default --ctypes-prefix ffi --no-layout-tests \
|
||||
--no-debug '.*' --enable-function-attribute-detection \
|
||||
-o $@ -- $(bindgen_c_flags_final) -DMODULE \
|
||||
$(bindgen_target_cflags) $(bindgen_target_extra)
|
||||
@@ -313,9 +324,6 @@ quiet_cmd_exports = EXPORTS $@
|
||||
$(obj)/exports_core_generated.h: $(obj)/core.o FORCE
|
||||
$(call if_changed,exports)
|
||||
|
||||
$(obj)/exports_alloc_generated.h: $(obj)/alloc.o FORCE
|
||||
$(call if_changed,exports)
|
||||
|
||||
# Even though Rust kernel modules should never use the bindings directly,
|
||||
# symbols from the `bindings` crate and the C helpers need to be exported
|
||||
# because Rust generics and inlined functions may not get their code generated
|
||||
@@ -362,7 +370,7 @@ quiet_cmd_rustc_library = $(if $(skip_clippy),RUSTC,$(RUSTC_OR_CLIPPY_QUIET)) L
|
||||
|
||||
rust-analyzer:
|
||||
$(Q)$(srctree)/scripts/generate_rust_analyzer.py \
|
||||
--cfgs='core=$(core-cfgs)' --cfgs='alloc=$(alloc-cfgs)' \
|
||||
--cfgs='core=$(core-cfgs)' \
|
||||
$(realpath $(srctree)) $(realpath $(objtree)) \
|
||||
$(rustc_sysroot) $(RUST_LIB_SRC) $(KBUILD_EXTMOD) > \
|
||||
$(if $(KBUILD_EXTMOD),$(extmod_prefix),$(objtree))/rust-project.json
|
||||
@@ -400,29 +408,28 @@ $(obj)/compiler_builtins.o: private rustc_objcopy = -w -W '__*'
|
||||
$(obj)/compiler_builtins.o: $(src)/compiler_builtins.rs $(obj)/core.o FORCE
|
||||
+$(call if_changed_rule,rustc_library)
|
||||
|
||||
$(obj)/alloc.o: private skip_clippy = 1
|
||||
$(obj)/alloc.o: private skip_flags = -Wunreachable_pub
|
||||
$(obj)/alloc.o: private rustc_target_flags = $(alloc-cfgs)
|
||||
$(obj)/alloc.o: $(RUST_LIB_SRC)/alloc/src/lib.rs $(obj)/compiler_builtins.o FORCE
|
||||
+$(call if_changed_rule,rustc_library)
|
||||
|
||||
$(obj)/build_error.o: $(src)/build_error.rs $(obj)/compiler_builtins.o FORCE
|
||||
+$(call if_changed_rule,rustc_library)
|
||||
|
||||
$(obj)/ffi.o: $(src)/ffi.rs $(obj)/compiler_builtins.o FORCE
|
||||
+$(call if_changed_rule,rustc_library)
|
||||
|
||||
$(obj)/bindings.o: private rustc_target_flags = --extern ffi
|
||||
$(obj)/bindings.o: $(src)/bindings/lib.rs \
|
||||
$(obj)/compiler_builtins.o \
|
||||
$(obj)/ffi.o \
|
||||
$(obj)/bindings/bindings_generated.rs \
|
||||
$(obj)/bindings/bindings_helpers_generated.rs FORCE
|
||||
+$(call if_changed_rule,rustc_library)
|
||||
|
||||
$(obj)/uapi.o: private rustc_target_flags = --extern ffi
|
||||
$(obj)/uapi.o: $(src)/uapi/lib.rs \
|
||||
$(obj)/compiler_builtins.o \
|
||||
$(obj)/ffi.o \
|
||||
$(obj)/uapi/uapi_generated.rs FORCE
|
||||
+$(call if_changed_rule,rustc_library)
|
||||
|
||||
$(obj)/kernel.o: private rustc_target_flags = --extern alloc \
|
||||
$(obj)/kernel.o: private rustc_target_flags = --extern ffi \
|
||||
--extern build_error --extern macros --extern bindings --extern uapi
|
||||
$(obj)/kernel.o: $(src)/kernel/lib.rs $(obj)/alloc.o $(obj)/build_error.o \
|
||||
$(obj)/kernel.o: $(src)/kernel/lib.rs $(obj)/build_error.o \
|
||||
$(obj)/libmacros.so $(obj)/bindings.o $(obj)/uapi.o FORCE
|
||||
+$(call if_changed_rule,rustc_library)
|
||||
|
||||
|
||||
@@ -1,5 +1,10 @@
|
||||
# SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
# We want to map these types to `isize`/`usize` manually, instead of
|
||||
# define them as `int`/`long` depending on platform bitwidth.
|
||||
--blocklist-type __kernel_s?size_t
|
||||
--blocklist-type __kernel_ptrdiff_t
|
||||
|
||||
--opaque-type xregs_state
|
||||
--opaque-type desc_struct
|
||||
--opaque-type arch_lbr_state
|
||||
|
||||
@@ -40,4 +40,5 @@ const gfp_t RUST_CONST_HELPER_GFP_KERNEL_ACCOUNT = GFP_KERNEL_ACCOUNT;
|
||||
const gfp_t RUST_CONST_HELPER_GFP_NOWAIT = GFP_NOWAIT;
|
||||
const gfp_t RUST_CONST_HELPER___GFP_ZERO = __GFP_ZERO;
|
||||
const gfp_t RUST_CONST_HELPER___GFP_HIGHMEM = ___GFP_HIGHMEM;
|
||||
const gfp_t RUST_CONST_HELPER___GFP_NOWARN = ___GFP_NOWARN;
|
||||
const blk_features_t RUST_CONST_HELPER_BLK_FEAT_ROTATIONAL = BLK_FEAT_ROTATIONAL;
|
||||
|
||||
@@ -25,7 +25,13 @@
|
||||
)]
|
||||
|
||||
#[allow(dead_code)]
|
||||
#[allow(clippy::undocumented_unsafe_blocks)]
|
||||
mod bindings_raw {
|
||||
// Manual definition for blocklisted types.
|
||||
type __kernel_size_t = usize;
|
||||
type __kernel_ssize_t = isize;
|
||||
type __kernel_ptrdiff_t = isize;
|
||||
|
||||
// Use glob import here to expose all helpers.
|
||||
// Symbols defined within the module will take precedence to the glob import.
|
||||
pub use super::bindings_helper::*;
|
||||
|
||||
@@ -3,9 +3,9 @@
|
||||
* A hack to export Rust symbols for loadable modules without having to redo
|
||||
* the entire `include/linux/export.h` logic in Rust.
|
||||
*
|
||||
* This requires the Rust's new/future `v0` mangling scheme because the default
|
||||
* one ("legacy") uses invalid characters for C identifiers (thus we cannot use
|
||||
* the `EXPORT_SYMBOL_*` macros).
|
||||
* This requires Rust's new/future `v0` mangling scheme because the default one
|
||||
* ("legacy") uses invalid characters for C identifiers (thus we cannot use the
|
||||
* `EXPORT_SYMBOL_*` macros).
|
||||
*
|
||||
* All symbols are exported as GPL-only to guarantee no GPL-only feature is
|
||||
* accidentally exposed.
|
||||
@@ -16,7 +16,6 @@
|
||||
#define EXPORT_SYMBOL_RUST_GPL(sym) extern int sym; EXPORT_SYMBOL_GPL(sym)
|
||||
|
||||
#include "exports_core_generated.h"
|
||||
#include "exports_alloc_generated.h"
|
||||
#include "exports_helpers_generated.h"
|
||||
#include "exports_bindings_generated.h"
|
||||
#include "exports_kernel_generated.h"
|
||||
|
||||
13
rust/ffi.rs
Normal file
13
rust/ffi.rs
Normal file
@@ -0,0 +1,13 @@
|
||||
// SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
//! Foreign function interface (FFI) types.
|
||||
//!
|
||||
//! This crate provides mapping from C primitive types to Rust ones.
|
||||
//!
|
||||
//! The Rust [`core`] crate provides [`core::ffi`], which maps integer types to the platform default
|
||||
//! C ABI. The kernel does not use [`core::ffi`], so it can customise the mapping that deviates from
|
||||
//! the platform default.
|
||||
|
||||
#![no_std]
|
||||
|
||||
pub use core::ffi::*;
|
||||
@@ -1,6 +1,5 @@
|
||||
// SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
#include <linux/export.h>
|
||||
#include <linux/errname.h>
|
||||
|
||||
const char *rust_helper_errname(int err)
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
// SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
#include <linux/err.h>
|
||||
#include <linux/export.h>
|
||||
|
||||
__force void *rust_helper_ERR_PTR(long err)
|
||||
{
|
||||
|
||||
@@ -27,5 +27,6 @@
|
||||
#include "spinlock.c"
|
||||
#include "task.c"
|
||||
#include "uaccess.c"
|
||||
#include "vmalloc.c"
|
||||
#include "wait.c"
|
||||
#include "workqueue.c"
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
// SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
#include <kunit/test-bug.h>
|
||||
#include <linux/export.h>
|
||||
|
||||
struct kunit *rust_helper_kunit_get_current_test(void)
|
||||
{
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
// SPDX-License-Identifier: GPL-2.0
|
||||
|
||||
#include <linux/export.h>
|
||||
#include <linux/mutex.h>
|
||||
|
||||
void rust_helper_mutex_lock(struct mutex *lock)
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user