LINUX.ORG.RU

Драйвера на руст

 , ,


2

10

http://www.opennet.ru/opennews/art.shtml?num=51475
Ну что, си можно выбрасывать на помойку? Или нет?
Ъ:соревнования по написанию сетевых драйверов на разных яп. У rust и си +- одинаковая производительность на картинке.
Ссылки на сорцы тут в README.md => https://github.com/ixy-languages/ixy-languages

★★★★★

Последнее исправление: crutch_master (всего исправлений: 4)
Ответ на: комментарий от anonymous

Уровень аналитики зашкаливает

Deleted
()
Ответ на: комментарий от anonymous

Сравниваешь жопу с пальцем? Давай сюда кагбэ «читаемых» C/C++ макросов если уже такой упоротый :)

P.S. Макросы - они почти везде выглядят как говно, это известный факт.

htower_ ★★
()
Ответ на: комментарий от WitcherGeralt

Ну в го секрет производительности один. Allocate заранее, не создавай мусор и будет рабоать плюс-минус как С.

Пример тому библиотека fasthttp на Go. На бенчах веб-фреймворков и библиотек годами заруливает все, С, С++, Rust. Они там толкаются обгоняя друг друга на 1% на верхушке, намекая что это просто пик возможностей железа.

Причем все что написано идиоматично на Go пасет задних

vertexua ★★★★★
()
Ответ на: комментарий от WitcherGeralt

Потому что открываются возможности вроде «машин времени» на UI. Когда код принципиально не сложный, в один поток в цикле обработки сообщений, но просто в нем 10 уровней наслоений из-за сложностей UI, то ФП не удобнее другого ФП в другом месте, ФП удобнее императивщины.

vertexua ★★★★★
()
Ответ на: комментарий от Deleted

Ну не создавай/забывай обьекты в цикле. Создай на начале работы приложения и с ними крутись как можешь.

https://github.com/valyala/fasthttp#fasthttp-best-practices

vertexua ★★★★★
()
Последнее исправление: vertexua (всего исправлений: 3)

Я не понимаю, на какой ОС тестировали? Для Linux разве не только на C можно писать kernel-драйверы, так как ядро Linux монолитное?

te111011010
()
Ответ на: комментарий от snake266

Это какая-то обёртка, которая позволяет пускать rust-код в kernel-space? А она универсальная, или только для конкретных подсистем?

te111011010
()

Ну что, си можно выбрасывать на помойку? Или нет?

Сначала перепишите всё ядро Linux, которое сейчас в кажом утюге, на Rust, потом будем говорить.

te111011010
()
Ответ на: комментарий от te111011010

Я, если честно, в кернелах и модулях не шарю, но ссылку на репу дать могу: https://github.com/fishinabarrel/linux-kernel-module-rust

А тут презентация к этому проекту: https://ldpreload.com/p/kernel-modules-in-rust-lssna2019.pdf

Но походу, это просто биндинги

snake266 ★★★
()
Ответ на: комментарий от te111011010

Модули ядра потенциально можно писать на любом языке, хоть на Perl.

Вопрос только в фреймворке, который будет предоставлять API на языке, который тебе нужен.

Deleted
()
Ответ на: комментарий от vertexua

Разве это недостаток Go? Ведь и malloc в C/C++/... не волшебный, а затратный, да ещё приводящий к фрагментации памяти. Иначе бы не было разных malloc-реализаций и memory pool'ов. И в ядре пользуются этим правилом.

Недавно появилась malloc-библиотека, которая борется с фрагментацией: Mesh.

gag ★★★★★
()
Ответ на: комментарий от WitcherGeralt

Гошечка вот удивила... Шарп впечатлил

WitcherGeralt

Бессмысленное сравнение.

Partisan

Очень хорошее сравнение. Возможно, у тех кто посмотрит и увидит Go и C# в топе, после этого пропадёт боязнь GC. А то до сих пор, в 2019, множество людей боится сборки мусора как огня, хотя нужно было забыть про это суеверие после просмотра первых тестов языка D, который тоже быстрый и тоже с GC.

А то для многих GC === Javascript или Java.

fsb4000 ★★★★★
()
Ответ на: комментарий от vertexua

Пример тому библиотека fasthttp на Go

Она быстрая только в бенчмарках, на практике у тебя будут аллокации, а производительность отдельных запросов ещё и ниже чем с дефолтной net/http.

WitcherGeralt ★★
()
Ответ на: комментарий от Legioner

И на горизонте не видно, даже модерновая фухсия на C.

Она на C++.

EXL ★★★★★
()
Ответ на: комментарий от anonymous

Как можно этого не понять? Ты вообще программист?

Нет, он форумный клоун - фрактал. Не обижай его.

anonymous
()
Ответ на: комментарий от EXL

Я видел бенчмарк, причем тут он? Не ясно к чему утвердженние что на бенчах одно, а потом когда пойдет реальная нагрузка, то железно мамкой клянусь будет дуже чем стандарная реализация

vertexua ★★★★★
()
Ответ на: комментарий от vertexua

Из личной практики, но я сходу не могу придумать как бы те проблемы, с которыми столкнулся, можно было бы получить в регулярном продуктовом коде, так что не будем об этом. Скажу лишь, что часть задач, которые решает net/http, в случае с fasthttp ты будешь решать сам (банально попарсить QUERY_STRING хотя бы), с помощью той же net/http, например.

Послушай лучше доклад от самого автора про грехи оптимизации: https://youtu.be/ewmUUC1rF280

WitcherGeralt ★★
()

У rust и си +- одинаковая производительность на картинке

Меня больше шарп удивил. Интересно, а на F# это можно экстраполировать?

no-such-file ★★★★★
()

Т.е. если хочешь быстро и с нормальным синтаксисом, то выбирай C#. Я так и думал.

ox55ff ★★★★★
()

Раст придуман инопланетянинами с планеты Нибиру, чтобы дисстабилизировать IT на Земле.

snake266 ★★★
()

в кернеле же нет сборщика мусора для тупых и прочих подгузников. ржавчина как была ненужна, так и остаётся.

Iron_Bug ★★★★★
()
Ответ на: комментарий от snake266

Раст придуман билгейтсом, чтобы кодеры в ужасе убегали на гуманный, но столь же шустрый C#. Гет зе факс!

bread
()
Ответ на: комментарий от Deleted

Эх, вот на нетке встроили lua engine в ядро. Причем, емнип, это портанули проект lunatik для линукса. Совсем другой подход. Почему не взлетел - хз. Поглядим как в нетке пойдёт, оправдано ли это.

Сейчас через биндинги все слишком через жопу. Опять же, поглядим на нетку.

Deleted
()
Ответ на: комментарий от vertexua

Че ему сливать если они с С на одном LLVM?

swift тоже на LLVM...

fsb4000 ★★★★★
()
Ответ на: комментарий от vertexua

код Glib/Gtk
На каждом входе в функцию проверочка на NULL для всех параметров

Ну давай, перепиши это на хескель, и я посмотрю как ты будешь создавать привязки для питонов всяких.

Deleted
()
Ответ на: комментарий от vertexua

Насчет дурацких вещей. В С популярен defensive programming, посмотри на код Glib/Gtk.

ну точно сектант - как сравнивать так драйверы, а как оправдываться - glib/gtk. В ядре Linux не проверяют на 0 если явно известно что 0 там не будет, не делают и другие бесполезные проверки с заранее известным результатом. На расте ты так не сможешь.

anonymous
()
Ответ на: комментарий от mersinvald

да без разницы, какие там анальные огораживания для потенциальных говнокодеров добавлены. в кернеле их нет. стало быть, получился аналог самой обычной сишечки. а написать аналог сишечки через 40 с гаком лет, да ещё и на чужом компиляторе - это прямо-таки премия лучшего слоупока напрашивается. в общем, двойное ненужно.

Iron_Bug ★★★★★
()
Ответ на: комментарий от WitcherGeralt

Не удивительно, что быстрее, в c# они всунули unsafe с ассемблерными вставками, а в java вкрутили jni (который сам по себе тормоз), большинство переменных сделали volatile (даже там, где это не нужно, чем убили оптимизации jit-а), и для каждого объекта аллоцируют память по 20кб каждый раз. В итоге для java замерили работу сборщика мусора. Молодцы, что. :-)

ma1uta ★★★
()
Ответ на: комментарий от Iron_Bug

Я вот никак не пойму почему С программисты мирятся с анальным огораживанием в офисах. Перила: нужно обходить, без них можно повернуть на две-четыре ступеньки раньше. Двери в лифтах: убрал двери, надел хорошие перчатки и спустился по тросам, огромная оптимизация времени. Скрытая проводка: на открытой проводке подцепился в любом месте, замотал скотчем, никакой возни с розетками и удлинителями.

Просто будь внимателен и профессионален и ничего страшного не случится. Ну и давать подписать на входе бумажку:

THE BUILDING IS PROVIDED «AS IS», WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF SAFEFY MEASURES, FITNESS FOR A PARTICULAR PURPOSE AND NONSLIPPERINESS. IN NO EVENT SHALL THE BUILDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE BUILDING OR THE USE OR OTHER DEALINGS IN THE BUILDING.

red75prim ★★★
()

Окей, сравниваем реализацию на С и на Расте для одной случайной функции vfio_enable_dma:

C: https://github.com/emmericp/ixy/blob/master/src/libixy-vfio.c#L27

Rust: https://github.com/ixy-languages/ixy.rs/blob/master/src/vfio.rs#L170

C - 13 строк, читается легко и приятно, Rust - 57 строк, 6 ансейфов, читается как говно.

Где больше шанс допустить ошибку? Стоит оно того? Раст неплохая штука, но ему тут явно не место.

ncuxer
()
Ответ на: комментарий от red75prim

Я вот никак не пойму почему С программисты мирятся с анальным огораживанием в офисах.

ты думаешь что очень оригинальный и код без ошибок пишешь ? На деле просто сравниваешь несравнимое. Напиши хоть один драйвер и может поймешь какой ты тупняк несёшь.

anonymous
()
Ответ на: комментарий от ncuxer

6 ансейфов

После каждого unsafe идёт вызов чего-то из libc. Для вас новость, что для использования сишных либ нужен unsafe? Если запилят фрэймворк для написания драйвером – не будет unsafe(во всяком случае в таких целях как тут).

C - 13 строк

А ну если небольшое количество строк улучшает ПО, то почему не записать в одну? И кстати, разве вызов функций внутри assert не считается плохой практикой?

andalevor ★★★
()
Ответ на: комментарий от ncuxer

А в чём проблема с 5-ю ансейфами? Можно сделать один большой на функцию, но лучше не от этого не будет. Unsafe обращает внимание на места, где легко всё сломать: например, поставим 4 вместо 2-х в pread, получим UB.

Хм… У них там и так UB, ioctl пишет в константный conf_reg. Видимо не было опыта работы с ioctl. Вот поэтому unsafe и полезен - нет опыта, пиши без unsafe. И это легко проверить грепом.

Код длинный, да. В основном потому, что с биндингами не заморачивались, всё на голом libc. С safe обёртками это выглядело бы как-то так:

pub fn vfio_enable_dma(device: &mut File) -> Result<(), Box<dyn Error>> {
    // Get region info for config region
    let conf_reg = unsafe { vfio_device_get_region_info(device, VFIO_PCI_CONFIG_REGION_INDEX)? };
    let command_register_offset = (conf_reg.offset + COMMAND_REGISTER_OFFSET) as i64;
    let mut dma = device.pread_u16(command_register_offset)?;
    dma |= 1 << BUS_MASTER_ENABLE_BIT;
    device.pwrite_u16(command_register_offset, dma)?;
    Ok(())
}

red75prim ★★★
()
Последнее исправление: red75prim (всего исправлений: 1)
Ответ на: комментарий от red75prim

С safe обёртками это выглядело бы как-то так:

а в драйвере ядра так

pci_set_master(pci_dev);

anonymous
()
Ответ на: комментарий от andalevor

То есть для разработки там, где нужен си, нужно использовать си, а не костылять. Вот когда запилят фреймворк на расте, тогда и можно сравнивать.

Разница между assert'ом и просто вызовом return с варнингом огромная. Если программист посчитал, что в данном месте нужен ассерт, значит так оно и надо. Плохая практика это писать варнинг, где должен быть ассерт.

ncuxer
()
Ответ на: комментарий от red75prim

даже без биндингов достаточно заменить ошибки ассертами, как в коде на Си, и написать #[derive(Default)] для vfio_region_info. Получится что-то такое:

pub fn vfio_enable_dma(device_fd: RawFd) -> Result<(), Box<dyn Error>> {
    let mut conf_reg = vfio_region_info::default(); 
    conf_reg.argsz = mem::size_of::<vfio_region_info>() as u32;
    conf_reg.index = VFIO_PCI_CONFIG_REGION_INDEX;
    if unsafe { libc::ioctl(device_fd, VFIO_DEVICE_GET_REGION_INFO, &conf_reg) } == -1 {
        return Err(format!(
            "failed to VFIO_DEVICE_GET_REGION_INFO for index VFIO_PCI_CONFIG_REGION_INDEX. Errno: {}",
            unsafe { *libc::__errno_location() }
        ).into());
    }
    let mut dma: u16 = 0;
    
    use std::mem::transmute;
    assert_ne!(unsafe {
        libc::pread(device_fd, transmute(&mut dma), 2, (conf_reg.offset + COMMAND_REGISTER_OFFSET) as i64)
    }, -1);
    dma |= 1 << BUS_MASTER_ENABLE_BIT;
    assert_ne!(unsafe {
        libc::pwrite(device_fd, transmute(&mut dma), 2, (conf_reg.offset + COMMAND_REGISTER_OFFSET) as i64)
    }, -1);
    Ok(())
}
от кода на Си это отличается макросом check_err, unsafe и явным приведением типов. Но хейтеру выше конечно плевать на такие тонкости

anonymous
()
Ответ на: комментарий от ncuxer

То есть для разработки там, где нужен си, нужно использовать си, а не костылять. Вот когда запилят фреймворк на расте, тогда и можно сравнивать.

Т.е. для небольшого сравнения возможности написания драйвера в userspace надо написать по фреймворку для каждого языка (Rust, Go, C#, Java, JavaScript, Swift, Python)?

andalevor ★★★
()
Ответ на: комментарий от ncuxer

Вот когда запилят фреймворк на расте, тогда и можно сравнивать.

Более того тут пишут:

I have, yes. I spoke with Greg Kroah-Hartman, and he said he’d be willing to accept a framework in the kernel for writing drivers in Rust

andalevor ★★★
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.