Pull to refresh

Comments 18

В конторе где я работал году в 2008 использовалось что-то типа подхода из раздела «Куча мучений»: при экспорте фактически делался образ памяти, который писался на диск с игрой. При загрузке уровня этот образ просто линейно читался в оперативную память, затем восстанавливались указатели (для этого еще писалась табличка со смещениями всех указателей и объектов и тем кто на что должен потом указывать) и в итоге в памяти образовывались уже готовые данные игры. Никакого сложного парсинга, никаких случайных чтений с диска.
В те годы (эпоха PS3) это уже было не так принципиально, а вот на прошлых поколениях приставок, говорят, иначе было практически невозможно уложиться в ограничения по времени загрузки уровня при условии довольно медленного привода для дисков.

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

внекоторых промышленных дистрибутивах линукса была замечательная возможность «как бы перезагрузится» просто скопировать нужный дамп в оперативку.
очень удобно.
Интересно, такие дикие утечки памяти — быдлокодинг или проблемы консоли?
Проблемы кодинга. Но называть это быдлкодингом — рука не поворачивается. Всё таки разработка в сжатые сроки всегда имеет последствия. И утечки — одна из них.
Хотя трюки может быть и грязные, но спасибо разработчикам, которые смогли выжать всё до капли из платформы и дать геймерам в те далёкие годы прекрасный, красочный и весёлый Crash Bandicoot.
Да вроде нет ощущения гразных хаков от этой статьи. Всё более или менее норм.
Спасибо, эта версия ГОРАЗДО понятнее.
Наверное, здесь должна быть ссылка на известную историю про 1 байт.
Переполнение мозга от таких длинных историй…
Так в итоге что, бабуля ему тоже не помогла впихнуть, только успокоиться?
Моя история. Игры для мобильников, Java ME.

ПАМЯТЬ.
• Строки в собственной однобайтной кодировке. В этой же кодировке работал шрифт собственного формата (ради технологичности: было много нелокализованных и плохо локализованных мобильников).
• Большинство информации — static-массивы и static-функции.
• Эти static’и для удобства разбивались на несколько классов (Dev=device, M=menu, G=game, Skin=оформление, D=data) и в таком виде отлаживались; специальный препроцессор объединял их в один. С константами ничего не надо было делать; ProGuard работал отлично.
• Если мобильник поворачивал картинки и имел мало памяти, некоторые спрайты делали симметричными и хранили только половинку (в хороших мобилках хранили весь спрайт).

АРХИВ.
• Предвычисленные таблицы грузились из файлов (так компактнее).
• Ещё один препроцессор объединял кучу файлов в один: грузим, например, таблицу спрайтовых атласов, затем тригонометрическую таблицу, затем таблицу меню, затем ещё что-то…
• KZIP для архивов и PNGOUT для картинок. Даже 7-zip (он нужен был, если какой-то мобильник глючил, тогда в Zlib было немало ошибок) давал меньший архив, чем стандартные утилиты.
• Иногда даже бывало, что к одному PNG мы пристраивали разные палитры, разбив его на палитру и «всё остальное».
• Мелкие математические функции вроде max лучше было написать свои, чем импортировать: архива меньше брало.
• Я специально настаивал: в играх для слабых мобильников резать всё, что угодно, только не игровой процесс. Заставка — одноцветный экран с каким-то логотипом, и т.д.
Еще хорошо бы вспомнить ZX-Spectrum.
Некоторые игры использовали область памяти для вывода изображения для хранения там данных и искусственно их затемняли атрибутами цвета, делая эту часть экрана например черной.
А очистка экрана через стековые функции, которые почему-то работали сильно быстрее чем пересылка байтов…
Не только очистка, но и копирование/рисование. И «почему-то» вполне понятно — например, потому что не нужно выполнять инкремент/декремент адреса и, например, потому что одной командой обрабатывалось сразу два байта, а не один.
Эх, вспоминаю времена демосцены. К примеру есть вывод RGB изображения, где с использованием стека выводятся пикселы и область цвета заливается одним цветом. Со стеком делал интовый (в рамках одного прерывания) попиксельный сколл текста, с ускорением, цветом и другими фишками. Вот там со стеком наигрался вдоволь. Единственное ограничение было, что отображалось только 6 строк со знакоместа и 2 линии просто затирались.

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

Да и вообще стек использовался и при отрисовке спрайтов.

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

А так очистка экрана через стек действительно быстрее: Побайтово — 7 + 6 = 13 тактов на байт, через стек 11 тактов на 2 байта. А учитывая убогую схемотехнику клонов и округление тактов в четную большую сторону, 14 против 6 на байт.
Через стек на спектруме быстрее были абсолютно все линейные операции с памятью. Как вы пишете, очистка (или заполнение) — 11 тактов на 2 байта (PUSH HL), копирование данных — 21 такт на 2 байта (LD HL, XXXX; PUSH HL — при этом «исходные» данные содержали по 2 байта полезной информации и 2 байта кодов команд), но это был единственный способ, позволяющий копировать на пентагоне (70К тактов между прерываниями) весь ч/б экран (6К) за прерывание.
А причина — Z80 был великолепным (по тем временам) процессором с точки зрения схемотехники, он позволял создать простейший вычислительный модуль чуть ли не на 4-х микросхемах, но вот на быстродействие его никто не оптимизировал (его оптимизировали на совместимость с медленными микросхемами памяти и портов, все операции работы с шиной у него выполнялись по 2 такта). В итоге вышло, что самым быстрым оказался стек.
Sign up to leave a comment.

Articles