Доброго времени суток.
Я уже длительное время не занимался серверами PW и вот решил снова попробовать что-то сделать.
И так, некоторое время назад господин int 3 написал гайд о том, как ограничть Debug для GM. Но предоставлять всем GM возможность использоваться Debug не очень хорошая идея поэтому я решил ограничть его по другим критериям, а именно по: roleid, userid, сделать его специальным правом GM (добавляется через таблицу auth в MySql).
Редактировать будем следующие функции в GS: gplayer_controller::CommandHandler и gplayer_controller::DebugCommandHandler.
Все манипуляции производятся на GS версии 1.2.6, но на других версия все делается аналогичным образом, кроме ограничения Debug по userid.
И так приступим. Открывает gs в IDA и переходим к функции gplayer_controller::DebugCommandHandler.
Как и в гайде от int 3 чтобы ограничить дебаг мы будем затирать вызов функции: GLog::log.
0. Получаем смещение до RoleID и затираем вызов функции.
В дальнейшем для ограничения Debug по RoleId и UserId нам понадобится RoleId персонажа.
На скриншоте цифра 1 указывает на функции GLog::log, которую необходимо затереть, а цифра 2 на аргумент передоваемый в функцию GLog::log, который, по счастливой случайности, является Id персонажа, который использует Debug.

Кликаем по параметру на который указывает цифра 2 и нажимаем клавишу J, для перехода к коду на ассемблере, и видим:

Крассной рамкой выделен вызов функции GLog::log, который необходимо затереть, а желтой смещения до Id персонажа. Копируем выделенное желтым себе.
Затираем вызов функции, для этого можно использовать встроенный Hex-радокр в IDA или любой другой, должно получиться так:

1. Ограничение Debug по Roleid.
Для того чтобы Debug мог использовать только определенный персонаж необходимо сравнить его id с разрешенным. Сделать это можно написав проверку на месте затертого вызова функции GLog::log.
На ассемблере указанная проверка будет выглядеть следующим образом:
Указанные команды необходимо перевести в opcod и используя Hex-редактор записать в выделенную область.
20h - Id персонажа, в данном случае 32.
jnz 2AAC - выход из функции, где 2AAC разность между адресом назначения и адресом команды, следующей сразу за прыжком. В данном случае: 80D4ECF - (080D241D + 6) = 2AAC. Где:
080D4ECF - адрес выхода из функции
080D241D - адрес по которому находится команда jnz
6 - количество байт занимаемых командой jnz.
Команды и соответствующии им opcod'ы
Вeсь Hex-код:
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер. После данных изменений Debug будет доступен только персонажу с Id равным 32.
2. Ограничение Debug по UserId. (Только для 1.2.6!)
И так в 1.2.6 UserID можно узнать используя RoleID использовав следующую формулу: UserID = floor(RoleID / 16) * 16
Таким образом, код проверки на ассемблере будет выглядеть следующим образом:
Указанные команды необходимо перевести в opcod и используя Hex-редактор записать в выделенную область.
20h - ID аккаунта, в данном случае 32.
jnz 2AA4 - выход из функции, где 2AAC разность между адресом назначения и адресом команды, следующей сразу за прыжком. В данном случае: 80D4ECF - (080D2425 + 6) = 2AAC. Где:
80D4ECF - адрес выхода из функции
080D2425- адрес по которому находится команда jnz
6 - количество байт занимаемых командой jnz.
Команды и соответствующии им opcod'ы
Вeсь Hex-код:
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер. После данных изменений Debug будет доступен только аккаунту с ID равным 32.
3. Debug как специальное право GM (добавляется через таблицу auth в MySql).
Для того чтобы это сделать необходимо узнать как проверяется наличие права на выполнение действия у GM. Так же необходимо выбрать код для него, который не только вам нравится, а так же и не занят другим правом.
Приступим:
Что бы узнать как осуществляется провека на наличие у GM права на выполнение действия необходимо обратится к функции gplayer_controller::GMCommandHandler, в которой такая проверка осуществляется.

На скриншоте красным вделенна интересующая нас проверка. Из которой видно, что вызвается функциия GNET:: Privilege::Has_Hide_BeGod. Как видно из названия данная функция проверяет может ли GM использовать нефидимость и неуязвимость.
Двойным кликом переходим к псевдокоду указанной функции и видим, что в ней осуществляется проверка на равенство единице значения элемента массива с индексом равным праву GM, которое записывается в MySql. Сам массив имеет фиксированный размер в 256 байт.

Т.е. для того чтобы сделать Debug специальным правом GM необходимо выбрать любое понравившееся число в диапозоне от 0 до 255, которое свободно и выполнить проверку на равенство его единице. Я выбрал значения 250.
И так, необходимо узнать смещения до данного массива.
Переходим в фукнцию gplayer_controller::GMCommandHandler и видим, что в качестве параметра в функцию GNET:: Privilege::Has_Hide_BeGod передается _gm_auth, переходим к коду на ассемблере и видим следуещее:

Переходим к коду на ассемблере функции GNET:: Privilege::Has_Hide_BeGod и видим:

Таким образом, код проверки на ассемблере будет выглядеть следующим образом:
Указанные команды необходимо перевести в opcod и используя Hex-редактор записать в выделенную область.
0FAh- ID специального права GM, в данном случае 250.
jnz 2AAC - выход из функции, где 2AAC разность между адресом назначения и адресом команды, следующей сразу за прыжком. В данном случае: 80D4ECF - (080D241D+ 6) = 2AAC. Где:
080D4ECF - адрес выхода из функции
080D241D - адрес по которому находится команда jnz
6 - количество байт занимаемых командой jnz.
Команды и соответствующии им opcod'ы
Вeсь Hex-код:
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер, выдаем кому надо GM право с ID равным 250. После данных изменений Debug будет доступен только аккаунтам, у которых есть GM право с ID равным 250.
4. Финальные штрихи.
И так, дебаг ограничен по одному из приведенных выше критериев и все вроде бы хорошо, но теперь у простых GM'ов не работает телепортация по ctrl+лкм.
Для того чтобы это исправить необходимо отредактировать функцию gplayer_controller::CommandHandler, а именно убрать из нее следующую проверку:

На ассемблере она выглядит так:

Для этого необходимо выделенный участок кода затереть.
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер.
На этом все. Теперь Debug ограничен одним из трех, приведенных выше, способом и у всех GM работает телепортация по ctrl+лкм.
Я уже длительное время не занимался серверами PW и вот решил снова попробовать что-то сделать.
И так, некоторое время назад господин int 3 написал гайд о том, как ограничть Debug для GM. Но предоставлять всем GM возможность использоваться Debug не очень хорошая идея поэтому я решил ограничть его по другим критериям, а именно по: roleid, userid, сделать его специальным правом GM (добавляется через таблицу auth в MySql).
Редактировать будем следующие функции в GS: gplayer_controller::CommandHandler и gplayer_controller::DebugCommandHandler.
Все манипуляции производятся на GS версии 1.2.6, но на других версия все делается аналогичным образом, кроме ограничения Debug по userid.
И так приступим. Открывает gs в IDA и переходим к функции gplayer_controller::DebugCommandHandler.
Как и в гайде от int 3 чтобы ограничить дебаг мы будем затирать вызов функции: GLog::log.
0. Получаем смещение до RoleID и затираем вызов функции.
В дальнейшем для ограничения Debug по RoleId и UserId нам понадобится RoleId персонажа.
На скриншоте цифра 1 указывает на функции GLog::log, которую необходимо затереть, а цифра 2 на аргумент передоваемый в функцию GLog::log, который

Кликаем по параметру на который указывает цифра 2 и нажимаем клавишу J, для перехода к коду на ассемблере, и видим:

Крассной рамкой выделен вызов функции GLog::log, который необходимо затереть, а желтой смещения до Id персонажа. Копируем выделенное желтым себе.
Затираем вызов функции, для этого можно использовать встроенный Hex-радокр в IDA или любой другой, должно получиться так:

1. Ограничение Debug по Roleid.
Для того чтобы Debug мог использовать только определенный персонаж необходимо сравнить его id с разрешенным. Сделать это можно написав проверку на месте затертого вызова функции GLog::log.
На ассемблере указанная проверка будет выглядеть следующим образом:
Код:
mov eax, [ebp+8]
mov eax, [eax+4]
mov eax, [eax+8]
cmp dword ptr [eax+30h], 20h
jnz 2AAC
Указанные команды необходимо перевести в opcod и используя Hex-редактор записать в выделенную область.
20h - Id персонажа, в данном случае 32.
jnz 2AAC - выход из функции, где 2AAC разность между адресом назначения и адресом команды, следующей сразу за прыжком. В данном случае: 80D4ECF - (080D241D + 6) = 2AAC. Где:
080D4ECF - адрес выхода из функции
080D241D - адрес по которому находится команда jnz
6 - количество байт занимаемых командой jnz.
Команды и соответствующии им opcod'ы
Код:
mov eax, [ebp+8] - 8B 45 08
mov eax, [eax+4] - 8B 40 04
mov eax, [eax+8] - 8B 40 08
cmp dword ptr [eax+30h], 20h - 83 78 30 20
jnz 2AAC - 0F 85 AC 2A 00 00
Вeсь Hex-код:
Код:
8B 45 08 8B 40 04 8B 40 08 83 78 30 20 0F 85 AC 2A 00 00
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер. После данных изменений Debug будет доступен только персонажу с Id равным 32.
2. Ограничение Debug по UserId. (Только для 1.2.6!)
И так в 1.2.6 UserID можно узнать используя RoleID использовав следующую формулу: UserID = floor(RoleID / 16) * 16
Таким образом, код проверки на ассемблере будет выглядеть следующим образом:
Код:
mov eax, [ebp+this]
mov eax, [eax+4]
mov eax, [eax+8]
mov eax, [eax+30h]
shr eax, 4
shl eax, 4
cmp eax, 20h
jnz 2AA4
Указанные команды необходимо перевести в opcod и используя Hex-редактор записать в выделенную область.
20h - ID аккаунта, в данном случае 32.
jnz 2AA4 - выход из функции, где 2AAC разность между адресом назначения и адресом команды, следующей сразу за прыжком. В данном случае: 80D4ECF - (080D2425 + 6) = 2AAC. Где:
80D4ECF - адрес выхода из функции
080D2425- адрес по которому находится команда jnz
6 - количество байт занимаемых командой jnz.
Команды и соответствующии им opcod'ы
Код:
mov eax, [ebp+8] - 8B 45 08
mov eax, [eax+4] - 8B 40 04
mov eax, [eax+8] - 8B 40 08
mov eax, [eax+30h] - 8B 40 30
shr eax, 4 - C1 E8 04
shl eax, 4 - C1 E0 04
cmp eax, 20h - 83 F8 20
jnz 2AA4 - 0F 85 A4 2A 00 00
Вeсь Hex-код:
Код:
8B 45 08 8B 40 04 8B 40 08 8B 40 30 C1 E8 04 C1 E0 04 83 F8 20 0F 85 A4 2A 00 00
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер. После данных изменений Debug будет доступен только аккаунту с ID равным 32.
3. Debug как специальное право GM (добавляется через таблицу auth в MySql).
Для того чтобы это сделать необходимо узнать как проверяется наличие права на выполнение действия у GM. Так же необходимо выбрать код для него, который не только вам нравится, а так же и не занят другим правом.
Приступим:
Что бы узнать как осуществляется провека на наличие у GM права на выполнение действия необходимо обратится к функции gplayer_controller::GMCommandHandler, в которой такая проверка осуществляется.

На скриншоте красным вделенна интересующая нас проверка. Из которой видно, что вызвается функциия GNET:: Privilege::Has_Hide_BeGod. Как видно из названия данная функция проверяет может ли GM использовать нефидимость и неуязвимость.
Двойным кликом переходим к псевдокоду указанной функции и видим, что в ней осуществляется проверка на равенство единице значения элемента массива с индексом равным праву GM, которое записывается в MySql. Сам массив имеет фиксированный размер в 256 байт.

Т.е. для того чтобы сделать Debug специальным правом GM необходимо выбрать любое понравившееся число в диапозоне от 0 до 255, которое свободно и выполнить проверку на равенство его единице. Я выбрал значения 250.
И так, необходимо узнать смещения до данного массива.
Переходим в фукнцию gplayer_controller::GMCommandHandler и видим, что в качестве параметра в функцию GNET:: Privilege::Has_Hide_BeGod передается _gm_auth, переходим к коду на ассемблере и видим следуещее:

Переходим к коду на ассемблере функции GNET:: Privilege::Has_Hide_BeGod и видим:

Таким образом, код проверки на ассемблере будет выглядеть следующим образом:
Код:
mov eax, [ebp+8]
mov eax, [eax+38h]
cmp byte ptr [eax+0FAh], 1
jnz 2AAC
Указанные команды необходимо перевести в opcod и используя Hex-редактор записать в выделенную область.
0FAh- ID специального права GM, в данном случае 250.
jnz 2AAC - выход из функции, где 2AAC разность между адресом назначения и адресом команды, следующей сразу за прыжком. В данном случае: 80D4ECF - (080D241D+ 6) = 2AAC. Где:
080D4ECF - адрес выхода из функции
080D241D - адрес по которому находится команда jnz
6 - количество байт занимаемых командой jnz.
Команды и соответствующии им opcod'ы
Код:
mov eax, [ebp+8] - 8B 45 08
mov eax, [eax+38h] - 8B 40 38
cmp byte ptr [eax+0FAh], 1 - 80 B8 FA 00 00 00 01
jnz 2AAC - 0F 85 AC 2A 00 00
Вeсь Hex-код:
Код:
8B 45 08 8B 40 38 80 B8 FA 00 00 00 01 0F 85 AC 2A 00 00
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер, выдаем кому надо GM право с ID равным 250. После данных изменений Debug будет доступен только аккаунтам, у которых есть GM право с ID равным 250.
4. Финальные штрихи.
И так, дебаг ограничен по одному из приведенных выше критериев и все вроде бы хорошо, но теперь у простых GM'ов не работает телепортация по ctrl+лкм.
Для того чтобы это исправить необходимо отредактировать функцию gplayer_controller::CommandHandler, а именно убрать из нее следующую проверку:

На ассемблере она выглядит так:

Для этого необходимо выделенный участок кода затереть.
Должно получится так:
Hex.

Asm.

Псевдокод.

Сохраняем, заливаем GS на сервер, запускаем сервер.
На этом все. Теперь Debug ограничен одним из трех, приведенных выше, способом и у всех GM работает телепортация по ctrl+лкм.