Эта статья о том, как мы создавали систему защиты браузерных HTML5-игр от взлома и фальсификации результатов, с какими трудностями столкнулись, как их решали и что получили в итоге.
Основная и знакомая проблема таких игр — возможность написания бота, который будет автоматически завершать игру.
Разработке такого бота способствует тот факт, что код игры находится в открытом доступе.
Ситуация осложнялась тем, что были объявлены настоящие призы, среди которых были iPad, билеты на концерты, флешки и т. д.
Статья будет полезна в основном тем, кто делает HTML5/Flash-игры и заботится об их безопасности; те, кто платит за разработку этих игр; и немного для тех, кто призван бороться с ботами.
И, конечно же, тем, кто написал эту статью.
Потому что мы надеемся, что это положит начало продуктивной дискуссии о том, как разработчики браузерных игр могут бороться с кибермошенниками.
Какая игра это?
Немного о самой игре.К сожалению, саму игру мы не можем показать по просьбе заказчика.
Несмотря на все описанные ниже приемы, к сожалению, «невежество» является ключевым элементом защиты.
То есть раскрытие методов применительно к конкретной игре существенно снизит их эффективность.
- Тип игры: Собери и беги.
- Примеры: всем знакомый Mario Bros. и его клоны.
- Продолжительность игры: примерно 1-2 минуты.
- Цель игры – набрать наибольшее количество очков.
- Основные элементы игры:
- Характер.
Главный герой постоянно движется.
Может прыгать и пригибаться, чтобы собирать бонусы и избегать препятствий.
- Бонусы.
Они могут увеличить очки персонажа или скорость передвижения.
Чтобы их собрать, персонаж должен прыгать.
- Препятствия.
Барьеры или объекты, движущиеся навстречу персонажу.
Чтобы избежать их, персонаж должен пригнуться или прыгнуть.
При столкновении с препятствием персонаж теряет скорость.
- Характер.
- Характеристики игры, используемые при подсчете результата игры:
- Набранные очки.
Увеличивается при сборе бонусов.
- Скорость персонажа.
Уменьшается со временем.
Уменьшается при столкновении с препятствием.
Увеличивается при сборе бонусов.
- Время, потраченное на игру.
- Набранные очки.
- Используемые технологии:
- Клиент: HTML5. Причина: игру необходимо запустить на всех устройствах.
JS-фреймворк: Pixi.js ( http://www.pixijs.com )
- Сервер: PHP, Фреймворк: Zend
- Клиент: HTML5. Причина: игру необходимо запустить на всех устройствах.
- Цель клиента: реклама своего бренда через игру.
Геймплей был связан с услугами компании; логотипы, фирменные цвета и все остальное доступно.
- Игра запускалась на определенный период, после чего игроки, показавшие лучшие результаты, были награждены ценными призами.
- Исходя из вышеизложенного, заказчик сразу подчеркнул, что игра должна быть защищена от фальсификации результатов.
Заказчик дорожит своей репутацией.
Он не хотел, чтобы после выхода игры в СМИ появилась информация о том, что их фирменную игру взломали.
Что за команда?
Мы веб-разработчики, но ранее не занимались разработкой игр.В самом начале мы придумали много забавных решений.
Например, мы допустили важную архитектурную ошибку — решили генерировать уровень на клиенте в браузере; а в качестве защиты они полагались на обфускацию JS-кода.
Правда, товарищи из соседних отделов сказали, что для качественной защиты придется «поиграть» игру на сервере и сравнить ее с клиентом.
Но мы тогда смеялись, что это было очень сложно.
Повторюсь, что основным требованием было обеспечение защиты от мошенничества.
Но наша команда решила сначала заставить игру работать в принципе.
И разработку защиты отложили на потом.
Это казалось логичным: сначала мы что-то делаем, а уж потом это «что-то» защищаем.
Проблема
Как только мы начали работать над безопасностью, мы сразу же столкнулись с основной проблемой всех браузерных игр, вытекающей из клиент-серверной архитектуры.А именно: игрок видит весь клиентский код игры и не может слепо доверять данным, поступающим на сервер.
Хотя мы знаем, как справиться со второй частью проблемы, возможность анализа и изменения исходного кода любым пользователем нас действительно озадачила.
Мы начали с простого решения — обфускации JS-кода и шифрования данных, отправляемых клиентом на сервер.
Но у заказчика была убийственная команда безопасности, которая за 15 минут смогла записать нереальный игровой счет, имея полностью запутанный код. Шифровать данные при передаче тоже не вариант — ключи находятся у клиента, и их легко вставить в нужное место.
Так что на самом деле оба эти решения были эффективны только для очень ленивых хакеров.
Более того, Flash-игры также подвергаются аналогичному обратному проектированию, и эти разработчики также ищут решение для обеспечения безопасности.
Ситуация осложнялась тем, что в нашей игре есть настоящие призы.
При этом ее взлом перешел из категории «взлом ради развлечения» в категорию «взлом на деньги».
Эта игра более чем привлекательна для специалистов более высокого класса, чем «начинающий хакер».
Советы из Интернета
Несмотря на то, что уже разработано множество онлайн-игр, о методах борьбы с их взломом найдено очень мало информации.Вот рекомендации, которые мы извлекли из Интернета:
- Скрывайте, защищайте и шифруйте игровые данные:
- Переменные, отвечающие за игровой счет, не следует помещать в глобальную область видимости.
Рекомендуется объявить их частными и поместить в замыкания.
- Не отправлять значения учетной записи в открытом виде, а необходимо их зашифровать.
- Зашифруйте адреса (uri), на которые отправляется счет.
- Запутайте часть кода, отвечающую за расчет и отправку счета.
- Отправьте лицензионные ключи вместе с результатами игры и проверьте их на сервере.
- Плюсы: относительная простота реализации.
- Минусы: как уже писалось выше, взломать можно за 15 минут.
- Переменные, отвечающие за игровой счет, не следует помещать в глобальную область видимости.
- Глупые хакеры:
- Если обнаружен накрутка аккаунта, всё равно покажите хакеру его результат в списке записей.
Пусть он думает, что дело сделано.
Но другие пользователи не должны этого видеть.
- Когда будет установлено, что игра взломана, то отложить наказание на случайный период (например, от 1 до 3 дней).
Хакер будет использовать несколько методов и периодически видеть, что у него получается.
Но понять, что именно происходит, и на чем именно его в итоге поймали, ему тоже будет сложно.
- Если обнаружен накрутка аккаунта, всё равно покажите хакеру его результат в списке записей.
- Проверьте реалистичность игровых данных:
- Проверьте на сервере теоретическую возможность отправленных значений.
Например, энергия не может быть отрицательной, счет не может уменьшаться, позиция игрока всегда увеличивается и т. д.
- Отправьте игровые данные на сервер и сравните их с такими же данными других пользователей.
Например, если игрок сделал 200 бросков и набрал счет 200 000, а остальные игроки, сделав 200 бросков, достигли счета 5 000, то это повод усомниться в честности игры.
- Удалить игры, которые длились меньше (больше) определенного времени.
- Плюсы: относительная простота реализации.
- Минусы: не обеспечивает полную защиту, добавляет лишние 5-10 минут на организацию взлома.
- Проверьте на сервере теоретическую возможность отправленных значений.
- Организационное влияние на счета:
- Добавьте значимости аккаунту, чтобы было жаль его терять.
Например, чтобы играть в эту игру с реальными призами, нужно сначала добиться чего-то в других играх без призов.
- Сделайте регистрацию аккаунта платной.
- Запретите хакерам по IP при первой же попытке взлома.
Ни в коем случае не давайте им шанса разобраться в этом.
- Добавьте значимости аккаунту, чтобы было жаль его терять.
- ЭИмитировать игру на сервере:
- Сделайте «мгновенный повтор» на сервере.
После прохождения уровня отправьте данные, по которым восстанавливаются события в игре и пересчитывается ее результат. Потом все это сравнивается с тем, что прислал игрок, и если есть большая разница, то это взлом.
- Плюсы: обеспечивает большую степень защиты.
- Минусы: События, отправленные в конце игры, также могут быть подделаны.
- Сделайте «мгновенный повтор» на сервере.
Некоторые из них были успешными, некоторые — не очень.
К не столь удачным можно отнести, например, вывод капчи «до», «во время» и «после» игры.
Или, скажем, делать скриншоты во время игры и отправлять их на сервер для проверки.
Ниже описаны наиболее интересные из реализованных методов.
ЭИгровой симулятор
После долгих раздумий и сопротивления сложному решению мы пришли к выводу, что играть (эмулировать) игру на сервере явно необходимо.Если не сказать – неизбежно.
Для этого мы начали генерировать игру (расположение бонусов и препятствий) на сервере и отправлять на сервер не конечный результат игры, а только события, произошедшие в ней: столкновения с препятствиями, бонусы и нажатия клавиш.
Для каждого события мы знали время, координаты, нажатые клавиши или бонусы/препятствия, с которыми столкнулся игрок.
Была возможность отправлять только нажатия клавиш, а результат вычислять на сервере в конце игры.
Но мы столкнулись с проблемой разной скорости игры на разных устройствах и в разных браузерах.
Высока вероятность сильного несоответствия игрового процесса на клиенте и сервере, так как этот метод очень чувствителен к несоответствиям.
Например, если вдруг клиент не отправит всего одно столкновение с препятствием, то эмулируемая игра с этого момента пойдет совсем по-другому.
Ведь при столкновениях теряется энергия и скорость.
Другой вариант — обрабатывать события на сервере и немедленно отправлять результаты событий клиенту.
Но это создает большой трафик между сервером и клиентом, увеличивается время ответа игры и резко возрастает нагрузка на сервер.
Так работают, например, MMO-игры.
Но для небольшой игры «Собери и беги» мы сочли это нецелесообразным.
Особо хотелось бы отметить тот факт, что устройства, на которых запускалась игра, имели разную производительность.
На быстрых устройствах игра шла плавно, на медленных - рывками.
Из-за этой разницы нам пришлось отказаться от привязки времени при эмуляции.
Вместо этого мы рассматривали события игры как нечто, происходящее в каких-то координатах.
Например, мы изначально думали, что прыжок для включения питания — это «нажатие кнопки вверх через 10 секунд, нажатие кнопки включения через 12 секунд».
Но нам больше подошло следующее: «нажатие кнопки вверх, когда X-координата игрока равна 1000, столкновение с бонусом, когда X-координата игрока равна 1100, а Y-координата игрока равна 300. » При этом и быстрые, и медленные устройства эмулировались более или менее одинаково.
В итоге после игры мы решили эмулировать на сервере каждое событие, отправленное клиентом, и дополнительно рассчитывать вероятность его возникновения.
Одной из задач, которые мы решали, было создание одинаковых алгоритмов расчета коллизий на сервере и на клиенте.
Необходимо было добиться такой же точности, включая округление.
В результате работы эмулятора мы получаем на сервер последовательность игровых событий в том же виде, что и в реальной игре.
После эмуляции событий переходим к анализу достигнутого.
Анализатор игр
Это самый интересный блок.Вот наиболее успешные методы выявления мошенников.
Они все разные, запускаются последовательно, при необходимости можно добавить еще.
- Координаты столкновения.
- Повышение позиции персонажа.
Оно не может уменьшаться или оставаться прежним.
- Персонаж достиг конца уровня.
- Продолжительность игры.
Поэтому игры, завершенные за 30 секунд или 2 минуты, считаются взломанными.
- Контроль показателей скорости и энергии.
При получении некоторых бонусов скорость персонажа увеличивается, а при столкновении с препятствиями снижается.
Также сбор некоторых бонусов увеличивает количество очков, набранных игроком.
Зная, какие предметы собрал игрок, можно на сервере посчитать, какие значения у него должны быть: скорость и количество очков.
- Прыгайте, прежде чем получить бонус.
Здесь проверяется, был ли прыжок перед взятием.
- Прыгните перед препятствием.
Для каждого препятствия мы проверяем, подскочил ли игрок к препятствию (нажатие кнопки прыжка) и не заблокировала ли его траектория прыжка.
- Правильные ключи.
Если нажималось что-то другое, то это подозрительно.
- Бонусы и препятствия собираются один раз.
- Коллизии на клиенте.
- Коллизии на эмуляторе.
Этот метод введен для того, чтобы иметь разные веса этого и предыдущих методов.
Мы посчитали, что если столкновение происходит в эмуляторе, но не в реальной игре, то это менее подозрительно, чем когда столкновение происходит в реальной игре, но не в эмуляторе.
- Прием ложных элементов.
Например, они немного выше, чем может прыгнуть персонаж; или рядом расположены два бонуса, но физически можно собрать только один из них.
И проверяем, клюнул ли хакер на удочку и забрал эти бонусы.
- Анализ отпечатков пальцев.
Это не поможет нам понять, была ли игра взломана.
Но в случае, когда администраторы отмечают игрока как хакера, анализатор сканирует всех игроков в системе и находит аналогичные «отпечатки».
Таким образом, вы можете с определенной вероятностью обнаружить хакеров, пытающихся взломать игру под одним аккаунтом, и играть «чисто» под другим.
Кстати, имеет смысл включить в настройки как можно больше параметров.
Потому что заранее не ясно, насколько чувствительным или грубым окажется тот или иной алгоритм в реальности.
В ходе работы анализатор присваивает каждому методу значения от 0 до 1 (0 — игра вне подозрений, 1 — тест полностью провален) и в конце рассчитывает «Индекс подозрительности игры» (также от 0 до 1).
).
Этот индекс используется для автоматической пометки игры.
Если оно больше порога, то игра считается взломанной.
Конкретное пороговое значение подбирается опытным путем; у нас получилось 0,4.
Управление доказательствами
Но это еще не все.Нам нужно что-то сделать со всеми этими расчетами.
Одно дело запрограммировать описанные выше алгоритмы, а другое — представить результаты работы администраторам игры в читаемом виде.
Игрок, заблокированный за взлом, может обратиться в службу поддержки с жалобами, при этом у них должны быть доказательства принятого решения.
Поэтому рекомендуется предоставить администраторам максимальное количество информации, чтобы они могли понять и обосновать, почему та или иная игра была определена как взломанная.
Для этого мы создали 4 страницы в админ-панели.
- Информация об игре - Симулятор
Таблица с реальными и эмулированными событиями выбранной игры.
Столбцы следующие:
- тип элемента (бонус, барьер)
- X- и Y-координаты элемента
- время на клиенте
- X- и Y-координаты персонажа (на клиенте)
- факт столкновения персонажа и элемента (да, нет)
- Координаты X и Y персонажа (эмулируются)
- вероятность коллизии в указанное время на клиенте
- Информация об игре - Анализатор
Общий индекс подозрительности игры и таблица с результатами анализатора по каждому методу.
- Анализатор
Показывает таблицу всех подозрительных игр на основе порога подозрений (0 — подозрений нет, 1 — определенно взломан).
Исходя из опыта, мы получили значение 0,4.
- Страница игрока
В профиль игрока добавлен «Индекс подозрительности игрока».
Он рассчитывается на основе показателей подозрительности всех своих игр.
Это значительно упростило бы работу игровых администраторов, поскольку за день человек не в состоянии просмотреть тысячи подозрительных игр.
Как все прошло
Анализировать лучших игроков через несколько дней после запуска игры было весьма интересно.
Один грабитель выбрал легкий путь и собрал все элементы, но так и не прыгнул.
Он также собрал все «ложные» элементы.
Другой «чемпион» эволюционировал последовательно.
Сначала у него было с десяток честных игр, потом много «пустых».
А в самых последних играх индекс подозрительности зашкаливал.
Некоторые «победители» проходят игру менее чем за 10 секунд. Некоторые люди сыграли в игру всего один раз и сразу же попали в топ.
Это, кстати, можно использовать как метод анализатора — мало кому удается сделать максимум с первого раза.
Были «рекордсмены», набравшие нереальное количество очков за одну секунду.
И так далее.
Всех их заблокировали и не позволили выиграть реальные призы.
Жалоб с их стороны не было.
Пересмотрев несколько десятков реальных игр, мы обновили некоторые пороговые параметры в сторону увеличения.
Например, может быть увеличено максимальное значение индекса подозрительности игры, при котором игра считается взломанной.
Другими словами, первоначальные настройки были очень подозрительными.
Реально мы получили положительный результат от работы этой системы.
Отображение результатов в админке во многом помогло разобраться.
В целом можно сказать, что система показала себя вполне жизнеспособной, заказчик остался доволен.
Заключение
При защите от накрутки аккаунта мы использовали данные только одной игры и пытались отловить их на внутренних несоответствиях.Мы предположили, что игра полностью уязвима: игроку доступны все источники, а входящие данные недостоверны.
Но есть часть игры, недоступная хакерам — это данные всех игр.
Есть предположение, что правильно используя базу данных тысяч игроков, можно повысить точность обнаружения взлома.
Сейчас мы считаем, что база данных результатов игр — главное преимущество разработчиков перед хакерами.
Что вы думаете, хабровчане? Поделитесь своими мыслями и подходами к защите онлайн-игр.
Теги: #gamedev #игры #взлом игр #взлом #разработка браузерных игр #защита от ботов #защита от взлома #разработка сайтов #разработка игр
-
Офлайн-Версия Playphrase.me
19 Oct, 24 -
Эвкалипт – «Облако» Своими Руками
19 Oct, 24 -
Китти = Замазка
19 Oct, 24 -
Совместное Владение И Управление Доменом
19 Oct, 24