背景
我已经有很长一段时间出现问题,玩家在我的安卓游戏中作弊。对于一个严格的单人游戏来说这不是一个大问题,但由于我的游戏包含多人战斗和全球高分榜,因此这会让合法玩家因为作弊而停止游戏。
他们如何作弊
作弊者为名为Gamecih的root用户使用应用。 Gamecih允许用户暂停应用,更改变量值,然后恢复应用。所以在我的情况下,他们只是暂停游戏,将“健康”改为74万亿,然后在多人游戏中将所有人从垃圾中剔除。这是一个video,显示Gamecih如何在水果忍者(不是我的游戏)中作弊。
考虑方法
我想要什么
可以说,考虑到方法nr 2是我应该使用的,但是再一次,它不会阻止黑客攻击,它只会让它变得更难。理想情况下,我想检测人们何时使用Gamecih作弊,显示弹出式文字“Darn you,you nasty hacker”,然后关闭应用程序。我不想要一个依赖服务器的解决方案,因为我希望我的玩家能够在离线时玩游戏。如果可能的话,我也想避免代码混淆。
答案 0 :(得分:9)
您可以将生命存储在X个变量中,实际值将是它们的总和(始终是动态计算的)。您随机选择要更新的那个。最重要的是你可以添加一些一致性检查,骗子很难意识到改变它的方式和方法。
一致性检查可能是一个简单的规则,例如第1,第2和第3变量处于增长顺序,第4个变量是最小的。用这个工具来解决这个问题需要花一些时间。
Yoy还可以获得更多创意,并加入一些加密等(你提到的方式)。然后,除非有人拥有你的代码,否则它将成为第二个不可能。
编辑:添加100个随机变量,这些变量随机更改名称(或数组中的位置,以使其更容易),然后为寻找正确名字的骗子带来好运。并使它全部动态,所以每次他们必须再次破解它。
答案 1 :(得分:7)
您可以定期检查您的值是否已更改。
例如,您可以在单独的隐藏标志中存储健康值已更改的事实。如果您的检查方法确实检测到值的更改,并且未设置标志,那么您可以判断该更改是非法的。
例如:
void incrementHealth(int amount) {
health = health + amout;
hiddenCheck.hasChanged = true;
}
并且必须定期调用一个单独的方法:
void checkHealth() {
if (hiddenCheck.hasChanged) {
// change is valid
hiddenCheck.hasChanged = false;
hiddenCheck.lastKnownValue = health;
} else {
if (hiddenCheck.lastKnownValue != health) {
// An illegal change has occured ! Punish the hacker !
}
}
}
}
答案 2 :(得分:6)
try{
ApplicationInfo info = getPackageManager().
getApplicationInfo("com.cih.gamecih", 0 );
return true;
} catch( PackageManager.NameNotFoundException e ){
return false;
}
如果此函数返回true,请不要让黑客进入多人游戏模式,并提示他将其卸载。
答案 3 :(得分:1)
从存储值动态计算您的统计数据。
private double getSaltedSqrt(int i){
return Math.sqrt(i)+1337;
}
private int getTrueValue(double i){
return (i-1337)*(i-1337);
}
这样,没有常规脑的人就能从RAM中找到你的价值观。健康状况为100的人的健康值为1347.0
如果有人对该玩家造成10点伤害,你只需要打电话:
currentHealth = getSaltedSqrt(getTrueValue(currentHealth)-damage);
但是,最安全的方法是通过服务器实现所有这些更改。
答案 4 :(得分:1)
我对此有一个想法,因为我有时会自己使用GameCIH。您可以拥有一个滚动的10项事务日志,可以自动检查每个新事务。
你会做什么(因为GameCIH一次只能处理一个变量)有两个相互检查的变量。
如果总和值的负数与原始加上10个记录的事务不匹配,则返回错误。
你只需要改变你的统计模式的处理方式 - 即使其中一个仍然试图直接修改原始值,你的游戏也会返回它被错误地改变。
答案 5 :(得分:1)
擅长作弊游戏的人也会阅读这些论坛,他们知道你所有的小秘密。
没有可靠的方法来阻止人们欺骗在本地存储重要变量的游戏。游戏必须将这些变量保留在服务器上。如果这些变量没有保存在服务器上,总会有人可以破解你的游戏。
答案 6 :(得分:0)
为防止记忆作弊,您可以执行以下操作之一:
答案 7 :(得分:0)
每次更新值时都应该存储健康状况的哈希值(例如crc32或md5),对当前设置的值进行哈希检查。在这种情况下,作弊者必须编写一个处理哈希值的独立应用程序。可能,但这将很快阻止脚本小伙子的作弊。
答案 8 :(得分:0)
在口袋妖怪游戏中,他们使用了DMA。当游戏暂停很短的时间时,你可以通过让计时器关闭并触发所有值的更新来获得类似的效果。更新会为所有变量添加一些随机数量(包括您从中减去的变量以获取单个值)。您还可以尝试将值存储在大型数组中并更改起始位置。你没有像GameState[121]
这样的绝对指针,而是像GameState[121+StartingPosition]
这样的东西,只需将值增量器与位置随机化器结合起来。在两种情况下,模块化算术都是你的朋友。要小心溢出阵列和逐个错误。缓冲区溢出不会很好。 ;)
如果这是一个Flash或Java应用程序:遗憾的是,使用内存管理快速重新映射RAM中的位置值并不像Gameboy Advance使用的本机二进制文件那样方便。将所有变量以随机顺序复制到第二组,然后删除并垃圾收集原始值可能会使您的游戏运行缓慢。
答案 9 :(得分:0)
您是否可以在游戏发布时检查root访问权限?然后拒绝打开应用程序或拒绝root设备上的多人游戏模式?只有在应用程序初始化时才在开启加载屏幕上提供一个小检查,可能有应用程序请求超级用户然后如果用户授予它尝试执行无法超级用户不允许的无害功能然后代码检查所述功能是否成功然后撤消更改和弹出一个消息框,指示用户应该再次尝试离开root模式。
或者,可以在进入多人模式时应用此检查。
此外,您可以从服务器运行多人游戏模式,从设备运行单人游戏,让单人游戏十六进制自由编辑。