#prog #rust хайлайты:
▪️Несколько изменений, связанных с гарантиями языка:
🔸char имеет одинаковый с u32 размер и выравнивание
🔸null-указатель имеет нулевой адрес. Насколько я понимаю, у разработчиков Rust нет планов поддерживать платформы, где это не так.
🔸касты между разнымии типами сырых указателей на слайсы (и содержащими их DST) сохраняют число элементов в части метаданных жирных указателей
🔸для некоторых типов гарантируется, что transmute от нулевых байт в Option от этого типа легален и даёт None.
▪️Следующие операции теперь доступны к const-контексте:
🔸std::mem::discriminant
🔸BinaryHeap::{new, new_in}
🔸Операции для байтовых смещений указателей (и в принципе стабилизированы)
🔸std::mem::zeroed и MaybeUninit::zeroed
▪️Парсер теперь избегает патологического квадратичного поведения на больших последовательностях непарных угловых скобок (до фикса подобный код приводил к OOM).
▪️Реализации
▪️Компилятор теперь замечает, когда на значении вызывается метод трейта, реализованный для его типа, и предлагает импортировать трейт вместо того, чтобы предложить его реализовать.
▪️Компилятор теперь корректно отлавливает ситуации, когда тип становится слишком большим из-за паддинга
▪️При
▪️При невозможности создания трейт-объекта из трейта компилятор теперь предлагает использовать enum, если число типов, реализовывающих трейт, невелико (и предлагает использовать тип напрямую, если всего один тип реализует трейт).
▪️Компилятор при попытке сделать биндинг на unsized значение теперь жалуется только на let вместо всех мест, где используется этот биндинг.
▪️Компилятор на попытку сконструировать кортежную структуру с приватными полями теперь предлагает вызвать конструктор (при его наличии). Фиксит issue от 2015 года!
К сожалению, сейчас сделано довольно костыльно, но нормальный фикс затруднителен.
▪️Компилятор теперь диагностирует некоторые случаи, когда у лямбды забыты аргументные скобки или они выставлены неверно.
▪️Стабилизирован инлайн-ассемблер с бекендом cranelift.
▪️Компилятор восстанавливается на коде вида
▪️Стабилизированы API для манипуляции с временными отметками файлов.
▪️
▪️Несколько изменений, связанных с гарантиями языка:
🔸char имеет одинаковый с u32 размер и выравнивание
🔸null-указатель имеет нулевой адрес. Насколько я понимаю, у разработчиков Rust нет планов поддерживать платформы, где это не так.
🔸касты между разнымии типами сырых указателей на слайсы (и содержащими их DST) сохраняют число элементов в части метаданных жирных указателей
🔸для некоторых типов гарантируется, что transmute от нулевых байт в Option от этого типа легален и даёт None.
▪️Следующие операции теперь доступны к const-контексте:
🔸std::mem::discriminant
🔸BinaryHeap::{new, new_in}
🔸Операции для байтовых смещений указателей (и в принципе стабилизированы)
🔸std::mem::zeroed и MaybeUninit::zeroed
▪️Парсер теперь избегает патологического квадратичного поведения на больших последовательностях непарных угловых скобок (до фикса подобный код приводил к OOM).
▪️Реализации
Ord
, PartialOrd
и Hash
для SocketAddr{V4, V6} теперь дерайвятся, а не написаны вручную. До этого изменения реализация PartialEq
для SocketAddrV6
, как и всякий дерайв, сравнивала все поля, включая flowinfo
и scope_id
, а вот реализации трейтов для упорядочивания эти поля игнорировали. По какому-то недоразумению этот баг просуществовал 28 версий!▪️Компилятор теперь замечает, когда на значении вызывается метод трейта, реализованный для его типа, и предлагает импортировать трейт вместо того, чтобы предложить его реализовать.
▪️Компилятор теперь корректно отлавливает ситуации, когда тип становится слишком большим из-за паддинга
▪️При
panic_immediate_abort
теперь меньше втягивается связанного с паникой кода.▪️При невозможности создания трейт-объекта из трейта компилятор теперь предлагает использовать enum, если число типов, реализовывающих трейт, невелико (и предлагает использовать тип напрямую, если всего один тип реализует трейт).
▪️Компилятор при попытке сделать биндинг на unsized значение теперь жалуется только на let вместо всех мест, где используется этот биндинг.
▪️Компилятор на попытку сконструировать кортежную структуру с приватными полями теперь предлагает вызвать конструктор (при его наличии). Фиксит issue от 2015 года!
К сожалению, сейчас сделано довольно костыльно, но нормальный фикс затруднителен.
▪️Компилятор теперь диагностирует некоторые случаи, когда у лямбды забыты аргументные скобки или они выставлены неверно.
▪️Стабилизирован инлайн-ассемблер с бекендом cranelift.
▪️Компилятор восстанавливается на коде вида
S { ref field: name }
и предлагает переписать на правильный S { field: ref name }
.▪️Стабилизированы API для манипуляции с временными отметками файлов.
▪️
offset_of!
теперь поддерживает поля внутри вариантов enum.GitHub
Guarantee that `char` has the same size and alignment as `u32` by joshlf · Pull Request #116894 · rust-lang/rust
Empowering everyone to build reliable and efficient software. - Guarantee that `char` has the same size and alignment as `u32` by joshlf · Pull Request #116894 · rust-lang/rust
🎉15👍5🔥1🤔1
#prog #article
LSP could have been better — Кладов рассказывает о технических аспектах LSP (как понятно из заголовка, не всегда хороших)
LSP could have been better — Кладов рассказывает о технических аспектах LSP (как понятно из заголовка, не всегда хороших)
matklad.github.io
LSP could have been better
We talk about programming like it is about writing code, but the code ends up being less important
than the architecture, and the architecture ends up being less important than social issues.
than the architecture, and the architecture ends up being less important than social issues.
👍4
#prog #amazingopensource
ast-grep — инструмент для структурного поиска и замены с паттернами не на уровне текста, а на уровне синтаксических деревьев.
Построен поверх tree-sitter, поэтому охват языков, корректность и произодительность на уровне.
Поддерживает интерактивный режим, который позволяет проверить все места, где применяется правило, перед совершением реальной замены.
Поддерживает предзаписанные правила (в YAML 😒), с возможностью вынесения в отдельные файлы общих определений.
Может быть использован как линтер, для поиска паттернов, но без замены.
ast-grep — инструмент для структурного поиска и замены с паттернами не на уровне текста, а на уровне синтаксических деревьев.
Построен поверх tree-sitter, поэтому охват языков, корректность и произодительность на уровне.
Поддерживает интерактивный режим, который позволяет проверить все места, где применяется правило, перед совершением реальной замены.
Поддерживает предзаписанные правила (в YAML 😒), с возможностью вынесения в отдельные файлы общих определений.
Может быть использован как линтер, для поиска паттернов, но без замены.
GitHub
GitHub - ast-grep/ast-grep: ⚡A CLI tool for code structural search, lint and rewriting. Written in Rust
⚡A CLI tool for code structural search, lint and rewriting. Written in Rust - ast-grep/ast-grep
👍11🔥3
#prog #rust #rustasync
Хозяйке на заметку
(или "Антон читает за вас документацию tokio")
1. Если вам требуется заспавнить несколько тасок с одинаковыми типами возврата, в количестве, известном только в рантайме, и дождаться результата исполнения каждой из них или только некоторых, то в tokio есть для этого готовый примитив: JoinSet.
Базовый пример использования:
Также можно отменить скопом все таски в наборе через abort_all. Также можно переиспользовать JoinSet, используя detach_all. Это уберёт все таски из
2. Если у нас есть несколько тасок, которые отсылают результаты своей работы через канал, и мы хотим ограничить число одновременно исполняемых тасок, то это можно сделать при помощи канала ограниченной ёмкости и API, описанного в статье Mutex without lock, Queue without push: cancel safety in lilos (о которой я уже рассказывал):
И надо предупредить (хотя навряд ли вы в такое вляпаетесь намеренно): очевидно, если Permit-ов утечёт достаточно много, вы можете оказаться в дурацкой ситуации, когда в канале есть место, но он не работает ни за отправку, ни на получение.
Хозяйке на заметку
(или "Антон читает за вас документацию tokio")
1. Если вам требуется заспавнить несколько тасок с одинаковыми типами возврата, в количестве, известном только в рантайме, и дождаться результата исполнения каждой из них или только некоторых, то в tokio есть для этого готовый примитив: JoinSet.
Базовый пример использования:
use tokio::task::JoinSet;
#[tokio::main]
async fn main() {
let mut set = JoinSet::new();
for i in 0..10 {
// таски спавнятся при помощи spawn, поэтому
// семантика та же: сразу начинают выполняться
// и паникует вне асинхронного контекста tokio
set.spawn(async move { i });
}
let mut seen = [false; 10];
// мы не обязаны получать все таски до конца
while let Some(res) = set.join_next().await {
let idx = res.unwrap();
seen[idx] = true;
}
for i in 0..10 {
assert!(seen[i]);
}
}
Также можно отменить скопом все таски в наборе через abort_all. Также можно переиспользовать JoinSet, используя detach_all. Это уберёт все таски из
JoinSet
, но они продолжат исполняться рантаймом.2. Если у нас есть несколько тасок, которые отсылают результаты своей работы через канал, и мы хотим ограничить число одновременно исполняемых тасок, то это можно сделать при помощи канала ограниченной ёмкости и API, описанного в статье Mutex without lock, Queue without push: cancel safety in lilos (о которой я уже рассказывал):
let (tx, mut rx) = tokio::sync::mpsc::channel(limit);
for _ in 0..n_tasks {
let work = async {
// какая-то полезная работа
};
let tx = tx.clone();
let task = async move {
let send_permit = tx.reserve_owned().unwrap();
let result = work.await;
let _ = send_permit.send(result);
};
tokio::spawn(task);
}
// дропаем свою копию Sender-а, чтобы не заблокироваться
// на чтении из канала, в который никто не пишет
drop(tx);
while let Some(res) = rx.recv().await {
// обрабатываем результат
}
И надо предупредить (хотя навряд ли вы в такое вляпаетесь намеренно): очевидно, если Permit-ов утечёт достаточно много, вы можете оказаться в дурацкой ситуации, когда в канале есть место, но он не работает ни за отправку, ни на получение.
docs.rs
JoinSet in tokio::task - Rust
A collection of tasks spawned on a Tokio runtime.
👍3
#prog #rust #itsec #article
sudo-rs' first security audit
> Запросили аудит sudo-rs
> Нашли уязвимость в дизайне, которая есть и в оригинальном sudo
sudo-rs' first security audit
> Запросили аудит sudo-rs
> Нашли уязвимость в дизайне, которая есть и в оригинальном sudo
Ferrous-Systems
sudo-rs' first security audit
Thanks to funding from NLNet and ISRG,
the sudo-rs team was able to request an audit from Radically Open Security (ROS).
In this post, we'll share the findings of the audit and our response to those findings.
ROS performed crystal-box penetration...
the sudo-rs team was able to request an audit from Radically Open Security (ROS).
In this post, we'll share the findings of the audit and our response to those findings.
ROS performed crystal-box penetration...
👍16😁12🤯4
#prog #rust #article
Destructing trees safely and cheaply
О том, как дропать глубоко вложенные рекурсивные типы без переполнения стека.
Destructing trees safely and cheaply
О том, как дропать глубоко вложенные рекурсивные типы без переполнения стека.
ismailmaj.github.io
Destructing trees safely and cheaply
👍5
Forwarded from ☕️ Мерлин заваривает τσάι 🐌
Примерно через 3 часа UNIX timestamp достигнет красивой отметки 1700000000
https://www.epochconverter.com/countdown?q=1700000000
https://www.epochconverter.com/countdown?q=1700000000
❤11🔥9🎉6
#prog #rust #article
How I Improved My Rust Compile Times by 75%*
*с инкрементальной сборкой
TL;DR: инкрементальная сборка выигрывает от использования более быстрого линкера (mold для Linux/sold для Macos) и бекенда Cranelift.
How I Improved My Rust Compile Times by 75%*
*с инкрементальной сборкой
TL;DR: инкрементальная сборка выигрывает от использования более быстрого линкера (mold для Linux/sold для Macos) и бекенда Cranelift.
benw.is
How I Improved My Rust Compile Times by 75%
One of Rust's often mentioned pain points is slow compile times. In order to have nice things like the borrow checker, safety guarantees, and zero cost abstractions, we pay in time spent compiling. I was able to decrease that time by 75%.
👍4🔥2