Сколько инструкций в x86? +78




vvvphoenix упомянул в своей позавчерашней статье: «Кстати, я пытался найти график роста числа X86 инструкций по годам (или по поколениям). Пока не смог (может, есть у кого?)»

Я решил, что мне это тоже интересно — да настолько, что не жалко потратить выходной день на сведение en.wikipedia.org/wiki/X86_instruction_listings в одну табличку:



Считались различные мнемоники; например, десятки вариантов MOV считались за одну инструкцию.

Таким образом, можно грубо считать, что количество мнемоник в x86 удваивается каждые 13 лет.




Комментарии (159):

  1. kAIST
    /#21651158 / +3

    Так сколько же?

    • tyomitch
      /#21651214 / +1

      Я насчитал 945 в Ice Lake; другой считавший в 2016 насчитал 981 без уточнения, что именно и где именно он считал.

      • Nagg
        /#21652728 / +1

        Это скорее всего не учитывает AVX-512, там добавилось еще солидно инструкций (хотя раз считали Iceв Lkae то должны были учесть)

  2. siryoshka
    /#21651292 / -5

    как хорошо что есть ещё АМД

    • bimcom
      /#21653346

      Комментатор имел в виду — как хорошо что есть конкуренция, но был не понят.

      • perfect_genius
        /#21666474

        Но причём здесь AMD и конкуренция? Intel ведь не упомянут в статье.

        • bimcom
          /#21668180 / +1

          Ось X на графике состоит только из процессоров Intel.
          И только благодаря наличию конкурента — в лице AMD происходило добавление новых инструкций.

          • perfect_genius
            /#21672626

            Хм, также в тэгах тоже только их процы. Но неужели если бы не AMD, то Intel не ускоряла бы декодирование и не добавляла шифрование?

  3. EvilGenius18
    /#21651334 / -4

    Объяснили бы хоть для чего нужны различные инструкции, какие процессы они ускоряют, и тп.
    А то количество инструкций и загуглить можно, но в чем польза то? Все равно, что написать «в стране X население Y», ок, рад что получил эту бесполезную информацию, которая находится в интернете за 1 секунду…

    • tyomitch
      /#21651460 / +4

      Если бы вы попытались загуглить «количество инструкций в x86», то вы бы увидели, что готового ответа нет ни у кого.

    • morgot
      /#21651518 / +1

      Есть неплохая книга "Modern X86 Assembly Language Programming: 32-bit, 64-bit, SSE, and AVX".

      • Alexey_Alive
        /#21653140

        Я бы ещё порекомендовал бы Agner fog. Там всё детально разбирается. Ну и официальные гайды, конечно же.

      • perfect_genius
        /#21666494

        2014 года — не устарела ли?

        • morgot
          /#21672950

          Это же не веб). Тут технологии не стареют десятилетиями. Некоторые вещи по Windows 3.1 актуальны до сих пор (с небольшими доработками, но все же).
          Книга вполне хорошая, и объясняет основные моменты, а если нужно самое свежее и самое полное руководство — есть мануалы Интела.

  4. fse
    /#21651428 / +3

    Любопытно какой процент транзисторов пожертвован на обратную совместимость.
    А вообще, это грустно. Я пытался как-то сделать дизассемблер x86, но вовремя остановился. Потом оценил объём сопутствующего кода, который присутствует в известных дизассемблерах, вроде CapStone.

    • khim
      /#21651874 / -1

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

      Просто дизассемблер x86 я делал когда AVX и AVX2 уже были, а AVX512 ещё не было. Заняло пару недель, сравнение с XEDом и Objdump'ом показало, что текстовый выхлоп совпадает на всех инструкциях.

      А вот если вы хотите сделать что-то, что работает и с x86 и с ARM и со всем существующим зоопарком… вот тут да — задачка будет посложнее.

      • fse
        /#21651924

        Две недели — это, на мой взгляд, быстро. Много кофе выпили?
        В моём случае поддержка x86 была необязательной опцией и сводилась по большей части к дизассемблеру длин.
        Поделка анализировала предельную глубину используемого стека в программах под ARM (если встречала alloca, либо рекурсию — ругалась). Начиная с точки входа потока выводилось дерево вызовов со счётчиком накопленного стекового расхода в каждом узле. Незаменимый инструмент в ряде случаев.

        • khim
          /#21651978 / +2

          Две недели — это, на мой взгляд, быстро. Много кофе выпили?
          Там не нужно «много кофе», на самом деле. Нужно примерно день на чтение мануала и медитацию.

          В x86 есть примерно дюжина «странных» инструкций из «ранней истрии вопроса» (вот всякие эти BOUND/ENTER/MOVS/...).

          Но подавляющее большинство инструкций следуют строгому шаблону (описан тут, а тут есть прямо даже красивая картинка). Пара дней уходит на декодер «абстрактной x86-инструкции», неделька на то, чтобы перенести все эти тысячи инструкций в тот формат описания, что вы себе придумали (может быть это можно как-то ускорить и вытащить данные из PDF… я не стал заморачиваться), ну и ешё день-два — на борьбу вот с теми «извращениями», которые из раннего х86 пришли к нам (все современные инструкции начиная с MMX и новее имеют регулярную форму, только EXTRQ из SSE4A выделяется).

          Мне тоже не нужен был «полноценный декодер», но зато была очень важна его скорость.

          На самом деле самое «весёлое» это не вот все эти тысячи инструкций, но подобного рода косячки.

          Иструкции из тех, чтоб были уже в самом-самом первом 8086, но по разному декодирующиеся в AMD64 и Intel 64… это ж просто праздник какой-то!

          • fse
            /#21652010

            Спасибо за полезную информацию. Вы вселили в меня осторожный оптимизм касательно дизассемблирования x86.

            • khim
              /#21652052 / +1

              Ну тут нужно подумать вот о чём. Декодеров в современном x86 CPU не много, а… очень много. Штук двадцать. Спршивается: куда столько? А вот… супер-скаляр-с. Вам нужно уметь декодировать 4 инструкции за такт… но как это сделать, если у них и длина-то неизвестно какая? Что именно мы декодировать-то собрались?

              Применяется простой приём: есть куча (16 обычно) «простых» декодеров (которые могут узнать только длину инстукции) и ещё 3-4 «сложных» — которые уже могут декодировать инстукции до конца.

              Потому декодирование стремятся сделать как можно более простым. Транзисторный бюжет ведь ограничен! Потому, в частности, AMD «выкинула на помойку» 3DNow! и SSE4a в 2012м (в «серии тяжёлая техника» — где появилась как раз поддержка AVX) и TBM и XOP в 2017м (Ryzen). Не потому что их сложно реализовать. А потому что их сложно декодировать!

              Так что… с течением времени, как ни странно, декодирование сильно сложнее не становится — инструкции всё более регулярные, наоборот. А вот «унаследованные инструкции»… вот там да — содом и гоморра.

              • gecube
                /#21652944 / +1

                Потому, в частности, AMD «выкинула на помойку» 3DNow! и SSE4a в 2012м (в «серии тяжёлая техника» — где появилась как раз поддержка AVX) и TBM и XOP в 2017м (Ryzen). Не потому что их сложно реализовать. А потому что их сложно декодировать!

                а как же обратная совместимость?

                • Alex_ME
                  /#21653010

                  Кое-где потрачена, видимо, решив, что не сильно нужно. Например, я столкнулся с багами рендера в игре Mass Effect на AMD FX.

                  • khim
                    /#21653486 / +1

                    Это другое. Некоторые инструкции просто дают разный результат на AMD, Intel и VIA. В частности пресловутый Reciprocals of Square Roots.

                    Они дают ошибку не более описанной, да, но вот побитовые значения — разные.

                    А если игра на это заложилась…

                    Самая большая беда — для многопользовательских игр: там не так важно, какой именно результат получается — важно, чтобы у всех игроков один и тот же. А тут, вдруг, такой «подарочек»…

                  • gecube
                    /#21653494

                    Ну, в этом смысле амд действительно правы — зачем вам 3Dnow!, если есть AVX. Пользуйтесь лучшими технологиями ))) К тому же 3Dnow! был разный — это не одно расширение, а чуть ли не три или четыре. С разными дополнительными наборами команд

                    • khim
                      /#21653718 / +1

                      К тому же 3Dnow! был разный — это не одно расширение, а чуть ли не три или четыре.
                      Два с половиной. 3DNow!, Extended 3DNow! и ещё пара специнструкций у Geode.

                      Последнее связано с тем, что Geode — это вообще разработка другой фирмы (Cyrix, который National Semiconductor купила, а потом перепродала AMD).

                • khim
                  /#21653492 / +1

                  Ещё в Pentium появилась инструкция CPUID (и в старшие модели 486х потом перекочевала).

                  Если программа не проверяет CPUID — то ССЗБ, это бага, чинить нужно.

                  • 0xd34df00d
                    /#21654160

                    К слову о проверке cpuid, как нынче в кланге модно делать несколько версий функции и динамик диспатч по ним? GCC вроде сам генерит диспатчинг-код, если использовать target-атрибут, а вот clang этого не делал, ну или я что-то делал не так.

                    • khim
                      /#21656772

                      Может просто не обновились? Clang это умеет. Начиная с 10й версии.

                      • 0xd34df00d
                        /#21659622

                        Хм, и правда, это многое объясняет, спасибо!


                        Увы, это публичная библиотека, так что придётся поддерживать и более старые версии и писать код руками.

                        • khim
                          /#21661268

                          А более старые версии — это какие? У нас в проекте это начали использовать только после перехода на clang 10, но я сейчас проверил: clang 7 тоже уже так умеет…

                          • 0xd34df00d
                            /#21663530

                            Это было года три назад, так что clang 7 ещё не было.


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


                            Олсо, прикольно, не замечал раньше на godbolt плашку про #include <c++>. Чудный новый мир.

                • stanislavshwartsman
                  /#21653572

                  У AMD нет такой проблемы как «обратная совсестимость». С их долей рынка все равно мало кто пользуется AMD-only инструкциями потому что не могут себе позволить чтобы код работал только на AMD.

    • perfect_genius
      /#21666944 / +1

      В итоге Capstone-то использовали?
      Интересно, что последняя версия вышла в начале этого месяца, а баг с декодированием mulsd в ней тоже присутствует. Но разработчик написал, что в пятой версии уже исправлено. Вот насколько x86 сложна, бедные разработчики Capstone...

      • fse
        /#21670864

        Успешно поэкспериментировал с Capstone и ещё с некоторыми дизассемблерами, но потом ограничился своими силами и поддержкой МК на ARM. То что делал — не особо актуально для процессоров с MMU, в том числе x86.

  5. vvvphoenix
    /#21651780 / +1

    Спасибо. Классный график :) Однако есть ещё некоторое количество "безымянных" опкодов. Ну то есть команда есть, а названия у неё нет. И документации как правило тоже нет. Но если знаешь — можно emitами в код вставлять. Но в целом я думаю они не более 1% инструкций

    • tyomitch
      /#21651834 / +1

      В 2017 исследователь перебрал всё пространство опкодов, и нашёл в Intel Core i7-4650U (вышедшем в 2013) несколько сотен недокументированных опкодов, не вызывающих #UD. Примерно четверть из них документировали «задним числом» (между 2013 и 2017).

      Несколько сотен недокументированных опкодов среди нескольких тысяч документированных — это, похоже, намного больше 1%.

      • eanmos
        /#21653002

        Кстати, тот же исследователь смог получить root доступ на Linux машине, используя недокументированные инструкции. Выступление называется «GOD MODE UNLOCKED — Hardware Backdoors in x86 CPUs».

        • tyomitch
          /#21653464 / +1

          Справедливости ради, эта «недокументированная фича» нашлась в процессоре VIA, а не Intel.

          • khim
            /#21653842 / +1

            Там более интересная история, на самом деле. Этот режим не то, чтобы уж совсем не документирован. В документации о VIA написано достаточно информации для того, чтобы его выключить (на Wikipedia есть ссылки… но сама идея, что железяка, с завода, поставляется в режиме, когда в ней есть работающий backdoor… а впрочем — такой ли это уникальный случай? Чем это принципиально отличиается от поведения Samsung?

      • vvvphoenix
        /#21653918

        Интересно, сохраняется ли поведение этих опкодов от поколения к поколению?

    • Alexeyslav
      /#21652164

      Более того, в любой момент в процессор можно добавить некоторое количество новых… сделав его уникальным.

  6. olegshutov
    /#21651824

    у меня на первом пне уже был MMX

    • tyomitch
      /#21651848

      Pentium MMX вышел в 1997, как и Pentium II.
      Для каждого года отмечен только один процессор.

      • Stasik0
        /#21651878 / +1

        Странно что он стоит прямо над «1995»

        • khim
          /#21651984 / +1

          Ну… мясник так видит. Посмотрите где стоят числа 1978 и 2019… Что-то съехало при генерации картинки чуток.

      • beeruser
        /#21654026 / +2

        На крышке P-MMX, кстати, написано ’92’95
        www.cpu-world.com/CPUs/Pentium/Intel-Mobile%20Pentium%20MMX%20166%20-%20TT80503166%20(TT166).html

        • gecube
          /#21654072

          У Вас ус отклеился, простите, ссылка сломалась… :-((((( хабрапарсер чертов

        • tyomitch
          /#21654084

          Хотел бы я знать, почему именно эти года там написаны.
          В 1992 ведь ещё и Pentium не было, не то что MMX.

          • JerleShannara
            /#21654108

            Вполне вероятно, что указали не дату начала выпуска серийного процессора, а к примеру, выпуска первых ES камней.

          • Vitalley
            /#21654180

            Как раз готовился к производству Pentium 60

  7. Asen
    /#21652012 / +1

    Графики отражают бум индустрии компьютерных игр середины 90x (SSE+MMX) и криптографический «бум» конца нулевых (AVX)

  8. gudvinr
    /#21652046 / +1

    Раз уж вы свели табличку, может и в текстовом виде её вставите?

  9. Vitalley
    /#21652060 / +1

    FPU был всегда, то что он переехал в корпус немного сбивает ваш график

    • tyomitch
      /#21652678

      Пока не переехал в корпус, он не был частью x86.

      • VerdOrr
        /#21653272

        С учетом того, что даже 8086 всегда так или иначе обрабатывал (передавал сопру или эмулировал с помощью исключений) команды FPU, x87 это изначально именно «a floating-point-related subset of the x86 architecture instruction set.» как написано в Вики

        • tyomitch
          /#21653316

          … либо не передавал и не эмулировал, если не было ни сопроцессора, ни рантайма для эмуляции.

          Не говоря о том, что сопроцессор для 8086 не обязан был быть арифметическим, т.е. опкоды сопроцессора не обязаны были соответствовать операциям с плавающей точкой.

        • khim
          /#21653518 / +1

          С учетом того, что даже 8086 всегда так или иначе обрабатывал (передавал сопру или эмулировал с помощью исключений) команды FPU
          Не подскажите как выглядел ультра-супер-мега-модуль, позволявший процессору в 1978м общаться с кристаллом, расположенным в 1980м? Это ж просто мегатехнология какая-то!

          То, что 8086 был выпущен с рассчётом на то, что в будущем, к нему будут выпущены сопроцессоры (не обязательно математические, был ещё и 8089… который, кстати, вышел раньше 8087, в 1979м) — не обозначает что все инструкции всех этих сопроцессоров нужно в список вносить…

          P.S. 80387й тоже через два года после 80386го появился, кстати.

          • VerdOrr
            /#21653598

            Именно так — проектировался «с рассчётом на то, что в будущем, к нему будут выпущены сопроцессоры». То, что 8087 был запущен в продажу в 80ом ничего не говорит о цикле разработки.

            The 8087 was initially conceived by Bill Pohlman, the engineering manager at Intel who oversaw the development of the 8086 chip. Bill took steps to be sure that the 8086 chip could support a yet-to-be-developed math chip.

            In 1977 Pohlman got the go ahead to design the 8087 math chip. Bruce Ravenel was assigned as architect, and John Palmer was hired to be co-architect and mathematician for the project.
            en.wikipedia.org/wiki/Intel_8087#Design_and_development

            Наличие/отсутствие позволяли обрабатывать исключения —
            #NM—Device Not Available (No Math Coprocessor)
            #MF—Floating-Point Error (Math Fault)


  10. vertolet0
    /#21652910

    Почему-то казалось, что наращивание числа потоков затормозит эту тенденцию, а нет.

  11. gecube
    /#21652940

    Так. У меня вопрос. TL;DR. Прошу прощения, если что


    Так вот. Считалось количество реально разных инструкций (т.е., например, все вариации MOV за одну команду) или количество разных вариаций оп-кодов (т.е., например, все вариации одной команды с разными опкодами — разные). И как считались префиксы (repne всякие)?

    • tyomitch
      /#21652972

      Считались мнемоники (написано прямо под графиком). Префиксы REPxx считались одной мнемоникой.

  12. QtRoS
    /#21653118

    Такой вопрос: SSE, MMX, AVX — с учетом того, что это более или менее про одно и то же, а именно SIMD, был ли практический смысл называть их абсолютно разными аббревиатурами? Логичнее было бы версиями обойтись? Это чисто маркетинг?

    • ToSHiC
      /#21653198

      У них длина регистров разная.

      • QtRoS
        /#21653232

        Условные SSE64, SSE128, SSE256 разве не были бы более понятными и более приемственными?

        • VerdOrr
          /#21653298

          SSE и AVX — да, а у MMX совсем другая архитектура.

          • khim
            /#21653642 / +2

            И даже и SSE и AVX — это не одно и то же. Когда появился AVX почти каждая SSE инструкция получила своего «AVX-двойника»: такую же инструкцию — но с тремя операндами. А чтобы всех окончательно добить — использование SSE и AVX инструкций «вперемешку» здорого просаживает производительность.

            Вот зачем была нужна вторая «фича» — до сих пор никто не знает, технически ничто не мешало сделать эти инструкции преемниками друг друга, просто с разным количеством аргументов.

            P.S. Кстати использование AVX512 тоже просаживает проиводительность AVX2-кода, но при этом имена похожие… в общем какие-то потуги маркетологов…

            • tyomitch
              /#21653680 / +1

              Думаю, это антипаттерн «фатальный недостаток»: каждая новая команда разработчиков хочет сделать что-то целиком и полностью своё.

              • khim
                /#21653798

                Вряд ли. Скорее потуги маркетологов и желание получить ещё 1% на каком-нибудь бенчмарке. Ранние AVX-процессоры работали с 256-битными регистрами как с парой 128-битных. И если вам 256-битные инструкции не нужны — можно было их «расцепить» и использовать как два 128-битных регистра.

                Что было и логично, так как работать с «полными» 256-битными регистрами более-менее беспроблемно можно только в AVX2, в первой версии AVX много ограничений. Программа, использующая AVX, могла об желании работать в таком режиме «явно сообщить» процессору, вызвав VZEROUPPER. А программа, использующая SSE — про AVX ничего не знает и нужен был другой способ.

                Ну вот… нахимичили… теперь расхлёбываем.

                • 0xd34df00d
                  /#21654184

                  Эм, я все равно не очень понимаю, как связан переход между SSE и AVX с расщеплением регистров на половинки и с false dependencies по ссылке. Разве у проца не хватает контекста понять, что, ну, SSE-код работает только с нижней половиной?


                  Вы там ниже про это чуть подробнее полёте, но в каких ситуациях появляется именно false dependency?

                  • tyomitch
                    /#21654422

                    В двух словах про false dependencies (не специфично для SSE/AVX — с любыми регистрами, к которым можно обращаться по частям, та же фигня):

                    • инструкция №1 заполняет R целиком;
                    • инструкция №2 читает R;
                    • инструкция №3 заполняет половинку R и оставляет вторую половинку нетронутой.

                    В этом раскладе невозможно запустить на выполнение №3 параллельно с №1, даже если нетронутая половинка R в дальнейшем использоваться не будет.

                    Именно поэтому в x64 прописали, что 32-битные операции обнуляют старшую половинку регистра. (Для сравнения, во время работы над 80386 о возможности OoO не подумали, и поэтому 16-битные операции оставляют старшую половинку 32-битного регистра нетронутой.)

                    • 0xd34df00d
                      /#21654456

                      А если бы инструкция 1 и 2 работала с той же половинкой регистра, разве было бы лучше? Вы точно так же без ренейминга не сможете параллельно эти инструкции выполнять (а с ренеймингом, по идее, и в этом сценарии проблем быть не должно).

                      • tyomitch
                        /#21654512

                        Ренейминг эту проблему не решает, потому что в дальнейшем может встретиться инструкция, читающая R целиком — а значит, №3 должна работать над тем же самым физическим регистром, что №1 и №2.

                        • khim
                          /#21656824 / +2

                          Здесь нужно заметить, что, строго говоря, можно разбить все регистры на два, и оперировать с ними независимо. Однако извести эти паразитные зависимости до конца всё равно нельзя, а схемотехнику процессора они сильно усложняют.

                          Для 8 битных регистров это делали с Pentium II (скорее всего и сейчас ещё делают).

                          Помните байку про то, что Pentium Pro плохо работает на 16-битных программах, но отлично на 32-битных? Вот это вот оно.

                          Там речь не про 16-битные программы, а про программы, использующие %al/%ah и вот это вот всё.

                          Но для «упрощения» шла речь о 16-битных программах (MS-DOS и Windows 95).

                          • netch80
                            /#21657110

                            После Pentium 4 делят биты условий во Flags на разные «регистры». Видно по тому, что правило «не используйте INC/DEC — у него false dependency, потому что не меняет CF!» перестало быть важным для Core.

            • VerdOrr
              /#21653724

              У SSE и AVX хотя бы регистры те же. Трехоперандные команды сильно облегчают задачу планировщика и, наверное, дорого обходится переключение между режимами (перезагрузка конвейера и т.п.)

              • khim
                /#21653776 / +1

                Как раз фишка в том, что замедление происходит из-за разных регистров! У SSE регистры 128-битные, у AVX — 256-битные, расширенные. При этом операции с SSE старшую половину не меняют, а AVX — либо записывает туда что-то полезное, либо нули.

                В результате SSE2 инструкции (с учётом переименования регистров) оказываются сложнее, чем AVX, но главное — возникают «паразитные связи» между инструкциями. Потому что если у вас в один и тот же регистр AVX инструкция чего-то пишет, а потом с ним работает SSE инструкция… то, внезапно, результат работы SSE инструкции оказывается зависимым от результата работы AVX-инструкции и впараллель их исполнять нельзя.

                Прелестно, да? Что мешало сделать SSE-иструкции просто копией AVX-инструкций с двумя операндами?

                • VerdOrr
                  /#21654202

                  Да я не оправдываю — просто предположил. Мне когда-то пришлось написать несколько функций на SSE — помню очень «облизывался» на, тогда еще только анонсированное, AVX — в нескольких местах трехоперандные команды позволили бы написать гораздо более красиво и лаконично.

                • beeruser
                  /#21654294

                  внезапно, результат работы SSE инструкции оказывается зависимым от результата работы AVX-инструкции и впараллель их исполнять нельзя.

                  А зачем бить себя лопатой по голове использовать AVX и SSE одновременно? В AVX есть 128-битные команды, аналогичные SSE2. Старшая часть отключается, если не нужна.
                  Также имеется VZEROUPPER чтобы сбросить зависимость.

                  Что мешало сделать SSE-иструкции просто копией AVX-инструкций с двумя операндами?

                  Простите что? SSE появился в 1999г, AVX в 2011.

                  • JerleShannara
                    /#21654310

                    Legacy код.

                    • beeruser
                      /#21654634

                      Не очень понятно о каком легаси идёт речь, если SSE используется параллельно с AVX.
                      software.intel.com/content/www/us/en/develop/articles/intel-avx-state-transitions-migrating-sse-code-to-avx.html
                      To бишь, согласно иллюстрации в документе Intel, мы переходим из состояния B в состояние C.
                      Operating in State C is undesirable.

                      Что же касается компиляции легаси кода, то SSE интринсики автоматически преобразуются в AVX компилятором.
                      zig.godbolt.org/z/BkFrTE

                      • JerleShannara
                        /#21654974

                        К примеру в 2002 году был написан кусок кода в котором торчали ассемблерные вставки (мы ведь понимаем, что врядли такое будут делать компиляторы) для ускорения каких-то вычислений, а через лет пятнадцать — было решено ещё что-нибудь отоптимизировать. И по результату вполне может получиться «отрицательный рост» производительности благодаря тому, что очередной кодер тупо вспомнил о том, что «вот есть такая крутая инструкция, она здесь просто прекрасно будет смотреться». Сам в поисках наиболее быстрого способа копирования памяти такое чудил, правда в те времена, когда кроме SSE ничего другого и не было.

                        • beeruser
                          /#21656030

                          Скорее всего тот код уже превратился в балласт и его давно пора удалить.
                          Ассемблерные вставки — зло. Используйте интринсики, либо пишите нормальный асм код.
                          Если ваш кодер плюёт на рекомендации Интел и расчесывает котов против шерсти не соблюдает правила, он ССЗБ.
                          Ещё раз напомню, что эта «страшная» проблема лечится одной инструкцией. Написав этот коммент, вы приложили на порядок больше усилий чем требует решение проблемы.

                          • khim
                            /#21656866

                            Ещё раз напомню, что эта «страшная» проблема лечится одной инструкцией.
                            Какая интсрукция? MAGICBEERUSER2? Или как?

                            Как вы собираетесь AVX-код на процессорах без AVX запускать?

                            У нас, к примеру требование: программа должна поддерживать все процессоры с поддержкой SSE2 и более новые.

                            Куда и какую команду вставить чтобы реализация инструкций на SSE (а не весь код требует 256 битных регистров, там есть даже и скалярные вычисления, представьте), вдруг, внезапно, стала нормально работать везде?

                            • tyomitch
                              /#21656898

                              Инструкция VZEROUPPER.

                              Если в вашем коде нет AVX-инструкций, а есть только SSE, то нет никаких проблем — проблемы появляются только от их смешения.

                              • khim
                                /#21657052 / +2

                                Проблема в том, что их смешение — это естественный результат применения DRY-принципа.

                                Если ваша прогремма должна, внезапно, поставляться заказчику (да и даже выполняться на кластере, где есть компьютеры с AVX и без) — то логично тот код, которому AVX не нужен писать на SSE и не умножать сущности без необходимости.

                                Но тогда вам придётся на каждом переходе требовать, чтобы использовался VZEROUPPER. И в результате, так как компиилятор понятия не имеет — использует ваша программа SSE-код или нет, он эту инструкцию пихает во все места. И он будет это делать даже без вашего желания. Да, можно его стукнуть по башке… но вы реально верите что вот все-все должны это делать и делают? Я даже не знаю как в MSVC это сделать в принципе (поиск показывать только кучу несчастных, безуспешно пытающихся его научить так делать).

                                Прелестно, не так ли? Вы и после вот всего этого будете утвеждать, что разработчики AVX вовсе-то и не обосрались?

                                • beeruser
                                  /#21658158

                                  Если ваша прогремма должна, внезапно, поставляться заказчику (да и даже выполняться на кластере, где есть компьютеры с AVX и без)

                                  Если у вашей минимальной целевой платформы нет AVX, значит используются чипы 9-летней давности и производительность никого не интересует.
                                  Это решить проще всего — используйте только SSE2.
                                  Если конечно маркетинг не продаёт AVX код как фичу.

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

                                  На каком переходе? Она нужна в конце вычислений с использованием 256-битного AVX.
                                  Если вы используете 128-битный AVX (который переводится из SSE компилятором), скорее всего уже
                                  проц находится в состоянии A (в вышеупомянутой таблице).

                                  он эту инструкцию пихает во все места.

                                  Вот видите, компилятор сам заботится о вас, чтобы у вас не тормозил код.
                                  В чём, собственно, проблема?

                                  Несмотря на то что в Skylake убрали столл при переключении состояния, если вы не сделаете vzeroupper, будет другая «беда».

                                  For what it's worth, the vzero family is still very much needed on Skylake. The big one-time state transition penalty has disappeared, but was replaced with the ongoing penalty of blending the high half of the register for all all the non-VEX encoded instructions.

                                  That penalty if often huge, perhaps a 2x to 6x slowdown, and it never ends while you run non-VEX code. So you very much need to do the zeroing on Skylake — not for «consistency» but for performance. This has been biting people repeatedly in weird and wonderful ways — the old one-time penalty probably occurred here too, but as a small one-time it would have never been noticed.


                                  Вы и после вот всего этого будете утвеждать, что разработчики AVX вовсе-то и не обосрались?

                                  А, ну всё понятно. Вас интересует поиск виноватых…

                                  • khim
                                    /#21658638

                                    Если у вашей минимальной целевой платформы нет AVX, значит используются чипы 9-летней давности и производительность никого не интересует.
                                    Если у вас нет мозгов — то ваше мнение никого не волнует.

                                    Представьте себе — не все программы в мире это игры, где CPU должно хватать для рассчёта картинки за 1/60 секунды.

                                    Какой-нибудь Floyd–Steinberg вполне может быть достаточно медленным даже на процессоре с AVX2, однако если ваш графический редактор не будет работать на компьютерах без оного — то вас, извините, не поймут-с.

                                    Photoshop до сих пор требует только SSE2 — и ничего более.

                                    На каком переходе?
                                    При мереходе из функции в функцию, однако.

                                    Вот видите, компилятор сам заботится о вас, чтобы у вас не тормозил код.
                                    В чём, собственно, проблема?
                                    Проблема в том, что цена VZEROUPPER — нифига не нулевая. И наличие его там, где оно не нужно (также, как и его отсутствие там, где нужно) — приводит к замедлению.

                                    Несмотря на то что в Skylake убрали столл при переключении состояния, если вы не сделаете vzeroupper, будет другая «беда».

                                    For what it's worth, the vzero family is still very much needed on Skylake. The big one-time state transition penalty has disappeared, but was replaced with the ongoing penalty of blending the high half of the register for all all the non-VEX encoded instructions.

                                    That penalty if often huge, perhaps a 2x to 6x slowdown, and it never ends while you run non-VEX code. So you very much need to do the zeroing on Skylake — not for «consistency» but for performance. This has been biting people repeatedly in weird and wonderful ways — the old one-time penalty probably occurred here too, but as a small one-time it would have never been noticed.
                                    А вы не заметили, что мы, как бы, ровно эту вашу «беду» тут и обсуждаем? То, что было в Sandy bridge — это, конечно, вообще ни в какие ворота не лезет, но вот это вот идиотское отличие SSE от AVX — по прежнему является проблемой, как вы сами-таки и откопали…

                                    • beeruser
                                      /#21659222 / -1

                                      Photoshop до сих пор требует только SSE2 — и ничего более.

                                      Как видите, они следуют моему совету. Отнюдь не потому что у них «нет мозгов» :)

                                      При мереходе из функции в функцию, однако.

                                      У вас весь код состоит из перемешанных SSE и AVX функций?

                                      Проблема в том, что цена VZEROUPPER — нифига не нулевая.

                                      А какая? Должна быть в районе нескольких тактов.

                                      А вы не заметили, что мы, как бы, ровно эту вашу «беду» тут и обсуждаем?

                                      Это ваша беда — у меня нет таких проблем.
                                      Обсуждаем мы «легаси код 2002г» и смешивание инструкций разных наборов, что крайне не рекомендуется делать разработчиком архитектуры.

                                      • khim
                                        /#21659418

                                        Проблема в том, что цена VZEROUPPER — нифига не нулевая.

                                        А какая? Должна быть в районе нескольких тактов.
                                        Даже один такт может вполне ощутимо просаживать производительность. Современные процессоры мало того, что могут исполнять 3-4 инструкции за такт, так они ещё и спекулятивно могут исполнять код в других функциях (для этого есть специальные оптимизации).

                                        Обсуждаем мы «легаси код 2002г»
                                        Серьёзно? То есть вы можете убедить вышеупомянутом примере MSVC не геренить лишний VZEROUPPER? Расскажите как — после этого можно будет что-то обсуждать. Там, как бы компилятор от декабря 2019го… свеженький такой.

                                        и смешивание инструкций разных наборов, что крайне не рекомендуется делать разработчиком архитектуры.
                                        Угу. И мы даже выясниль — костылём к какому именно костылю этот идиотизм был порождён… Вот только платите вы за всё это даже на самых соврменных процессорах и даже там, где никакого SSE нет и не будет (нет, clang/gcc позволяют от костылей отказаться… MSVC, похоже, нет).

                                        • beeruser
                                          /#21661798

                                          Даже один такт может вполне ощутимо просаживать производительность.

                                          Смешно.

                                          После условных 10000 тактов на выполнение цикла, этот 1 такт прямо так ощутимо будет просаживать производительность вашей программы :)
                                          Согласно таблицам Фога, на процессорах Intel vzeroupper и занимает 1 такт. Не думаю, что вы считаете количество обращений к памяти. Это подотчётная операция у вас? Ибо, с такой заботой об каждом такте, она должна быть таковой.

                                          Современные процессоры мало того, что могут исполнять 3-4 инструкции за такт

                                          А вы измеряли сколько в реальности выполняется?

                                          sophisticated CPU cores actually sustain an average of slightly more than one instruction per cycle when executing many programs.

                                          Или вот отрывок из документации по vtune:
                                          Modern superscalar processors issue up to four instructions per cycle, suggesting a theoretical best IPC of 4. But various effects (long-latency memory, floating-point, or SIMD operations; non-retired instructions due to branch mispredictions; instruction starvation in the front-end) tend to pull the observed IPC down. A IPC of 1 is generally considered acceptable for HPC applications but different application domains will have very different expected values.

                                          То есть вы можете убедить MSVC не геренить лишний VZEROUPPER?

                                          А смысл? Его нужно генерить в вашем случае.
                                          Это рекомендация Интел.

                                          Его не нужно было бы генерить, если бы вы использовали AVX-128. Моя целевая платформа (кстати с довольно дорогим vzeroupper) предполагает наличие AVX, соответственно вашей проблемы у меня нет, как я уже говорил.

                                          И мы даже выясниль — костылём к какому именно костылю этот идиотизм был порождён

                                          Операции над AX точно так же не очищают EAX. Искать виноватых — последнее дело.

                                          MSVC, похоже, нет

                                          С выходом 10-го clang, пользоваться MSVC по большому счёту и не нужно.

                                          • tyomitch
                                            /#21661978 / +1

                                            Операции над AX точно так же не очищают EAX. Искать виноватых — последнее дело.

                                            Зато очищают верхнюю половинку RAX :-P

                                            • netch80
                                              /#21662254 / +1

                                              Ни у Intel ни у AMD операции над AL, AX не очищают верхнюю половинку RAX. Можете взять ассемблер и проверить.

                                              Тут
                                              #include <stdio.h>
                                              #include <stdint.h>
                                              int main() {
                                                uint64_t a = 0x123456789abcdef0;
                                                asm(
                                                  "mov $3, %%bl\n\t"
                                                  "mov %%bl, %%al"
                                                  : "=a" (a) : "0" (a) : "rbx");
                                                printf("%lx\n", a);
                                              }
                                              

                                              Запускаю:
                                              123456789abcde03

                                              • khim
                                                /#21662616

                                                Обратите внимание, что компиляторы для переноса 8- и 16-битных значений в регистр жёстко предпочитают использовать не простой mov, а movsbl, movzbl, movswl, movzwl и т.п. (в обозначениях AT&T) — именно для исключения этих зависимостей самым дешёвым доступным способом…
                                                Только 16 бит. Из-за MS-DOS и Windows 95 в Pentium II сделали AL и 3/4 AX отдельными регистрами, а дальше — на это компиляторы заложились, потому это теперь не убрать.

                                                • netch80
                                                  /#21662724 / +1

                                                  Переключите с clang на gcc и увидите movzx и при 8-битном аргументе.
                                                  Про clang & icc принято, но всё равно странновато и никто не мешает тут не делать потенциальные диверсии.
                                                  А что такое «3/4 AX»?
                                                  Биты 8-31 от EAX?

                                                  • khim
                                                    /#21663242

                                                    А что такое «3/4 AX»?
                                                    Биты 8-31 от EAX?
                                                    Угу. У них была проблема в том, что в MS-DOS активно используется API, где AL/AH, BL/BH, CL/CH и DL/DH рассматриваются как независимые регистры. Из-за этого архитектурно более совершенный Pentium Pro оказывался по скорости едва-едва быстрее Pentium. При цене чуть не на порядок большей.

                                                    В Pentium II эти регистры начали рассматривать как независимые.

                                                    Про clang & icc принято, но всё равно странновато и никто не мешает тут не делать потенциальные диверсии.
                                                    Если учесть, что ICC — это прямо «компилятор от производителя CPU», то, наверное, так и надо…

                                                    А вообще — у них заметно разные «подходы». Вот тут можно увидеть. Clang пытается за счёт использования дополнительных регистров код сделать проще, icc довольно быстро отказывается от 8-битных регистров и пытается за счёт битовых оптимизаций что-то сделать… gcc тупо «сливает».

                                                    P.S. В 64-битном режиме это меньше заметно, там же 16 8-битовых регистров (правда включая SPL). В 32-битном режиме — это беда…

                                          • khim
                                            /#21662626

                                            Это подотчётная операция у вас? Ибо, с такой заботой об каждом такте, она должна быть таковой.
                                            Знаете, если у вас весь код пишется с одинаковым подотчётным тщанием — то мне вас просто жаль.

                                            Потому что у нормальных людей, у которых в голове мозги, а не пиво, в одной и той же программе может быть код на Python (какая там производительность — знаете без меня) и код, в котором не то, что каждый такт учтён, но даже проверена раскладка по испоняющих устройствам для разных CPU.

                                            Всё зависит от того, что это за код и где он используется.

                                            То есть вы можете убедить MSVC не геренить лишний VZEROUPPER?

                                            А смысл? Его нужно генерить в вашем случае.
                                            Это рекомендация Интел.
                                            Ах, ну да. Как же я мог забыть. Нужно просто соблюдать рекомендации — и всё будет чики-пуки. А если ништяки с неба не сыплются, то нужно просто рекомендации тщательнее исполнять.

                                            Его не нужно было бы генерить, если бы вы использовали AVX-128.
                                            А кто тут у нас писал Что же касается компиляции легаси кода, то SSE интринсики автоматически преобразуются в AVX компилятором? Быстро же у вас сменилась «линия партии».

                                            Операции над AX точно так же не очищают EAX и вызывают partial register stall.
                                            А вот операции с EAX, внезапно, так не делают. Старшая половина RAX всегда либо обнуляется.

                                            Искать виноватых — последнее дело.
                                            Наоборот. Когда кто-то где-то вырезает «гланды автогеном через задницу» — это первое, что нужно сделать. И понять почему. А потом уже можно решить — что с этим делать. Может уже пора и перестать, а может нужно и, наоборот, продолжить это делать — если тому есть веская причина.

                                            С выходом 10-го clang, пользоваться MSVC по большому счёту и не нужно.
                                            По-моему это рекорд: тут у вас «линия партии» сменилась посередине одного сообщения.

                                  • 0xd34df00d
                                    /#21663522

                                    Если у вашей минимальной целевой платформы нет AVX, значит используются чипы 9-летней давности и производительность никого не интересует.
                                    Это решить проще всего — используйте только SSE2.
                                    Если конечно маркетинг не продаёт AVX код как фичу.

                                    Я хочу наконтрибьютить в опенсорс-библиотеку для работы со строками, потому что функция поиска символа в строке там тормозит. Эту задачу можно эффективно решать как через SSE4.2, так через AVX2 и через AVX512. Что мне выбрать в этих условиях?

                                    • JerleShannara
                                      /#21663584

                                      При учёте того, что почти весь современный около-GPL софт (за редкими исключениями) я совершенно спокойно собираю и запускаю на Pentium II — то лучше всего будет сделать на MMX. И не забыть предусмотреть варианты сборки на SPARC/ARM/MIPS/Alpha и прочих. То есть сделать недурной такой подраздел в ./configure на распознавание/выбор процессора.

                  • netch80
                    /#21654800

                    Я его понял так: вот мы расширили регистры и можем предполагать любую семантику для старшей части — что мешает сделать, что старые инструкции (SSE) чистят всё выше бита 127?
                    И вот поиском на такую тему нахожу:

                    The history is this: The extension of vector registers from 128 to 256 bits caused a problem when legacy Windows device drivers saved only the lower 128 bits of the new 256-bit registers. This problem was solved in a rather complex way.
                    и дальше описание того, что уже знаем.
                    «Семь бед — один ответ! Костыль и велосипед!» (tm)

                    • tyomitch
                      /#21654828

                      Дальше по ссылке пояснение, что виноваты не «legacy drivers», а Win64 ABI, предписывающее сохранять XMM-регистры. Во время создания этого ABI ещё не предполагалось, что у XMM-регистров появится «верхняя половина», которую уже скомпилированный код сохранять не сможет.

                      • netch80
                        /#21654858

                        OK, пусть Win64 ABI не сохраняет верхние половины. Мы знаем, что оно их не сохраняет, но у нас корректное состояние с сохранением нижних половин (всё SSE их сохраняет, а верхние части могут обнулиться или иначе измениться). Что мешает зафиксировать факт такой работы текущего ABI и не насиловать процессор? Всё равно если надо сохранять YMM регистры целиком — это будет другой ABI.

                        Объясните, а то что-то не сходится.

                        • tyomitch
                          /#21654970

                          Если не менять ABI, то получится, что XMM-регистры сохраняются дважды: вызывающей стороной вместе с верхней половиной, и вызываемой стороной без верхней половины. Это не катастрофично, но очень странно.
                          Поэтому ABI собирались обновить обратно-совместимым образом: вызываемая сторона либо сохраняет верхние половинки, либо не трогает их, и тогда они остаются без изменения. Хотя судя по тому, что я вижу в MSDN прямо сейчас, такого обновления ABI так и не произошло.

                          • netch80
                            /#21655384

                            > вызывающей стороной вместе с верхней половиной, и вызываемой стороной без верхней половины. Это не катастрофично, но очень странно.

                            Это неизбежно. И тут Intel мог бы помочь, например, прямым доступом к верхним половинам… хотя смысла всё равно нет с текущим стилем железа — для такой задачи, где нужен AVX256, сохранить на 16 байт больше из одного регистра — копейки.

                            > такого обновления ABI так и не произошло.

                            Они и не могли сделать такое обновление. Костыль принципиально уже не мог сработать и не сработал.

                            • tyomitch
                              /#21656936

                              Они и не могли сделать такое обновление. Костыль принципиально уже не мог сработать и не сработал.

                              Думаю, что при добавлении в MSVC поддержки AVX вполне могли бы. (Сейчас, конечно, уже не могут.)

                      • khim
                        /#21656962 / +1

                        Дальше по ссылке пояснение, что виноваты не «legacy drivers», а Win64 ABI, предписывающее сохранять XMM-регистры.
                        Нет.

                        Во время создания этого ABI ещё не предполагалось, что у XMM-регистров появится «верхняя половина», которую уже скомпилированный код сохранять не сможет.
                        То, что он эти части YMM-регистров не может сохранить или восстановить — это полбеды. В конце-концов если они потеряны никакой VZEROUPPER не поможет.

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

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

                        Если бы SSE-код эти страршие половинки бы обнулял — весь этот «танец с бубнами» был бы не нужен.

                        К сожалению иначе как вредитеством я это решения назвать не могу. Ну потому что это ж было через много лет после фиско Pentium Pro — та история должна была бы остаться у кого-то в мозгах!

                        А VZEROUPPER — это уже попытка частично это вредительство смягчить…

                    • khim
                      /#21656928 / +1

                      Проблема в том, что вы нашли кой-чего-совсем-не-то.

                      Подумайте для начала — почему, вдруг, процессор оказался в таком состоянии, что VZEROUPPER может чему-то помочь?

                      Ответ: потому что кто-то сохранил значение 128 бит в стеке, а потом восстановил (как вы прочитали в той статье) с помощью SSE инструкций!

                      А что было бы, если бы, вместо этого, использовались бы AVX128 инструкции (или если бы SSE инструкции вели себя так же, как AVX128 инструкций). Ой, глядика-ты: проблема бы рассосалась и исчезла!

                      Паразитных зависимостей не было бы изначально, никакой VZEROUPPER был бы не нужен.

                      и дальше описание того, что уже знаем.
                      «Семь бед — один ответ! Костыль и велосипед!» (tm)
                      Ага. Только вот этот «костыль и велосипед» — это уже как раз следствие того, что SSE ведёт себя не как AVX128.

                      А вот какую проблему это «расчщепление сущностей» помогло-таки решить?

                      • netch80
                        /#21657098

                        > Подумайте для начала — почему, вдруг, процессор оказался в таком состоянии, что VZEROUPPER может чему-то помочь?

                        Вам незачем мне тут возражать — я точно так же говорю, что проблема возникла, когда решили, что SSE на расширенных регистрах должно не трогать старшие 128 бит, при том, что это была вторая половина 2000-х и последствия уже все знали.

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

                        > Проблема в том, что вы нашли кой-чего-совсем-не-то.

                        А что именно «то»?
                        Ваши же слова рядом:

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


                        так вот — Intel, возможно, и идиоты, но не кретины, в медицинском смысле. Что именно было тут причиной? Я перебрал возможные ситуации со своей точки зрения, и единственное предположение тут следующее: если драйвера (это слово там прозвучало не зря?) используют SSE, и умеют при этом сохранять модифицированные ими регистры, но только командами SSE (а не каким-нибудь XSAVE), и нет горизонтального переключения между соседними процессами (это важно — иначе не поможет), или же это горизонтальное переключение сделано системным кодом, который уже YMM-aware, а драйвера — ещё нет — то вариант «делаем, чтобы никакое SSE не трогало верхние половинки» тут поможет. Пенальти на переключение между State B и State C на входе/выходе сисколла или прерывания — не так уж и страшно, с их точки зрения.

                        Многовато натяжек (всё равно непонятно, почему нельзя было на границе сисколла/прерывания явно отработать проблему), но «если отбросить всё невозможное — остаётся реальное». Или у вас есть другие идеи?

                        • khim
                          /#21657210

                          Многовато натяжек, но «если отбросить всё невозможное — остаётся реальное». Или у вас есть другие идеи?
                          Похоже они не нужны. Да, там по ссылки есть сообщение от чувака из Intel, который ровно про это и говорит: да, у нас есть драйвера, которые трогают SSE (руки бы оторвать таким драйверописателям) и нам придётся «устроить всем кузькину мать».

                          Которую мы теперь будем разсхлёбывать вечно. Ну или пока от испоьзования SSE не откажемся совсем, по крайней мере.

                          Класс.

                          Ну спасибо хоть объясниснили в чём беда, а то я уж совсем испугался за разум товаристчей из Intel: Theoretically a new OS could take care of this for the ISR, but we didnt want to penalize users of the legacy architecture and could not mandate a major OS re-write.

                          Жуть. Хоть бы флаг в процессоре сделали бы, чесслово. Собственно два флага: один для привелегированного кода, другой для непривелигированного. И всё. И нет проблем.

                          Никто бы про эту разницу между SSE и AVX (кроме драйверописателей) даже не задумывался бы…

                          Тогда хотя бы те, кого это не касается (все пользователи Линукс, собственно), жили бы спокойно…

                          • tyomitch
                            /#21657466

                            Так а всё-таки, что создатели «кривых драйверов» сделали не так?
                            Не сохраняли верхнюю половину регистров, которой ещё не существовало?

                            • netch80
                              /#21657848

                              > Так а всё-таки, что создатели «кривых драйверов» сделали не так?

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

                              Решить её можно было несколькими методами, но почему-то выбран оказался «лучший из худших».

                              • tyomitch
                                /#21658022

                                Ну, конкретно khim предложил «руки бы оторвать таким драйверописателям», а я не понимаю, за что.

                                • netch80
                                  /#21658124

                                  Ааа. Я думаю, это недовычищенное при редактировании. Я его вначале и не заметил.

                                • khim
                                  /#21658682

                                  За использование SSE в драйверах. В 99% случаев никакой SIMD в драйверах нафиг не нужен, потому что процессор почти всегда всё равно быстрее, чем железо.

                                  А зато если SSE регистры не используются, то их не нужно и сохранять.

                                  Если же ну вот очень-очень-очень надо, прям край как надо, ускорение ожидается космическое… можно использовать инструкцию, которая, внезапно, как раз для этого и предназначена (и появилась в Pentium II, ещё когда SSE первой версии в проекте был… так что не надо про то, что «мы ж не знали» — знали, просто не думали).

                                  Подобные дискуссии среди разработчиков Linux — ни разу не редкость и, в результате, в Linux в драйверах ни SSE, ни AVX не используются (за исключением драйвера RAID).

                              • khim
                                /#21658736

                                При чём тут авторы драйверов, когда проблема создана на уровне процессора?
                                Проблема не создана на уровне процессора. Она создана на уровне драйверов. Сохраниение контекста (включая SSE регистры!) процессором осуществляется с помощью команды FXSAVE, которая, внезапно, появлась аж в Pentium II (то есть до изобретения SSE даже).

                                Однако некоторые ушлые драйверописатели обнаружили, что это ж долго — все рагистры-то сохранять! А давайте мы парочку регистриков тихо-и-незаметно куда-нибудь сохраним, а потом восстановим… никто ж ничего не заметит, ведь правда?

                                Ну а потом, как мы выяснили, и родилось вот это вот идиотское решение с явным разнесенеием SSE и AVX инструкций и «штрафом» за их перемешивание…

                                • tyomitch
                                  /#21658780

                                  Хм, но ведь и FXSAVE не сохраняет верхние половинки?
                                  Если нет разницы, зачем платить больше?

                                  • khim
                                    /#21659464

                                    Хм, но ведь и FXSAVE не сохраняет верхние половинки?
                                    Так она их не сохраняет потому что драйвера эту инструкцию не используют!

                                    Научить сохранять YMM'ы в 32-битном режиме (где самое лютейшее легаси и обитает) — вообще без проблем, в 64-битном — можно было бы прописать в какой-нибудь MSR адрес процедуры, которая бы YMM регистры куда-нибудь записывала бы.

                                    Главное — сохранение и восстановление состояния выполнялись бы настолько медленно (62+68 тактов = 130 тактов на Pentium II), что вся эта конструкция «яйца бы выеденного не стоила». Применялась бы в трёх всем известных драйверах, как в Linux, и всё.

                                    Вообще вся эта попытка выиграть что-то под Windows и MacOS — это какой-то вечный забег по граблям. В духе «а давайте мы для экономии памяти научим ядро часть своего кода выгружать… а лет через 10 обнаружим, что у нас и невыгружаемая часть теперь больше, чем вообще всё ядро в Linux».

                                    Про большую коллекцию граблей, которую собрала MacOS из-за попытки вписаться в 128K в 1984м году есть даже отдельная статья в Wikipedia.

                                    Но, как известно уроки истории заключаются в том, что люди ничего не извлекают из уроков истории — тут мы это видим в очередной раз.

                                    Развитие идёт по спирали, как известно… и каждое следующее поколение, получил от граблей фингал под глазом и обматерив предшественников всеми нехорошими словами, какие удалось вспомнить, тут же разворачивается и аккуратно покрывает оставшуюся за ними дорожку всё теми же самыми граблями.

                                    А то, вдруг, следующее поколение без фингалов под глазами окажется… непорядок.

                                    • netch80
                                      /#21659724

                                      > Главное — сохранение и восстановление состояния выполнялись бы настолько медленно (62+68 тактов = 130 тактов на Pentium II)

                                      Это, кстати, для общих затрат даже на вертикальное переключение — не очень много — всё равно все регистры сохранять-восстанавливать, а если делать это одной порцией в память, то самые серьёзные затраты с торможением по памяти будут обойдены. Не восстанавливать все пользовательские регистры опасно утечкой данных, потому что в стандартном соглашении вызова те регистры, что args + result + scratch, никто не чистит, а в callee-saved, наоборот, может что-то лишнее притечь ядру… опасно.

                                      • tyomitch
                                        /#21661134

                                        ARM при вертикальных переключениях сам заменяет все регистры.
                                        Спрашивается, что мешало AMD и Intel при реализации x64 сделать так же? Вопрос обратной совместимости тогда не стоял, а стольких проблем удалось бы избежать.

                                        • khim
                                          /#21661252 / +1

                                          ARM при вертикальных переключениях сам заменяет все регистры.
                                          Это кто ж вас так жестоко обманул? На картинку, хотя бы, гляньте. В большинстве режимов он меняет буквально пару регистров и только в FIQ — половину (и то не все).

                                          Все регистры менял 8080… уже даже Z80 не мог себе этого позволить.

                                          Спрашивается, что мешало AMD и Intel при реализации x64 сделать так же?
                                          Дык никто не мешал. Кроме здравого смысла. Прерывание — оно, знаете ли… прерывает. И потому должно работать быстро. Соответственно обычные регистры x64 сохраняет, а x87 и SSE — нет. Ну просто никому и в страшном сне не могло присниться, что при обработке прерываний кто-то решит, внезапно, использовать SSE.

                                          Но… нет такого идиотизма, который не могут совершить разработчики в погоне за требованиями маркетологов! Если у вас есть кто-то вроде Линуса, кто посылает маркетологов «в пешее эротическое» — всё будет в порядке. Если нет — ну вот и получим то, что получили…

                                          • tyomitch
                                            /#21661446

                                            Дык никто не мешал. Кроме здравого смысла. Прерывание — оно, знаете ли… прерывает. И потому должно работать быстро.

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

                                            Но… нет такого идиотизма, который не могут совершить разработчики в погоне за требованиями маркетологов! Если у вас есть кто-то вроде Линуса, кто посылает маркетологов «в пешее эротическое» — всё будет в порядке. Если нет — ну вот и получим то, что получили…

                                            Драйвера под Windows проверяются в WHQL, и Windows не загружает их без подписи, удостоверяющей, что драйвер проверен.

                                            • gecube
                                              /#21661652

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

                                              В смысле? Т.е. Вы хотите сказать, что при переключении контекста НИКОГДА не сохраняется содержимое регистров в ОЗУ? Или про то, что прерывания != переключение контекста? Или про то, что в процессоре есть дофигища регистров, скрытых от пользователя (программиста), на которые можно что-то там намаппить?

                                              • tyomitch
                                                /#21661692

                                                Вы хотите сказать, что при переключении контекста НИКОГДА не сохраняется содержимое регистров в ОЗУ?

                                                Если процессор не сохраняет регистры сам, то их приходится сохранять программисту в ОЗУ.

                                                Или про то, что в процессоре есть дофигища регистров, скрытых от пользователя (программиста), на которые можно что-то там намаппить?

                                                Конечно есть.

                                                • gecube
                                                  /#21661700

                                                  Конечно есть.

                                                  Я, наверное, не совсем правильно выразился. Т.е. существование их мне известно и я могу его… как бы… обосновать технически. Вопрос в том ДЕЙСТВИТЕЛЬНО ли они участвуют в означенных процессах ("сохранение регистров при прерывании" и "сохранение контекста при переключении процесса") или это побочный эффект.


                                                  И это мы не затрагиваем еще режимы работы вроде SMM.....

                                                  • khim
                                                    /#21661832 / +1

                                                    Вопрос в том ДЕЙСТВИТЕЛЬНО ли они участвуют в означенных процессах («сохранение регистров при прерывании» и «сохранение контекста при переключении процесса») или это побочный эффект.
                                                    Это — не побочный эффект, но сознательное архитектурное решение. От которого, внезапно, все отказались в современных архитектурах. Так как это — существенное усложнение всей конструкции без каких-либо плюсов. В оригинальной, 32-битной, архитектуре ARM IRQ сохранял 3 регистра, FIQ сохранял 8, на Arrch64 — в обоих случаях сохраняется парочка, остальным занимается OS.

                                                    И это мы не затрагиваем еще режимы работы вроде SMM.....
                                                    С SMM всё, как раз, гораздо проще: он под конкретный процессор затачивается, в случае существенного архитектурного обновления — может потребоваться обновления firmware всё равно.

                                            • khim
                                              /#21661752 / +1

                                              Время, занимаемое переключением регистров, не зависит от числа переключаемых регистров, потому что меняется только маппинг, самое содержимое регистров никуда не перекачивается.
                                              В физическом мире ничего не бывает «бесплатно». Если вы добавляете в процессор систему маппинга регистров, то у вас усложнается стадия декодирования и, что ещё хуже, она начинает зависеть от режима, в котором находится процессор… в общем всё это далеко небесплатно. Вспомните как и почему sysenter появился.

                                              Драйвера под Windows проверяются в WHQL, и Windows не загружает их без подписи, удостоверяющей, что драйвер проверен.
                                              А толку? WHQL — это просто некоторый набор тестов. Вы не поверите на что свособно воображение драйверописателей, у которых с одной стороны есть одна задача (пройти тексты), с другой другая (удовлетворить хотелки маркетинга).

                                              • tyomitch
                                                /#21661956

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

                                                Я про то, что если это уже сделано для половины регистров, то можно без дополнительных затрат расширить эту систему на все регистры.

                                                А толку? WHQL — это просто некоторый набор тестов.

                                                Они в том числе проверяют драйвера на использование «запрещённых приёмов».

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

                                                devblogs.microsoft.com/oldnewthing/20040305-00/?p=40373

                                                • khim
                                                  /#21662108

                                                  Я про то, что если это уже сделано для половины регистров, то можно без дополнительных затрат расширить эту систему на все регистры.
                                                  А… вы про это. Ну так её довольно давно Intel выпилил. Ещё при переходе с 8080 на 8086 в 1978м году. Про ARM не знаю — вроде документация от 1987го года (тут можно найти) говорит о том, что там действительно маппинг регистров имеется, но я не уверен, что в современных суперскалярах это всё ещё поддерживается…

                                                • beeruser
                                                  /#21662412

                                                  Я про то, что если это уже сделано для половины регистров, то можно без дополнительных затрат расширить эту систему на все регистры.

                                                  У ARMv8 маппинг РОН убрали. Для поддержки AArch32 он всё ещё есть, аппаратно, но все теневые регистры отображены на 31 РОН. Некоторые современные ARM процессоры больше не поддерживают 32-битный режим.

                                            • netch80
                                              /#21661910 / +1

                                              > Время, занимаемое переключением регистров, не зависит от числа переключаемых регистров, потому что меняется только маппинг, самое содержимое регистров никуда не перекачивается.

                                              Это будет означать, что количество архитектурных регистров будет умножено на количество уровней привилегий. Пусть их 4, как в типовых современных архитектурах — значит, ко всем номерам регистров добавится по 2 бита. Соответственно утолщение блока переименований… увеличение объёма пула реальных регистров на весь этот балласт… зачем?

                                              Я боюсь, вы допускаете тут ошибку, полагая, что если говорят, что, например, SP каждый на свой уровень, то он реально хранится раздельно и подключается именно конкретный в каждый момент. Для более чем одного регистра это невыгодно, лучше копировать в момент переключения, а адресовать уже один регистр всегда.
                                              И даже для комплекта для FIQ это скорее всего на момент перекидки использование прямой связи между тремя версиями одного регистра.

                                              • khim
                                                /#21662200

                                                Я боюсь, вы допускаете тут ошибку, полагая, что если говорят, что, например, SP каждый на свой уровень, то он реально хранится раздельно и подключается именно конкретный в каждый момент.
                                                В ранних процессорах так и было. Именно за счёт этого EXX, «меняющая» местами 4 регистровых пары в 8080 отрабатывает всего за 4 такта (вот тут есть немного на эту тему).

                                                И даже для комплекта для FIQ это скорее всего на момент перекидки использование прямой связи между тремя версиями одного регистра.
                                                В ARM2 точно не так. Они там за задержки очень переживали. Аж даже ради этого сотворили архитектуру где FIQ не берёт адрес инструкции откуда-то, а может прямо код иметь расположенный по адресу 1C: The FIQ routine might reside at 0000001CH onwards, and therebay void the need for (and execution time of) a branch instruction.

                                                Но мне кажется из всех суперскаляров все эти извращения выпилили.

                                                • beeruser
                                                  /#21662786 / +1

                                                  Именно за счёт этого EXX, «меняющая» местами 4 регистровых пары в 8080 отрабатывает всего за 4 такта

                                                  Z80.

                                                  Аж даже ради этого сотворили архитектуру где FIQ не берёт адрес инструкции откуда-то, а может прямо код иметь расположенный по адресу 1C:

                                                  Таблица векторов прерываний содержит не адрес, а инструкции, что часто использовалось в те времена (в вами же упомянутом 8080), плюс упрощало создание процессора.
                                                  Такая простая мелочь позволяла вдвое(?) сократить время реакции на прерывание.

                                                  • khim
                                                    /#21663254

                                                    Такая простая мелочь позволяла вдвое(?) сократить время реакции на прерывание.
                                                    Только в случае пустого обработчика. Что в реальном мире несколько… эээ… бессмысленно. Очередная победа маркетологов над здравым смыслом.

                                                    • beeruser
                                                      /#21663768

                                                      Время реакции не зависит от размера обработчика.

                                                      Очередная победа маркетологов

                                                      Тогда и слов-то таких не знали.
                                                      Думаю вам стоит вернуться в прошлое [шутка] и убедить Sophie Wilson потратить ещё немного транзисторов чтобы сделать как вам нравится.

                                                      • khim
                                                        /#21663878

                                                        Время реакции не зависит от размера обработчика.
                                                        То есть, я извиняюсь, как? Процессор у вас без исполнения какого-то кода что-то, внезапно, начинает делать?

                                                        Зависит, конечно.

                                                        Правда в этой истории есть и «условно счастливый» конец: вдрызг проиграв «гонку мегагерц» (во многом как раз из-за «клёвых находок» типа 26-битной адресации и FIQ) процессоры ARM оказались востребованы в бытовой электронике. И да — вот как раз там все эти штучки оказались «к месту».

                                                        Думаю вам стоит вернуться в прошлое [шутка] и убедить Sophie Wilson потратить ещё немного транзисторов чтобы сделать как вам нравится.
                                                        Даже если вы вернётесь в прошлое вы там никакой «Sophie Wilson» не найдёте. Вот с Роджером можно бы и поговорить — впрочем не слишком ясно о чём: ресурсов на то, чтобы создать что-то конкурентоспособное в сравнении хотя бы с 80486м у Acorn не было, а уж про Pentium (который появится через несколько лет) — тягаться и совсем бессмысленно.

                                                        Так что как раз FIQ можно и оставить (хотя на десктопе он не нужен), а вот как раз если что-то и столо бы предвидеть — так это то, что 64MiB окажется «небольшим объёмом» куда быстрее, чем казалось в 1985м…

                                                        Тогда и слов-то таких не знали.
                                                        Знали, конечно. И FIQ как раз под то, чтобы можно было заявить о том, как всё круто в пресс-релизах делался. А что он, потом, реально пригодился — но только уже после того, как Acorn обанкротился… это скорее счастливая случайность…

                                                        • beeruser
                                                          /#21666520

                                                          То есть, я извиняюсь, как?

                                                          Я подразумевал время до выполнения первой инструкции ISR.

                                                          вдрызг проиграв «гонку мегагерц» (во многом как раз из-за «клёвых находок» типа 26-битной адресации и FIQ)

                                                          Казалось бы, причём тут 26-битная адресация и мегагерцы. Интел выиграл гонку мегагерц за счёт своего производства. Acorn же не имел таких возможностей.

                                                          а вот как раз если что-то и столо бы предвидеть — так это то, что 64MiB окажется «небольшим объёмом» куда быстрее

                                                          ARM был сделан чтобы решать проблемы «здесь и сейчас» а не когда-то в будущем.
                                                          Вы бы просто физически не могли подключить столько памяти к ARM2/3 и т.д.
                                                          68000 выдавал 24 бита адреса на шину по тем же причинам — экономия транзисторов.
                                                          Если соблюдать элементарную гигиену, программам решительно пофиг, сколько там бит выведено на шину адреса. Мои программы под 68к работают на любом другом.

                                                          Давайте лучше вспомним «640КБ хватит всем». A20 gate и прочие красоты х86.

                                                          Знали, конечно. И FIQ как раз под то, чтобы можно было заявить о том, как всё круто в пресс-релизах делался.
                                                          Пресс-релиз в студию! Иначе это враньё.
                                                          Продавался компьютер целиком, а не контроллер прерываний.
                                                          ISA спроектирована (тогда ещё Роджером) в одиночку для решения необходимого круга задач, а вовсе не для удовлетворения маркетологов. Цель была получить RISC-овый 32-битный «6502» с быстрой подсистемой памяти. Там всё продиктовано тем, чтобы максимально эффективно работать с памятью.
                                                          В итоге получился супероптимизированный процессор, легко опережающий 386, который имел в 10 раз больше транзисторов.
                                                          Блестящая инженерная работа!

                                                          • khim
                                                            /#21668208

                                                            Казалось бы, причём тут 26-битная адресация и мегагерцы. Интел выиграл гонку мегагерц за счёт своего производства. Acorn же не имел таких возможностей.
                                                            Acorn не имел таких возможностей, но партнёры ARM (DEC, Samsung и даже, внезапно, Intel) — несомненно имели.

                                                            Однако их процессоры, внезапно, не имели совместимости с 26-битным режимом, под который были заточены как RiscOS, так и куча софта.

                                                            Вы бы просто физически не могли подключить столько памяти к ARM2/3 и т.д.
                                                            Речь идёт не о подключении такого количетва памяти, а возможности написания софта, способного столько памяти использовать.

                                                            В ранние модели на 80386 тоже больше 16MiB не впихнуть, но Windows 3.1 может использова 512MiB… а программы для Windows 3.1 работают и в Windows 10, которая может и больше.

                                                            68000 выдавал 24 бита адреса на шину по тем же причинам — экономия транзисторов.
                                                            Однако же 68000 не пытался в те же 32 бита запихнуть ещё и статусные биты и потому апгрейд тех же Маков до 68020 прошёл без титанических усилий, требовавших переписать вообще всё.

                                                            Если соблюдать элементарную гигиену, программам решительно пофиг, сколько там бит выведено на шину адреса.
                                                            Как вы собрались «соблюдать элементарную гигиену», если на ARM2 флаги процессора засунуты в R15, слиты в единое целое с адресом инструкции и сохраняются просто командой STR как единое целое?

                                                            Давайте лучше вспомним «640КБ хватит всем». A20 gate и прочие красоты х86.
                                                            Ну там как раз всё понятно: чего вы вообще хотите от «заглушки для сокета»? 8086, как известно, был создан только для того, чтобы ну хоть что-то противопоставить Z80 и прочим всяким 68000, пока настоящий ответ готовился.

                                                            Что, собственно, и позволило Apple выжить и лет 10 просуществовать в статусе «премиальной платформы» — аж до 1995го года.

                                                            В итоге получился супероптимизированный процессор, легко опережающий 386, который имел в 10 раз больше транзисторов.
                                                            Блестящая инженерная работа!
                                                            Работа-то, может, и блестящая, но не без косяков. В частности FIQ (вот именно дизайн с размещением кода прямо по адресу 1C) и 26-битный режим — очевидные ошибки.

                                                            Хотя в целом — да, куда более качественная разработка, чем, скажем, 8086…

                                          • rogoz
                                            /#21661790 / +1

                                            Прерывание — оно, знаете ли… прерывает. И потому должно работать быстро. Соответственно обычные регистры x64 сохраняет
                                            А точно сохраняет? Вроде же выпилили на х64 аппаратное переключение задач, точно должно сохраняться CS,RIP,RFLAGS, а дальше ручками наверно (даже pushad выпилили).

                                            • khim
                                              /#21661960

                                              Строго говоря вы правы: сохраняет действительно не процессор, а операционная система. Спасибо за поправку.

                                              Но с практической точки зрения — это без разницы: важно что их кто-то да сохраняет. А вот x87/SSE регистры — не сохраняет никто… но это не значит, что в них нужно, тайком от мамы, залезать «через задний проход»… нет — это значит, что в них не нужно лазить. Совсем.

                                              • VerdOrr
                                                /#21666586

                                                не сохраняет никто…
                                                Хм…
                                                Сохраняемые регистры вызываемого и вызывающего объектов
                                                Регистры RAX, RCX, RDX, R8, R9, R10, R11, XMM0-5 и верхние части YMM0-15 и ZMM0-15 рассматриваются как изменяемые и должны считаться уничтоженными при вызовах функций (если иное не обеспечивается защитой при анализе, например при оптимизации всей программы). В AVX512VL регистры ZMM, YMM и XMM 16-31 являются изменяемыми.
                                                Регистры RBX, RBP, RDI, RSI, RSP, R12, R13, R14, R15 и XMM6-15 считаются неизменяемыми и должны быть сохранены и восстановлены с помощью функции, которая их использует.
                                                docs.microsoft.com/ru-ru/cpp/build/x64-calling-convention?view=vs-2019

                                                • khim
                                                  /#21668218

                                                  Кто-то же этот бред ещё и плюсует… Вы не заметили, что мы тут, внезапно, обсуждаем обработчик прерываний в драйвере? А вовсе не вызов функций? Какое к нему имеет отношение процитированный вами документ?

                                                  • VerdOrr
                                                    /#21669060

                                                    Действительно, просматривая только свежие сообщения, выпал из контекста. Прошу прощения.

                                      • khim
                                        /#21661292

                                        Не восстанавливать все пользовательские регистры опасно утечкой данных, потому что в стандартном соглашении вызова те регистры, что args + result + scratch, никто не чистит, а в callee-saved, наоборот, может что-то лишнее притечь ядру… опасно.
                                        Абсолютно безопасно. Задаёте опцию -mno-sse — и нет проблем, никаких утечек.

                                        • netch80
                                          /#21661680

                                          > Абсолютно безопасно. Задаёте опцию -mno-sse — и нет проблем, никаких утечек.

                                          Общие регистры вы принципиально игнорируете? В них обычно сильно более интересные данные, чем в SSE :)

                                          В текущем коде их, насколько вижу, восстанавливают равным значениям на входе.

                                          • khim
                                            /#21661842 / +1

                                            В текущем коде их, насколько вижу, восстанавливают равным значениям на входе.
                                            Совершенно верно — а поскольку их восстанавливают, то утечек быть не должно (если забыть про Spectre).

                                            А вот x87 и SSE регистры обработчики прерываний просто не должны трогать — и всё.

                                            Даже пресловутый драйвер RAID в Linux не использует SSE регистры внутри обработчика прерываний.

                                • netch80
                                  /#21658794

                                  > FXSAVE, которая, внезапно, появлась аж в Pentium II (то есть до изобретения SSE даже).

                                  Ага, вот где меня заглючило — решил по кривым описаниям, что она появилась позже SSE. Спасибо, тогда полностью согласен.

                  • khim
                    /#21656848 / +1

                    Что мешало сделать SSE-иструкции просто копией AVX-инструкций с двумя операндами?
                    Простите что? SSE появился в 1999г, AVX в 2011.
                    Простите. Голова. Мозги. Думать.

                    На процессоре с 256-битными регистрами, внезапно, AVX есть всегда есть. По определению. И если бы SSE инструкции были бы переопределены внутри процессора как 128-битные инструкции с двумя операндами — совместимость не пострадала бы ни на йоту.

                    Вместо этого… имеем вот весь этот геморой.

                    А зачем бить себя лопатой по голове использовать AVX и SSE одновременно?
                    Ну, например, чтобы не тащить с собой две копии всех функций: для «старых» процессоров и для «новых».

                    • beeruser
                      /#21662090

                      Простите. Голова. Мозги. Думать.

                      Какой вы нервный, однако.
                      Я не счёл нужным ставить табличку [сарказм]. Похоже что зря.

                      И если бы SSE инструкции были бы переопределены внутри процессора как 128-битные инструкции с двумя операндами — совместимость не пострадала бы ни на йоту.

                      AVX-128 и SSE это разные наборы команд. Да, SSE могли бы чистить старшую половину (например, в зависимости от режима работы процессора), но так не сделали, и с этим нужно жить.

                      например, чтобы не тащить с собой две копии всех функций: для «старых» процессоров и для «новых».
                      И ничего бы не изменилось — AVX-128 более совершенный набор чем SSE.

        • tyomitch
          /#21653300

          На числа невозможно заявить интеллектуальную собственность.
          Грубо говоря, ничто не мешает конкуренту Intel сделать чип с поддержкой SSE и продавать его под названием «SSE-256», даже если Intel под «SSE-256» понимает нечто совсем иное.

          Поэтому Pentium вместо i586, поэтому AArch64 вместо ARM-64, и т.д.

  13. wormball
    /#21653234 / +2

    > сведение en.wikipedia.org/wiki/X86_instruction_listings в одну табличку:

    Теперь хорошо бы сие изображение в ту же википедию запостить.

  14. Tsimur_S
    /#21653290

    Это канал про анимэ? Раз уж тут пошла такая пьянка, подскажите пожалуйста курс/книгу который бы последовательно и подробно разложил по полочкам всю следующую информацию: виды плат(fpga, asic, микропроцессоры), архитектуры(фон неймана, dataflow), наборы команд и их архитектуры(risc/cisc и тд) и микроархитектуры(условно чем отличается zen от conroe). Хочется как-то разбить по категориям эту кашу в голове.

  15. robomakerr
    /#21663288

    Оказывается, закон Мура был о числе инструкций)