🔥

Тред (Дмитрий Бежецков)


“Пфф, да как два байта дописать.” Людям, которые не знакомы с внутренней кухней разработки браузеров или компиляторов иногда бывает очень непонятно почему вроде казалось бы очевидные вещи делаются ну очень долго.

Например, средний инженер гугла может потратить всю свою карьеру только на то, чтобы в google drive интерфейсе правильно работала кнопка сохранить.

Другой пример парольный менеджер в браузере. Рядовой фулстек разработчик скажет что это по сути всего лишь бд для паролей, но стоит вам начать его писать как вы поймете что даже очень хорошей командой из 4-5 разработчиков пишется он за 1.5-2 года.

Вот в прошлом году мне поручили сделать оптимизацию в wasm, которая помимо всего прочего требовала поменять ABI в SpiderMonkey. SpiderMonkey это движок JS в браузере firefox.

ABI это application binary interface, т.е. это что-то похоже на api, в том смысле что это тоже набор соглашений о том, как будет происходить взаимодействие частей системы.

В отличии от API ABI работает на более низком уровне и отвечает на такие вопросы: а как физически передавать параметры функции? в какие регистры их распихивать? как вообще представлять функцию на стеке и т.д.

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

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

В SM то и дело в разных частях кода раскидано знание о abi: где и в каких регистрах ожидаются значения и т.д. Так как wasm использовал системное abi пришлось вручную обрабатывать каждое такое место и разделять новое abi с двумя байтами и системное.

Делать платформенно-зависимые правки и фиксить баги для arm32, arm64, x86 и конечно x86_64, благо mips и mips64 мне не пришлось трогать. Да, низкоуровневую часть кода все еще надо править под каждую платформу, даже в 2к20.

Менять и фиксить баги в двух компиляторах - Baseline и Ion. Это было относительно легко, потому что и Baseline и Ion живут в обном репозитории mozilla. Внезапно пришлось синхронизовать изменения с компилятором на rust - Cranelift, который живет в отдельном репозитории :(.

Эх, еще от моих правок отвалился аллокатор регистров. Аллокатор регистров это компонента компилятора которая обычно очень сложно написана... Пришлось снимать логи и общаться с людьми в чате, в итоге баг оказался в самом аллокаторе...

Не сильно сложный пункт, но нужно помнить что разные OS требуют разного ABI, особенно windows с его shadow stack, так что это тоже надо поддержать.

Чтобы это все залить в браузер надо разбить все работу на очень маленькие кусочки и заливать по отдельности на ревью. Никто не будет ревьюить большой PR.

Наконец после заливки ваш код может внезапно упасть через неделю на какой-нибудь конфигурации OS + arch, например потому что фазер или тестер найдет что-нибудь, так что вливать все это надо не один раз. На картинке видно количество моих провалов для этой задачи :)
notion image

Подытоживая могу сказать что это не все так сложно как и я описал. Комитить в большие проекты это как играть в dark souls, сначала все сложно, часто умираешь, но потом, привыкаешь и начиаешь играть лучше и получать от этого непередоваемое удовольствие.