LINUX.ORG.RU

Реализация SHA1 на С от Торвальдса обогнала реализацию на ассемблере от OpenSSL

 ,


0

0

В своём блоге небезызвестный программист Линус Торвальдс сообщает, что на его рабочей станции с процессором на ядре Nehalem его реализация SHA1 для git работает быстрее SHA1 из библиотек OpenSSL. Он отмечает, что это позволило отказаться от привязки к libcrypt и на несколько секунд увеличить результаты прохождения тестов. Причём он выделяет, что он писал на «почти кросс-платформенном ассемблере» С, в отличие от разработчиков OpenSSL, писавших на ассемблере.

В своей обычной манере Торвальдс отзывается о компиляторах ("...it turns out that getting good results from SHA1 really is mostly about trying to fight the compilers tendency to try to be clever" - "...ясно, что чтобы получить хорошую реализацию SHA1, надо бороться с тенденцией компиляторов быть самыми умными"), процессорных архитектурах («On my Nehalem machine (but not Netburst or Atom - poor fragile micro-architectures that they are)...» - «На моей машине с Nehalem (ни в коем случае не с Netburst или Atom - убогие хрупкие микро-архитектуры)...») и даже бибилиотеках, к которым привязывался git ("...I get rid of two silly runtime loadable libraries that git no longer needs" - "...Я избавился от двух глупых загружаемых библиотек времени исполнения, которые больше не нужны git")

>>> Подробности



Проверено: Shaman007 ()

Ответ на: комментарий от frame

> http://pastebin.com/m3bf105d1 - Линуса
> http://pastebin.com/mf7c0785 - твое


Ну вот хоть ты тресни, у меня при компиляции твоих исходников даже под i386 получился один и тот же размер (правда, gcc 4.4, но по идее, он выполняет только трансляцию и сборку — оптимизация уже выполнена):

https://url.odesk.com/sqid0

У меня нету под рукой машины с Hardy, чтобы собрать с gcc-4.1 под i386; в 32-битном chroot'е с gcc-3.4, 4.2, 4.3, 4.4 у меня получились такие результаты:

https://url.odesk.com/ijb6t

> А твоя функция работает корректно работать лишь в случае 32-х битных переменных


Замени в моем варианте unsigned int на uint64_t и 32 на 64, получишь версию для 64-битного поворота.

А вообще скажу по секрету, только ты никому не говори: SHA1 использует как раз-таки 32-битные повороты; как следствие, переменные 32-битные. В оригинале я называл функции rol32() и ror32().

Идём дальше. Посмотри внимательно на код Линуса:

#define SHA_ROL(X,n) SHA_ROT(X,n,32-(n))
#define SHA_ROR(X,n) SHA_ROT(X,32-(n),n)

64-битного поворота у него тоже не получится. Он там и не нужен.

К тому же, если ты внимательно смотрел на код, ты наверняка обратил внимание на defined(__i386__) || defined(__x86_64__). И ты наверняка знаешь, что что на архитектуре i386 нет 64-битных регистров общего назначения, и для 64-битного поворота одной инструкцией ro{r,l} не обойтись.

> Поздравляю, ты не нашёл смысла в исходниках от самого Линуса Торвальдса!


"Самого" меня очень впечатлило, да.

Задай самому себе вопрос, почему реализация на C обогнала реализацию на ассемблере, и честно на него ответь.

Хоть Линус в своей обычной ироничной манере и отзывается о том, что компиляторы слишком умные, но ведь именно этот "ум" и приводит к приросту производительности. Очень трудно "заточить" асмовский код под все процессоры (из-за того, что у каждого есть свои архитектурные особенности), компилятору же сделать перебор гораздо проще. И из-за лучшего планирование инструкций получаешь лучший результат при одном и том же коде.

> Ядто (активно) использует расширения GCC, и некоторый софт тоже.


Я в курсе. Но ты же обозвал gcc тормозным и глючным поделием, а не я. А разработчики ядра покраснели от стыда за то, что они используют gcc.

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

>Ну вот хоть ты тресни, у меня при компиляции твоих исходников даже под i386 получился один и тот же размер (правда, gcc 4.4, но по идее, он выполняет только трансляцию и сборку — оптимизация уже выполнена)

Да, просто замечательный код, раз он компилируется "правильно" только у тебя :)

>Задай самому себе вопрос, почему реализация на C обогнала реализацию на ассемблере, и честно на него ответь.


Очевидно же: изначально плохая реализация на асме

>Очень трудно "заточить" асмовский код под все процессоры


Асм используют обычно под какой-то один процессор/архитектуру, и иногда это дает до 300% прироста производительности. Меня честно говоря удивляет позиция тех, кто с пеной у рта в таких случаях орет что нефиг было извращаться, чтобы выжать где-то даже 5% - лучше пишите тормознутый си-only код, чтобы нам, анальным рабам компиляторных опций было легче его читать. Что-то не нравится - форкни и докажи, что ты правильнее.

>И из-за лучшего планирование инструкций получаешь лучший результат при одном и том же коде.


ага, только у тебя

>Но ты же обозвал gcc тормозным и глючным поделием


И это правда.

>А разработчики ядра покраснели от стыда за то, что они используют gcc.


Ну да, выбора-то нет, кроме "умолчания" :)

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

>При желании можно поставить icc, pcc, компиляторы Sun Studio, Tiny C Compiler, LCC (:-)), Cyclone, TenDRA, cilk и т.п. Как говорится, было бы желание.

Угу, желание и надежда, что хоть что-нибудь кроме helloworld скомпилируется моим любимым tcc который даже интегрировать с autotools гемор еще тот =)

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