1. Си / Говнокод #27812

    +5

    1. 01
    2. 02
    3. 03
    4. 04
    5. 05
    6. 06
    7. 07
    8. 08
    9. 09
    10. 10
    11. 11
    12. 12
    13. 13
    14. 14
    15. 15
    16. 16
    17. 17
    18. 18
    19. 19
    // http://cmustdie.com/ - баттхерт анскильных лалок, неосиливших сишку
    
    // Возьмём следующий фрагмент кода на языке Си:
    
    int x = 1;
    x = x << sizeof(int) * 8;
    
    // Попробуем предположить, какой результат у нас получится. Допустим, мы скомпилировали этот
    // код для процессоров архитектуры ARM. Инструкция битового сдвига в рамках этой аппаратной
    // платформы определена так, что итоговым значением переменной "x" должен быть "0". С другой
    // стороны, мы можем транслировать нашу программу в машинный код архитектуры x86. И уже там 
    // битовый сдвиг реализован таким образом, что значение "x" не изменится и останется равным
    // "1". Мы могли бы сделать вывод, что результат работы данного фрагмента кода зависит от
    // того, для какой аппаратной платформы мы его скомпилировали. Но на самом деле это не так.
    
    // В действительности данный фрагмент кода может быть обработан компилятором любым возможным 
    // и невозможным образом. Причина в следующем: согласно тексту стандарта языка Си битовый 
    // сдвиг на величину, большую или равную размеру выражения в битах, является неопределённым
    // поведением. Получается, нет никакой гарантии, что этот кусок кода вообще будет работать.

    Охуеть конечно

    Запостил: j123123, 12 Ноября 2021

    Комментарии (40) RSS

    • > Для своей операционной системы разработчик решил использовать собственную реализацию функции memset. Но он не учёл, что в процессе трансляции компилятор gcc обнаружит в этом коде весьма заманчивую возможность для оптимизации. Фактически функция была в итоге преобразована к следующему виду:

      void *memset(void *ptr, int value, size_t num)
      {
          return memset(ptr, value, num);
      }


      > Вполне вероятно, что среди разработчиков компилятора gcc были непревзойденные мастера софистики. В любом случае способности компилятора к оптимизациям явно превосходят все доступные человеческому разуму пределы.

      Какой багор )))
      об этом кстати есть баг: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56888
      memcpy implementation optimized as a call to memcpy
      Можно memcpy на ассемблере написать, тогда нихуя уже не заоптимизируется
      Ответить
      • stackoverflow же?
        Ответить
      • Лол, я тоже на эту рекурсию налетала )))
        Ответить
      • > current memcpy implementation is sufficiently overcomplicated to avoid getting detected by the optimizer as a memcpy

        Какой багор )))
        Ответить
        • Это нужно было запостить с учетки "Хардкорный петух"
          Ответить
        • Т.е. гцц убивает только анскилльную тривиальную реализацию, а с царскими всё норм.
          Ответить
    • Я охуел.
      Ответить
    • как вообще люди живут без ассемблерной команды ROR не помню какая там была на zx spectrum
      Ответить
      • ... и без того, что делают MUL и однооперандный IMUL в x86.
        При мне кое-кому приходилось вычислять, сколько процентов от одного большого числа составляет другое (потенциально не влезающее в 4 байта при умножении на 100). И они там нагородили что-то плавающее.
        Кстати, у каких-нибудь компиляторов языков уровня выше ассемблера есть гарантия, что при умножении 4-байтовых чисел и использовании результата как 8-байтового задействуются вышеупомянутые инструкции?

        ЗЫ при чём здесь zx spectrum, если ROR, ROL и даже RCR с RCL есть и в x86?
        Ответить
        • Forth умеет умножать 2 одинарных ячейки и получать двойную, а также делить двойную на одинарную. Других реальных примеров я не помню.
          Ответить
        • какой противный аккаунт, аватарка и манера речи
          Ответить
        • Ну преобраозовать во флоат или __uint64 самое простое (если не на ассемблере писать, и не под микроконтроллер, где может сразу плавающая библиотека прилинковаться). Если точность не нужна, можно тупо if (total > 0xFFFFFF) done >>= 8, total >>= 8; ну а если нужно, чтобы результат полностью соответствовал, то нужно аккуратно.
          Ответить
    • И вообще, даже в своем примере
      int x = 1;
      x = x << sizeof(int) * 8;

      лалки проявили свою анскильность. Ведь CHAR_BIT есть:
      int x = 1;
      x = x << sizeof(int) * CHAR_BIT;

      и он не везде 8
      Ответить
      • И вообще не стоит бездумно двигать знаковый инт влево...
        Ответить
    • Барыня, барыня,
      Сударыня-барыня,
      Если баринъ при цепочке,
      Значит, баринъ безъ часовъ.
      Ответить
    • А почему умножить, а не взять всё и поделить?
      Ответить
    • https://thephd.dev/c-the-improvements-june-september-virtual-c-meeting
      N2709 - Adding a Fundamental Type for N-bit Integers

      _BitInt(N), where N is the number of bits you want in an integer, is a really, really big deal for C in my opinion. There have been entire extensions built around C for analyzing the compile-time information available to integers in C programs. Most often, that information is used to determine the effective range of integer operations, and strip off those bits for savings in e.g. FPGAs or other custom hardware. Entire optimizations go into “how many bits is this really using and can I get some speed if I rearrange these 4 integers to instead be a smaller set of bytes I can perform parallel instructions with?”. Unfortunately, all of that has been stuck fairly fundamentally in the land of “special magic C users cannot hope to touch”.

      Until now.

      _BitInt(N) makes C suitable for hardware and embedded work, as it provides something that BitVec Author and Embedded Badass myrrlyn explains succinctly:


      Какое битоебство )))

      Интересно, в кресты это перенесут потом?
      Ответить
    • Они это кстати на хабр выставили, и я туда им даже написал:
      https://habr.com/ru/post/592233/comments/#comment_23781835
      Вот зацените че пишут:
      > Паскаль всегда был и остается языком высокого уровня, поэтому размер типа Integer там не указан намеренно.
      Ответить
      • Т.е. си с его int и long -- тоже язык высокококого уровня?
        Ответить
        • Да хер их знает. Вот в джаве вроде размер Int указан явно, наверное это язык низкого уровня
          Ответить
          • Однозначно. В другой статье на хабре джаву относили к сложным низкоуровневым языкам, а хуйни на хабре не напишут.
            Ответить
      • > и я туда им даже написал

        - Хабрапидор! - в один голос заорали все 3 пользователя ГК.

        - Хабрапидор! Хабрапидор! Хабрапидор!

        Кто-то включил сирену. Над дверьми замигали красные лампочки тревоги. На окнах мгновенно сомкнулись плотные жалюзи. На сайте одновременно бывает полтора человека. На обеде вся эта толпа собирается на первом этаже, где яблоку негде упасть. А поэтому, как страйкер ни пытался вырвать хабрапидора из рук разъяренной толпы, ему это не удалось. По всему говнокоду стоял сплошной рев:

        - Хабрапидор!
        Ответить
        • Хабрапидоры даже формат ссылок с ГК спиздили.
          Ответить
      • В старом си размер не был указан явно, и потому borland c 3.1 это язык высокого уровня
        В современном си есть uint_t всякие, стало быть это язык низкого уровня.
        Ответить
        • зависит от того, насколько высоко лежит книжка про язык в стопке
          Ответить
          • Ты кстати программист низкоуровневый, у вас там вроде NSInteger от разрядности айфончика зависел
            Ответить
            • а может я пользуюсь NSNumber

              но вообще к obj c без защитного костюма приближаться не советую, можно подхватить что-то эдакое, низкоуровневое
              Ответить
              • Какой-то был API, где был именно NSInteger (а не объект NSNumber), и там какие-то черти соснули при переходе с четвертого айфона на пятый:)

                Низкоуровневая хуита была вроде в районе KeyChain. Там вдруг торчал CoreFoundation и сишечный API. Возможно потом починили
                Ответить
                • ну NSNumber в API это вообще зачастую дичь. нужен для того, чтобы забоксить примитив в объект, чтобы потом например сохранить в дефолтсах, не более. я-то на самом деле иронизировал.
                  Ответить
                  • Что такое NSNumber? National Socialist Number, фашик ебанный
                    Ответить
                    • Третий путь: без плавающих питухов и фиксированных полей.
                      Ответить
                    • ein Apfel! ein Job!
                      Ответить
                      • Знание немецкого тебе пригодится. Пообщаешься с Шикльгрубером, когда попадешь в чистилище, безвременно умерший. Кажется, его у вас любят.
                        Ответить

    Добавить комментарий