Панчулу не показывайте

На кикстартере собирают (точнее уже собрали) деньги на книжку-игрушку с демонстрацией работы логических элементов:

https://www.kickstarter.com/projects/babyengineering/computer-engineering-for-babies

Про кофе

Регулярно в фейсбуке встречаю ужасы от путешествующих по Италии, которые то ли не в то время суток заказали капуччино, то ли неправильно поставили ударение в слове латте, то ли вообще заказали неизвестный за пределами МКАД лавандовый раф. Так вот, в любое время дня и ночи можно совершенно спокойно заказывать caffe corretto — ну и напомню, что по-русски подобное называется «медведь» и описано в мореманских рассказах Станюковича — «стакан крепкого черного кофе, на треть разбавленного ромом» (а вообще и на половину вполне себе неплохо).

А как это называется?

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

Электронный документооборот

Пока тут Исавнин с Артамоновым кидают друг в друга какахами на хабре из-за дистанционного электронного голосования — реальные электронные сервисы «от государства» выглядят примерно так:

Прекрасно все, особенно ссылка через левый совершенно «сокращатель ссылок» на гуглодиск.

UPD А за «так же» надо вообще убивать.

Имею вопрос

А как играть в бинго 3*4?

Ну и чтоб два раза не вставать — обратите внимание, что непьющий, молодой и неженатый препод — не абьюзер, без этого бинго не складывается. Видимо, предполагается, что можно его захомутать и окольцевать. Заодно напомню, что «молодой преподаватель» по документам минобра — это до 35 лет; но если он доктор наук — то молодым считается до 40.

Что-то #MeToo в этом году никакое

Хотя вот истории про Хохла, могущественного начальника котлопункта просто волшебно хороши. Например:

https://m.vk.com/wall-195334579_801 — вдали от мужа нахуяриться коньяком с тем самым Хохлом, невероятным половым гигантом? Умею, люблю, практикую! Спустя 13 лет мадам стала испытывать по этому поводу некое странное чувство, когда все воспитание говорит тебе, что ты хорошая девочка, а обстоятельства указывают на то, что ты — конченная блядь; в психологии это вроде бы называется фрустрацией и когнитивным диссонансом. Выход? Разумеется, объявить Хохла ужасным абьюзером!

Продолжения (а в MeToo продолжения просто обязательны, без них никак нельзя) менее насыщены сюжетно, но прекрасны своими определениями:

https://m.vk.com/wall-195334579_803 — «Тут очень важно не забывать фигуру и вес слова этого человека на ББС: он там высоко на Олимпе среди прочих богов этого замкнутого места и действительно мановением пальца может сделать жизнь любого нижестоящего человека адом»

https://m.vk.com/wall-195334579_807 — «Хохол — очень харизматичный и могущественный человек, который заведовал всей едой, принимал заказы на доставку с большой земли (продрейс), и который, если ты ведёшь себя хорошо, может привезти тебе сигареты.»

Видать, совсем плохо жилось на биостанции, раз заведующий котлопунктом был «высоко на Олимпе» и ему отдавались за еду и сигареты.

PS Интересно, пропустит ли фейсбук ссылку на пост, где много раз встречается слово «хохол»?

1000 верст, осень 2021

Узнал инсайдерскую информацию про маршрут осенних «1000 верст» в этом году. Информация заключалась в следующем — поедем в город Кашин, один из судейских пунктов будет находиться у проходной ликероводочного завода, а фирменный магазин «Вереска» находится в центре города. Ушел готовиться и смотреть видеоролик с дегустацией кашинских настоек, дичайше котирующихся среди автоспортсменов:

PS Ночевка, совмещенная с традиционным для 1000 верст феерическим бухичем, будет в Рыбинске.

Волшебные константы, часть 2

Мне так понравилось разнообразие мнений по поводу написанного leetspeak-ом слова Bootload (там, где я спер этот скриншот, срач был под полторы сотни комментов), что предлагаю обсудить вот этот кусок кода, 13 лет в практически неизменном виде существующий в довольно популярном опенсорсном проекте:

Хотя… Пожалуй, обсуждать, по какой причине господин Mathieu Lacage старательно расписал enum для разных значений SUBTYPE_CTL_*** и не стал так делать для SUBTYPE_MGT_*** и SUBTYPE_DATA_*** будет довольно скучно (ответ: потому что мудак), а было бы забавней обсудить, как и почему для того, чтобы два байта отослать — я не вру — вот эти два байта октета:

— надо городить аж вот такую фигню:

uint8_t m_ctrlType;     ///< control type
uint8_t m_ctrlSubtype;  ///< control subtype
uint8_t m_ctrlToDs;     ///< control to DS
uint8_t m_ctrlFromDs;   ///< control from DS
uint8_t m_ctrlMoreFrag; ///< control more fragments
uint8_t m_ctrlRetry;    ///< control retry
uint8_t m_ctrlMoreData; ///< control more data
uint8_t m_ctrlWep;      ///< control WEP
uint8_t m_ctrlOrder;    ///< control order

Вообще, я видел три подхода к проблеме заполнения всякого рода "предопределенных" байтовых и битовых структур на C и C++. Подход первый, расточительный, продемонстрирован только что - заводим по полю избыточного, но удобного размера на каждый элемент структуры, а затем пишем две функции Serialize и Deserialize, в которых занимаемся странным байтоебством примерно в таком духе (да, волшебных констант тут налепили много):

uint16_t val = 0;
val |= (m_ctrlType << 2) & (0x3 << 2);
val |= (m_ctrlSubtype << 4) & (0xf << 4);
val |= (m_ctrlToDs << 8) & (0x1 << 8);
val |= (m_ctrlFromDs << 9) & (0x1 << 9);
val |= (m_ctrlMoreFrag << 10) & (0x1 << 10);
val |= (m_ctrlRetry << 11) & (0x1 << 11);
val |= (m_ctrlMoreData << 13) & (0x1 << 13);
val |= (m_ctrlWep << 14) & (0x1 << 14);
val |= (m_ctrlOrder << 15) & (0x1 << 15);
return val;

Вариант второй - экономично-эмбеддерский, выглядит примерно так:

uint16_t frameControl = 0;
frameControl |= (CTL_TYPE_DATA << FRAME_CONTROL_CONTROL_TYPE_OFFSET) & FRAME_CONTROL_CONTROL_TYPE_MASK;
frameControl |= (CTL_SUBTYPE_DATA_QOS << FRAME_CONTROL_CONTROL_SUBTYPE_OFFSET) & FRAME_CONTROL_CONTROL_SUBTYPE_MASK;

ctrlSubtype = (frameControl & FRAME_CONTROL_CONTROL_SUBTYPE_MASK) >> FRAME_CONTROL_CONTROL_SUBTYPE_OFFSET;
/* and so on */

Отличие от предыдущего - мы работаем напрямую с этими двумя байтиками, и это довольно экономично, нам не надо работать с "тяжеловесным" по эмбеддерским меркам объектом с десятком-другим полей, а то и целой ссылкой на vtable (если обратите внимание - функции Serialize и Deserialize виртуальные). Можно обернуть это все в несколько более удобные макросы или inline-функции.

Но неужели для такой стандартной задачи человечество не придумало ничего лучше? Подобного рода херней люди занимаются вот уже несколько десятков лет, и в полувековой давности языке C есть прекрасная штука - битовые поля. В книжке 1984 года The Unix Programming Environment они описывались, как рекомендованный и правильный способ вот этого битоебства. По удобству это напоминает первый способ, с членами структуры, а по экономичности полностью аналогично второму:

struct {
    unsigned int protocolVersion : 2;
    unsigned int type : 2;
    unsigned int subtype : 4;
    unsigned int toDS : 1;
    unsigned int fromDS : 1;
    unsigned int moreFragments : 1;
    unsigned int retry : 1;
    unsigned int powerManagement : 1;
    unsigned int moreData : 1;
    unsigned int protectedFrame : 1;
    unsigned int order : 1;
} frameControl;

frameControl.type = CTL_TYPE_DATA;
frameControl.subtype = CTL_SUBTYPE_DATA_QOS;

ctrlSubtype = frameControl.subtype;
/* and so on */

Но... если на уровне "байтиков" структуры в C и C++ еще как-то предсказуемы (а проблемы с выравниванием обычно решаются с помощью #pragma pack(1)), то вот битовые поля оказываются настолько непредсказуемы, что в книжке Кернигана и Ритчи приведено осторожное предупреждение, а в любом современном учебнике настоятельно рекомендуется ими никогда не пользоваться!

Что-то мне подсказывает, что вовсе не этого хотели Керниган с Ритчи. А что вы порекомендуете?