1. C++ / Говнокод #27022

    −1

    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
    20. 20
    21. 21
    22. 22
    23. 23
    24. 24
    25. 25
    26. 26
    27. 27
    28. 28
    29. 29
    30. 30
    #include <iostream>
    #include <string>
    
    using namespace std;
    
    struct A
    {
        uint16_t    n;
    
        uint8_t     a1:1;
        uint8_t     a2:1;
        uint8_t     a3:1;
        uint8_t     a4:1;
        uint8_t     a5:4;
    
        uint8_t     b;
    } __attribute__((packed));
    
    int main()
    {
        char v[] = { 0x1, 0x1, 0b01010011, 0x9 };
        A *p = (A*)v;
        
        cout << (uint16_t)p->a1 << endl;
        cout << (uint16_t)p->a2 << endl;
        cout << (uint16_t)p->a3 << endl;
        cout << (uint16_t)p->a4 << endl;
        cout << (uint16_t)p->a5 << endl;
        cout << (uint16_t)p->b << endl;
    }

    http://cpp.sh/6e5myf

    Битовые поля неправильно считываются.

    Запостил: YpaHeLI_, 12 Октября 2020

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

    • показать все, что скрытоПереведи на "PHP". Здесь никто не обязан знать язык для "Arduino" и прочих игрушек для школьников, увлекающихся робототехникой, нанотехнологиями и мечтающих попасть в "Сколково" (на котором верхи, к слову, просто пилят деньги и ржут над сиволапым деревенским синим быдлом, отдающим детей в "крутые" кружки и классы).
      Ответить
      • В ПХП наверное нету битовых полей.
        Ответить
        • показать все, что скрытоМне надо просто принять от клиента данные и сохранить их в базе данных; либо, напротив, выдать ему некую информацию. Нахуй мне какие-то битовые поля? В чём их прикол?
          Ответить
          • Ну вот потребует клиент сохранить половину бита — и что ты будешь со своим «PHP» делать?!
            Ответить
            • показать все, что скрытоВ какой ситуации это может понадобиться? Честно - я действительно не понимаю, что это и зачем оно нужно.
              Хотя, половина бита - это нечто невозможное.
              Ответить
              • Ну вот смотри: у Васи Пупкина есть тысяча воздушных шариков, из которых 707 — красные, а 293 — зелёные. Пётр Иванович Штольников — престарелый профессор философских наук — страдает лёгкой степенью протанопии. Опаздывая на встречу выпускников, Вася Пупкин не глядя схватил десяток шариков и выбежал на улицу. Однако в это же время совершенно случайно в городе была сильная буря, и девять из десяти шаров Васи унесло непогодой в соседний город. Примерно через три часа один из унесённых ветром шаров пролетел мимо окна Петра Ивановича Штольникова, который в этот момент любовался красивым закатом. К сожалению, из-за глазной болезни заслуженного профессора пролетающий воздушный шарик остался незамеченным Петром Ивановичем. Возможно, сложись всё иначе, и Пётр Иванович вспомнил бы, как, стоя на линейке с красивой лентой через плечо, он вместе со своей одноклассницей Людей — теперь уже, конечно, Людмилой Сергеевной — запускал в небо точно такие же воздушные шарики. Вспомнил бы — и позвонил своей старой знакомой, которая всю жизнь страшно любила поболтать. Проболтав (хотя, откровенно говоря, прослушав) с ней до темноты, Пётр Иванович раздосадованно стукнул бы себя по лбу — в магазин идти уже поздно. Поворчав для приличия, профессор щёлкнул бы выключателем ночника и спокойно заснул.
                К сожалению, пролетающий воздушный шар Пётр Иванович не заметил. С неохотой оторвавшись от окна он оделся, проверил плиту, взял ключи и вышел за дверь. Проезжающий по мокрому асфальту серебряный «Hyundai Solaris» не справился с управлением и не успел затормозить. Петра Ивановича не стало.


                Вот это и есть примерно половина бита.
                Ответить
            • > половину бита

              От половины бита и сишник взвоет. Хотя и такое бывает, конечно.
              Ответить
              • У меня есть идея: половина бита — это такое значение, которое не имеет смысла без его второй половинки.

                Вот у нас есть «половина бита» b1 (в памяти она занимает целый бит — будем считать это выравниванием) и «половинка бита» b2, а в программе везде используется только (b1 xor b2) или (b1 == b2). Тогда, зная только b1 или только b2, мы не сможем предугадать поведение программы, а зная значения обоих, будем знать результат.
                Ответить
                • комплексный бит, вещественная часть, мнимая часть

                  при bitwise-операциях может стать отсутствием одного бита
                  Ответить
                • Ну да, примерно так это и работает во всяком энтропийном кодировании. По значению b1 мы всегда можем предсказать значение b2. Т.е. мы упихали 2 значения в один бит. И можно сказать, что каждое из них занимает по половине.
                  Ответить
                  • > упихали 2 значения в один бит
                    Упихал два значения — 1 и 0 — в один бит, проверь.
                    Ответить
        • Поэтому я за "ПХП".
          Ответить
      • показать все, что скрыто
        <?php
        
        class AFlags
        {
        	const A1 = 0b1;
        	const A2 = 0b10;
        	const A3 = 0b100;
        	const A4 = 0b1000;
        	const A5 = 0b11110000;
        };
        
        class A
        {
        	public $n;
        	public $a_flags;
        	public $b;
        };
        
        function main()
        {
        	$a = new A();
        	$a->n = 0b000000100000001;
        	$a->a_flags = 0b01010011;
        	$a->b = 0x9;
        	
        	echo ($a->a_flags & AFlags::A1) ? 1 : 0, "\n";
        	echo ($a->a_flags & AFlags::A2) ? 1 : 0, "\n";
        	echo ($a->a_flags & AFlags::A3) ? 1 : 0, "\n";
        	echo ($a->a_flags & AFlags::A4) ? 1 : 0, "\n";
        	echo ($a->a_flags & AFlags::A5) ? 1 : 0, "\n";
        }
        
        main();
        
        ?>


        Хз зачем я это сделал
        Ответить
        • > &

          Ну вот и на сишке так сделай и всё будет норм. Только сдвиг ещё добавить надо, если значение А5 интересно.
          Ответить
          • Да я так всегда и делал, тимлид сказал лучше битовые поля юзать.
            Чисто чтобы потом людям удобнее читать было, если нужно станет, видимо.
            Я уж не совсем новичок, лет 6-7 уже опыт на крестах.
            Ответить
            • > тимлид сказал лучше битовые поля юзать
              Ну если их не сериализовывать (или сериализовывать только в рамках одного приложения на одной машине) — действительно лучше же.
              Ответить
            • > лучше битовые поля юзать

              Если тебе пофиг на их внутреннее представление - да, они довольно удобны.

              Но тебе же не пофиг, раз ты полез байты разглядывать. Видимо пытаешься совместимость с чем-то запинать. В этом случае я бы не стал юзать битовые поля.

              Хотя подогнать порядок можно, конечно. И в пределах одного ABI он не уплывёт. Конпеляторы, соблюдающие одно ABI, всё-таки стараются чтобы сишные интерфейсы между ними не ломались.
              Ответить
      • Никогда раньше не видел такое стремление умереть в страшных муках
        Ответить
    • А в чем проблема?
      Ответить
    • У кого последний MSVC стоит проверьте плиз, а я пойду на шланге скомпилю это.
      Видимо багрепорт придется писать.
      Ответить
      • 9.6 Bit-fields

        Allocation of bit-fields within a class object is implementation-defined. Alignment of bit-fields is implementation-defined.

        Удачного багрепорта.

        З.Ы. Именно поэтому я никогда не юзаю битфилды.
        Ответить
        • Но там же хуйня получается.
          Ответить
          • 0101 0 0 1 1
            Где хуйня? Просто порядок не совпадает с твоими ожиданиями. Или дока к конкретному конпелятору обещала другой порядок?
            Ответить
            • именно эта поебень заставила меня много лет тому назад делать на шаблонах битовые поля в структуре, чтобы не зависело от компилятора и, главное, бесплатно проходило через границу слова внутри структуры

              при этом чтобы на высоком уровне оставался доступ через foo.a = 100;
              Ответить
              • показать все, что скрытоЯ не понимаю, о чём ты.
                Ответить
              • кстати, я помню, из-за того, что проффессия прогграммиста была типа илитарной, а должность крестуха уж тем более, а контора нанимала 1 крестоблядь в столетие, я после собесов на домашнее задание именно эту задачу и давал лол
                Ответить
            • Ну я понял, он на младший бит ссылается, так как биты у в x86 в big-endian.
              Значит он будет в конце байта.
              Ответить
              • Не-не-не. С endian это никак не связано.
                Ответить
                • А с чем?
                  Ответить
                  • Х.з., с фазой луны? Короче порядок байт и порядок бит - разные вещи.

                    Ну и x86 всё-таки little-endian, младшим байтом вперёд.
                    Ответить
                    • Я про порядок битов говорю, а не про порядок байт.
                      Ответить
                      • показать все, что скрытоНе беспокойся, я не понимаю ни то, ни другое. Мне всё равно.
                        Ответить
                      • А порядок битов может зависеть от компилятора. Он не обязан совпадать с принятым для данного процессора.
                        Ответить
                        • Не порядок битов, а порядок упаковки битовых полей в структуру.

                          Порядок битов - это скорее о каком-нибудь последовательном порту, в который мы биты один за другим срём. А с точки зрения проца порядка битов обычно и нет. Он их все одновременно выгружает.
                          Ответить
                          • Я вспомнил, как компиляторы хранят локальные переменные функции (если на них брать указатели, чтобы он не смог их оптимизировать в регистр):
                            • Одни компиляторы пушат в стек переменные по очереди, так что последняя переменная находится ниже всех.
                            • Другие компиляторы сразу выделяют память в стеке (sub rsp, константа) и размещают переменные в порядке их объявления, так что последняя переменная оказывается выше всех.

                            И вроде оба способа имеют право на существование, потому что из хорошего кода есть доступ только к переменным по отдельности, по их имени, а доступа к локальным переменным как к массиву нет.

                            Значит, и тут в хорошем коде должен быть доступ только к битовым полям по отдельности, по их имени, чтобы не думать о порядке упаковки?
                            Ответить
                            • Ну тип того. Тут ведь между ними ещё и паддинг может быть.
                              uint8_t a: 1;
                              uint8_t b: 8;
                              uint8_t b: 7;
                              З.Ы. gcc вот даже ругается, что паддинг битовых полей был изменён в 4.4, если добавляешь packed.
                              Ответить
                              • Какой багор )))

                                Значит, для сериализации нужно собирать байты ручками?
                                Ответить
                                • Да не, в пределах одного ABI можно аккуратно запинать битовые поля. Самому битовые и байтовые паддинги расставить, типы правильно подобрать и т.п. Но стоит ли оно того?
                                  Ответить
                            • показать все, что скрытоvanished
                              Ответить
                              • В «Турбо Паскале» отказались от проверки дескриптора вариантных полей записи, чтобы они работали, как union в сишке (в популярных на тот момент реализациях сишки, а не в стандарте). Всё правильно сделали?
                                Ответить
              • >> биты у в x86 в big-endian

                Приведите реальные примеры инструкций x86, у которых есть доступ к битам по номеру.
                Ответить
          • https://gcc.godbolt.org/z/j85PvM
            mov     rax, qword ptr [rip + a]
            movzx   esi, byte ptr [rax + 2]
            and     esi, 1                        ; a1
            mov     edi, offset .L.str
            xor     eax, eax
            call    printf
            mov     rax, qword ptr [rip + a]
            movzx   esi, byte ptr [rax + 2]
            shr     esi
            and     esi, 1                        ; a2
            mov     edi, offset .L.str
            xor     eax, eax
            call    printf
            mov     rax, qword ptr [rip + a]
            movzx   esi, byte ptr [rax + 2]
            shr     esi, 2
            and     esi, 1                        ; a3
            mov     edi, offset .L.str
            xor     eax, eax
            call    printf

            Где здесь хуйня, YpaHeLI_?

            Берём 0b01010011, наименее значащий бит — первое битовое поле, следующий за наименее значащим — второе, потом третье, и так далее, и тому подобное. a5 получается простым сдвигом вправо на 4 бита.
            Ответить
            • показать все, что скрытоБлядь, как всё сложно. Нахуй вы себе мозги ебёте этим говном?
              Ответить
              • Какого хуя ты приперся в ветку C++ и начал здесь доказывать что C++ это хуйня ебанная для собак и говноедов? Иди дальше оптимизировать хранение строчки в мускуле называя это достижением века
                Ответить
                • Экий багор )))
                  Ответить
                • показать все, что скрытоvanished
                  Ответить
                  • А mysql скалируется горизонтально?
                    Ответить
                    • показать все, что скрытоvanished
                      Ответить
                      • формально, существуют с 4ТБ памяти
                        Ответить
                        • показать все, что скрытоvanished
                          Ответить
                          • ебанись

                            ну это, походу, вот такой вариант
                            https://www.supermicro.com/en/products/bigtwin?pro=cpu%3D2%26cputype%3D3%26nodes%3D4%26dimm%3D24%26storageinterface%3D57

                            4 ноды по 2 цпу (= 8 цпу) и 24 слота памяти на ноду (=96 слотов)
                            если заебенить 256ГБ модули, как раз 24ТБ и выйдет

                            а зионы 28 ядерные (8*28*2), чтобы получить 448 vcpu
                            Ответить
                            • * CPU будут работать в режиме энергосбережения
                              Ответить
                              • ну и память наверняка load reduced
                                Ответить
                                • Интиересная какая штукаа.

                                  Выходит, DRAM контроллер управляет не чипами, а управляет он буфером, который эмулирует для него этакий виртуальный "ранк".

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

                                  Впрочем, там наверное такие кеши, что это и не важно.
                                  Ответить
                              • А cpu они оверселльнут другим клиентам.
                                Ответить
                  • Но ведь действительно: оптимизация - это путь нищебродов, неспособных арендовать сервер подороже и вынужденных тщательно продумывать длину поля в БД, отказывающих себе в "mediumtext" и "bigint", тяжело вымучивающих каждый индекс, и так далее.
                    Ответить

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