Erro E0554 do Rust: #![feature] may not be used on the stable release channel
O E0554 quer dizer que o seu código começa com uma linha #![feature(...)], e só a versão nightly do Rust aceita essas linhas. Quase sempre ele aparece em código copiado: de um post de blog, de um repositório no GitHub, de uma resposta de IA, de uma resposta antiga no Stack Overflow. Esse código foi escrito para o Rust nightly, e você está no stable, que é o que o rustup instala por padrão. Não tem nada de errado com a sua instalação. A correção costuma ser apagar uma linha e usar um jeito stable de fazer a mesma coisa. Esta página faz parte do guia de erros do compilador.
A mensagem de erro
Seção intitulada “A mensagem de erro”error[E0554]: `#![feature]` may not be used on the stable release channel --> src/main.rs:1:1 |1 | #![feature(iter_map_windows)] // ❌ copied from code written for nightly Rust | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^Em português: “#![feature] não pode ser usado no canal de lançamento stable”.
Este é o programa que gera o erro:
#![feature(iter_map_windows)] // ❌ copied from code written for nightly Rust
fn main() { let temps = [18, 21, 19, 24]; let changes: Vec<i32> = temps.iter().map_windows(|[a, b]| *b - *a).collect(); println!("{:?}", changes);}(O comentário quer dizer “copiado de um código escrito para o Rust nightly”. Ele fica em inglês porque aparece na saída do compilador.)
O que significa
Seção intitulada “O que significa”O ^^^ sublinha a primeira linha inteira, #![feature(iter_map_windows)]. Essa linha é um pedido: “por favor, ative o recurso inacabado chamado iter_map_windows”. Só o compilador nightly aceita esses pedidos. O “stable release channel” (canal de lançamento stable) da mensagem é o Rust normal que você recebe do rustup, e ele recusa.
Repare no que o rustc não reclama: o map_windows na linha 5. Ele para antes, na linha do #![feature]. Quando você tirar essa linha, vai descobrir se o resto do código funciona no stable.
Você recebe o mesmo erro no canal beta. Se o seu código tem várias linhas #![feature], o rustc normalmente só mostra a primeira, então confira o topo do arquivo para ver se há mais.
É como um crachá de “só funcionários”. A cozinha de testes (o nightly) deixa você entrar com ele. O restaurante (o stable) não aceita esse crachá de jeito nenhum, por mais educado que você seja ao mostrá-lo.
Por que o Rust faz isso
Seção intitulada “Por que o Rust faz isso”O Rust promete que o código que compila no stable hoje vai continuar compilando em todas as próximas versões stable 1.x. Recursos inacabados não podem fazer parte dessa promessa: os nomes, os argumentos e o comportamento deles ainda podem mudar, ou eles podem ser removidos. Por isso eles vivem só no nightly, uma nova versão do compilador gerada toda noite, e você ativa cada um pelo nome com #![feature(...)].
O Rust stable não simplesmente ignora a linha: ele para com um erro. Assim você não tem como construir um projeto em cima de um recurso inacabado sem perceber. Quando um recurso fica pronto, ele passa a fazer parte do Rust stable e não precisa mais da linha.
Então, quando você vê o E0554, só existem três perguntas de verdade: existe um jeito stable de fazer isso (Correção 1), o recurso já virou stable (Correção 2), ou você quer mesmo o nightly (Correção 3)? Veja Stable, beta e nightly.
Como corrigir
Seção intitulada “Como corrigir”Correção 1: Remova o atributo e use a API stable
Seção intitulada “Correção 1: Remova o atributo e use a API stable”Escolha esta quase sempre. Apague a linha #![feature] e compile de novo. Se agora aparecer o E0658 (use of unstable library feature `iter_map_windows` , uso de um recurso instável da biblioteca), o recurso ainda está inacabado, e você precisa de um jeito stable de fazer a mesma coisa. A maioria dos métodos instáveis é um atalho para algo que o Rust stable já consegue fazer. Aqui, .windows(2) num slice entrega cada par de vizinhos:
fn main() { let temps = [18, 21, 19, 24]; let changes: Vec<i32> = temps.windows(2).map(|w| w[1] - w[0]).collect(); // ✅ stable println!("{:?}", changes);
for w in temps.windows(2) { println!("{} -> {}", w[0], w[1]); }}Saída:
[3, -2, 5]18 -> 2121 -> 1919 -> 24Para achar o jeito stable, abra o método na documentação da biblioteca padrão. Itens instáveis têm uma caixa que diz “This is a nightly-only experimental API” (esta é uma API experimental só do nightly), e o nome do recurso na sua linha #![feature] normalmente corresponde a uma página do The Unstable Book (em inglês). Veja Slices e Iteradores.
Correção 2: Veja se o recurso já virou stable
Seção intitulada “Correção 2: Veja se o recurso já virou stable”Escolha esta quando o código é um pouco mais antigo. Muitos recursos que antes precisavam de #![feature] hoje fazem parte do Rust stable, e aí a linha simplesmente não é mais necessária. O rustc avisa isso num warning logo abaixo do erro:
error[E0554]: `#![feature]` may not be used on the stable release channel --> src/main.rs:2:1 |2 | #![feature(slice_as_chunks)] // ❌ not needed any more: this feature is stable now | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
warning: the feature `slice_as_chunks` has been stable since 1.88.0 and no longer requires an attribute to enable --> src/main.rs:2:12 |2 | #![feature(slice_as_chunks)] // ❌ not needed any more: this feature is stable now | ^^^^^^^^^^^^^^^O warning diz: “o recurso slice_as_chunks é stable desde a 1.88.0 e não precisa mais de um atributo para ser ativado”.
O programa com erro:
// Copied from an older tutorial#![feature(slice_as_chunks)] // ❌ not needed any more: this feature is stable now
fn main() { let pixels = [255, 0, 0, 0, 128, 255]; let (rgb, _rest) = pixels.as_chunks::<3>(); for [r, g, b] in rgb { println!("r={} g={} b={}", r, g, b); }}(Os comentários querem dizer “copiado de um tutorial mais antigo” e “não é mais necessário: este recurso agora é stable”.)
Apague a linha #![feature] (e o comentário acima dela), e o resto funciona sem mudanças:
fn main() { let pixels = [255, 0, 0, 0, 128, 255]; let (rgb, _rest) = pixels.as_chunks::<3>(); // ✅ stable desde o Rust 1.88 for [r, g, b] in rgb { println!("r={} g={} b={}", r, g, b); }}Saída:
r=255 g=0 b=0r=0 g=128 b=255Para recursos da linguagem, o rustc é ainda mais direto e acrescenta help: remove the attribute (remova o atributo) embaixo do erro, mais uma linha como the feature `async_closure` has been stable since `1.85.0` and no longer requires an attribute to enable.
Não apareceu nenhum warning, mas você desconfia que o recurso já é stable? Talvez o seu Rust seja simplesmente mais antigo do que a versão em que ele ficou stable. Confira e atualize:
rustc --versionrustup updateSe o rustc --version continuar mostrando uma versão antiga depois disso, provavelmente o projeto tem um arquivo rust-toolchain.toml que fixa a versão. Veja Fixando uma toolchain por projeto.
Correção 3: Use o nightly de propósito
Seção intitulada “Correção 3: Use o nightly de propósito”Escolha esta por último, quando não existe um jeito stable e você aceita que o seu código pode quebrar com um nightly futuro. Bons motivos típicos: você está testando um recurso novo, escrevendo um pequeno experimento, ou o projeto em que você contribui já usa nightly. Instale o nightly ao lado do stable e use-o para um único comando:
rustup toolchain install nightlycargo +nightly runOu faça o projeto inteiro usar nightly com um arquivo rust-toolchain.toml ao lado do Cargo.toml. Aí um cargo run simples escolhe o nightly nessa pasta, e o stable em todas as outras:
[toolchain]channel = "nightly"Num projeto que outras pessoas também compilam, fixe uma data, como channel = "nightly-2026-10-01", para que todo mundo use o mesmo compilador. No Rust Playground, escolha Nightly no menu de toolchain.
Talvez você encontre a dica de definir RUSTC_BOOTSTRAP=1 para fazer o stable aceitar #![feature]. Essa opção existe para compilar o próprio compilador do Rust. Usá-la traz todos os riscos do nightly enquanto finge que você está no stable, então não faça isso.
Onde você costuma ver esse erro
Seção intitulada “Onde você costuma ver esse erro”Benchmarks com #[bench]. Guias antigos escrevem benchmarks assim, e #![feature(test)] continua sendo só do nightly:
error[E0554]: `#![feature]` may not be used on the stable release channel --> src/main.rs:3:1 |3 | #![feature(test)] // ❌ built-in benchmarks are nightly-only | ^^^^^^^^^^^^^^^^^//! Price helpers.//! Benchmark written the old way, for nightly Rust.#![feature(test)] // ❌ built-in benchmarks are nightly-onlyextern crate test;
fn total(prices: &[u32]) -> u32 { prices.iter().sum()}
#[bench]fn bench_total(b: &mut test::Bencher) { let prices: Vec<u32> = (1..1000).collect(); b.iter(|| total(&prices));}
fn main() { println!("{}", total(&[3, 4, 5]));}(O comentário quer dizer “os benchmarks embutidos são só do nightly”.)
Correção: use uma crate de benchmarks que funcione no stable, como criterion ou divan, e rode cargo bench. Apagar só a linha #![feature] não basta aqui: aí o extern crate test; dá o E0658 (use of unstable library feature `test` ). Veja Desempenho.
Uma dependência que precisa do nightly. Se a linha --> aponta para uma crate dentro de ~/.cargo/registry/, em vez do seu próprio src/, é uma crate da qual você depende que usa #![feature]. Correção: leia o README da crate; muitas vezes uma versão mais nova funciona no stable (por exemplo, o framework web Rocket precisava do nightly até a 0.4, e a 0.5 roda no stable). Se não, escolha outra crate. Veja Cargo e crates.
Código copiado com #![feature(let_chains)]. As let chains (if let Some(x) = a && x > 0) ficaram stable no Rust 1.88, mas só na edição 2024. Correção: apague a linha (Correção 2) e coloque edition = "2024" no Cargo.toml. Sem isso, você recebe let chains are only allowed in Rust 2024 or later (let chains só são permitidas no Rust 2024 ou posterior).
Erros relacionados
Seção intitulada “Erros relacionados”- E0658: use of unstable feature: o que você normalmente recebe depois de tirar a linha
#![feature], se o recurso ainda é só do nightly. - E0599: no method found: se você tira a linha e o método realmente não existe, ou vem de uma crate que você não adicionou.
- E0463: can’t find crate: se você troca para
criterionoudivane esquece de adicioná-la aoCargo.toml. - E0435: attempt to use a non-constant value in a constant: um motivo comum para as pessoas irem atrás de recursos constantes do nightly, para começo de conversa.
- Todos os erros do compilador: a lista completa de páginas de erro.
Teste o que aprendeu
Seção intitulada “Teste o que aprendeu”Teste o que aprendeu
1. Você cola um código que começa com #![feature(try_blocks)] e recebe o E0554. O que isso quer dizer?
2. Embaixo do erro, o rustc avisa que o recurso é stable desde a 1.88.0. O que você deve fazer?
3. Você quer mesmo o nightly para um experimento. Qual é o jeito mais limpo?
Pontuação: 0 / 3
Para saber mais
Seção intitulada “Para saber mais”- E0554 — Rust error codes index (em inglês): a explicação oficial: atributos de recurso só são permitidos no canal nightly.
- How Rust is Made and “Nightly Rust” — The Rust Book (em inglês): os canais stable, beta e nightly, e como um recurso passa do nightly para o stable.
- Channels — The rustup book (em inglês): como instalar o nightly e usá-lo ao lado do stable.
- The toolchain file — The rustup book (em inglês): como o
rust-toolchain.tomlescolhe o compilador de um projeto, incluindo um nightly com data fixa. - The Unstable Book (em inglês): todos os nomes de recursos que você pode colocar em
#![feature], com um link para a issue de acompanhamento de cada um.