Unable to compile Rust with no_std/lang_items

点点圈 提交于 2021-01-27 23:26:30

问题


I am attempting to set up a project very similar to dueboot. That is, Rust on embedded ARM. Right now, I'm only up to the point of compiling the Rust code, but I can't get it to compile.

I've basically copied the rust code exactly from that project, but I don't fully understand the lang_items feature.

#![feature(asm)]
#![feature(lang_items)]
#![feature(no_std)]

#![no_std]

use arduino::{init, delay, pinMode, digitalWrite, analogWrite, LOW, HIGH, OUTPUT};
mod arduino;

#[lang="sized"]
trait Sized {}

#[lang="copy"]
trait Copy {}

#[lang="sync"]
trait Sync {}

static PWM:u32 = 2;
static LED:u32 = 11;

#[no_mangle]
pub fn main() {
  // ...
}

Attempting to compile the code as above, results in this error:

main.rs:11:1: 11:15 error: parameter `Self` is never used
main.rs:11 trait Sized {}
           ^~~~~~~~~~~~~~
main.rs:14:1: 14:14 error: parameter `Self` is never used
main.rs:14 trait Copy {}
           ^~~~~~~~~~~~~
main.rs:17:1: 17:14 error: parameter `Self` is never used
main.rs:17 trait Sync {}
           ^~~~~~~~~~~~~
error: aborting due to 3 previous errors

I also attempted to comment out all of the lines relating to the lang_items, including the feature line at the top. This is the resulting error message:

// more lines of the same message
error: requires `sized` lang_item
error: requires `sized` lang_item
error: requires `sized` lang_item
error: requires `sized` lang_item
error: requires `sized` lang_item
error: aborting due to 54 previous errors

I'm using rust built from master, as of yesterday.

Any suggestions?


回答1:


A few days ago, Rust added the rule that all type parameters must appear in the methods of the trait (RFC 738). But since Sized (and Copy and Sync) doesn't have any methods of its own, it breaks this rule by default.

The official workaround is to mark the trait as PhantomFn, which silences the error:

#![feature(asm)]
#![feature(lang_items)]
#![feature(no_std)]

#![no_std]

use arduino::{init, delay, pinMode, digitalWrite, analogWrite, LOW, HIGH, OUTPUT};
mod arduino;

// Copied from <http://doc.rust-lang.org/core/marker/trait.PhantomFn.html>
#[lang="phantom_fn"]
trait PhantomFn<A: ?Sized, R: ?Sized = ()> {}

#[lang="sized"]
trait Sized: PhantomFn<Self> {}

#[lang="copy"]
trait Copy: PhantomFn<Self> {}

#[lang="sync"]
trait Sync: PhantomFn<Self> {}

static PWM:u32 = 2;
static LED:u32 = 11;

#[no_mangle]
pub fn main() {
  // ...
}

This change should make the code compile again.

Addendum: What are lang items?

A lang item is a symbol that's marked as "special" to the compiler. Some examples are:

  • The heap allocator

  • Procedures for unwinding on panic

  • Types and traits that ensure type safety, like Send and Drop and PhantomData

  • Traits for operator overloading, like Add and Eq and Deref

You can find a list of them in lang_items.rs.

These items are critical to the semantics of the language, but are impractical to implement in the compiler itself. So we put them in the standard library instead, with special annotations that tell the compiler where they are.

Now, while you can define these items itself, it's recommended to link to core instead, which declares these lang items for you. But I'm not sure how well that would work with your setup.



来源:https://stackoverflow.com/questions/28649120/unable-to-compile-rust-with-no-std-lang-items

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!