LOADING...
LOADING...
LOADING...
当前位置: 玩币族首页 > 区块链资讯 > 基于RSA加密算法的随机区块链

基于RSA加密算法的随机区块链

2020-11-24 waves中国社区 来源:区块链网络

这是分布式网络中随机数生成的解决方案。

在开发我们的游戏过程中,我们需要解决一个问题,在分布式网络中生成随机数很复杂,现几乎所有区块链都面临这个问题。?因此,在任何人都无法相互信任的互联网之间,创建随机数可以解决许多问题。

在本文中,我们将讲解我们是如何在我们的游戏中解决这个问题的。?首当其冲的便是Waves Xmas Tree.

起初,我们计划使用区块链信息来生成一个数字,但在进一步的研究中我们发现创建这个数字的过程可以被操纵干预,因此我们不得不放弃这个方案。

此后我们提出了一个新的方案,?使用“Commit-Reveal”方案。首先服务器生成一个1到5之间的数字,然后往其中添加“盐”并且使用Keccak function?进行哈希值处理。服务器使用已储存的数字对智能合约进行预调试,?结论是游戏被有效的简化,为用户猜测哈希值下所隐藏的数字。

玩家下注后服务器将发送一个隐藏的数字并且将其“盐”带到一个智能合约中。换句话说,信息已被揭露,之后服务器也会验证这个数字并判断用户的输赢。

如果服务器未发送该数字和“盐”进行验证,则该用户赢了。 在这种情况下,必须提前部署智能合约,并为每场比赛安排潜在的获胜机会。 这是非常不方便,成本高且消耗大量时间。 但那时还没有提出其它安全的解决方案。

此后不久,Tradisys团队提议向Waves协议添加rsaVerify()函数。 这将根据公钥和私钥检查RSA签名的有效性。 根据我们的建议,该功能已被添加。

我们开发了三款新游戏:《摇骰子》,《掷硬币》和《乘浪行》。?在每个游戏中,每款游戏都部署了新的随机数方法,让我们仔细观察它是如何工作的

让我们先看看生成的随机数,你可以在此处查看智能合约。

切换到脚本选项卡并选择反编译,您即可看到智能合约的代码(或脚本)。

智能合约的代码由一系列的函数组成。其中的@Callable 可以通过调用事务选项运行。?我们对其中两个很感兴趣:下注和撤回:

1.用户选择范围和下注大小

2.客户安排下注功能。 对于上面的图像,即为bet(?50?)

3. 客户端将调用事务发送到智能合约地址(播报 InvocationTx)。 作为Call参数的交易依据并包含bet函数。 这意味着调用事务开始在智能合约上执行下注函数(选择:字符串)。

4.让我们看一看bet函数

@Callable(i)

func bet (playerChoice) = {

let newGameNum = IncrementGameNum()

let gameId = toBase58String(i.transactionId)

let pmt = extract(i.payment)

let betNotInWaves = isDefined(pmt.assetId)

let feeNotInWaves = isDefined(pmt.assetId)

let winAmt = ValidateBetAndDefineWinAmt(pmt.amount, playerChoice)

let txIdUsed = isDefined(getString(this, gameId))

if (betNotInWaves)

then throw ("Bet amount must be in Waves")

else if (feeNotInWaves)

then throw ("Transaction's fee must be in Waves")

else if (txIdUsed)

then throw ("Passed txId had been used before. Game aborted.")

else {

let playerPubKey58 = toBase58String(i.callerPublicKey)

let gameDataStr = FormatGameDataStr(STATESUBMITTED, playerChoice, playerPubKey58, height, winAmt, "")

ScriptResult(WriteSet(cons(DataEntry(RESERVATIONKEY, ValidateAndIncreaseReservedAmt(winAmt)),cons(DataEntry(GAMESCOUNTERKEY, newGameNum), cons(DataEntry(gameId, gameDataStr), nil)))), TransferSet(cons(ScriptTransfer(SERVER, COMMISSION, unit), nil)))

}

该函数在智能合约中记录了一场新的游戏。

l?游戏的ID = game id

l?游戏状态?= 已提交

l?玩家选择(选择范围为50)

l?公钥

l?潜在奖励(取决于玩家的下注)

这是键值数据库在区块链上的呈现方式

{

"type": "string",

"value": "03WON_0283_448t8Jn9P3717UnXFEVD5VWjfeGE5gBNeWg58H2aJeQEgJ_06574069_09116020000_0229",

"key": "2GKTX6NLTgUrE4iy9HtpSSHpZ3G8W4cMfdjyvvnc21dx" ??}

“Key”是新游戏的game id,其他数据都包括在了value属性部分。

这是数据都储存在智能合约的数据一栏中。

7.服务器发送一个调用事务到智能合约中(broadcast InvocationTX)。该事务包含了一个调用以生成撤回函数。(gameId, rasSign):

该函数是含有?game id 以及RSA签名的唯一id,因此签名保证了其不可篡改性。

这意味着什么?

我们使用相同的值并且将RSA签名应用在其中,这就是RSA算法的工作原理。 由于game id和RSA算法的结果是未知的,因此不可能操控其最终数值,并且猜测最终数值也变得毫无意义。

8.区块链接收到一个运行撤回函数的事务(gameId,rsaSign)

9.撤回函数内包含一个调用GenerateRandIn函数。

# @return 1 ... 100

func GenerateRandInt (gameId,rsaSign) = {

# verify RSA signature to proof random

let rsaSigValid = rsaVerify (SHA256, toBytes(gameId), rsaSign, RSAPUBLIC)

if (rsaSigValid)

then {

let rand = (toInt(sha256(rsaSign)) % 100)

if ((0 > rand))

then ((-1 * rand) + 1)

else (rand + 1)

}

else throw ("Invalid RSA signature")

rand 即为一个随机数

首先,RSA签名结果的字符串已被使用。其次,其已通过SHA-256哈希处理。

我们无法预测签名结果以及后续的哈希处理,因此生成结果不可能被干预。为了获取指定范围内的一个数字(例如从1到100),转换函数toInt 以及%100(mod?模拟)也被应用在其中。

在本文开头,我们提到了rsaVerify()函数,该函数允许通过私钥针对公钥来检查RSA签名的有效性。这里是部分GenerateRandInt(gameId,rsaSign):

rsaVerify (SHA256, toBytes(gameId), rsaSign, RSAPUBLIC

以此开始,?RSAPUBLIC公钥以及rsaSign字符串已被使用,该签名用以验证其有效性。 如果验证通过,那么数字将会生成。 否则系统将会判定该签名无效(Invalid RSA signature)

服务器需要使用私钥注册游戏ID并且在2880个区块内发送有效的RSA签名。在部署智能合约的同时该选项已被管理。如果规定时间内没有其他情况则玩家获胜。在此基础上,奖励会被用户单独发送。 ?就此而言,作弊对服务器将毫无益处,因为作弊会导致输局。 如下示例:

玩家参与摇色子游戏。玩家从6个面中选择2个,并下注14个WAVES。 如果服务器未在设定的时间(2,880区块)内向智能合约发送有效的RSA签名,则用户将收到34.44 WAVES。

就数字生成而言,我们使用了预言机,一个非区块链的外部系统。服务器应用一个RSA签名到游戏ID中,智能合约将会检查签名的有效性并且判断赢家。如果服务器未发送结果,那么玩家则会自动胜出。

这种方法保证了人为操纵是不可能的,所有Tradisys游戏都基于以上阐述的算法以保证我们游戏的公平性和透明性。 所有内容都可以公开审核以确保其公正。

—-

编译者/作者:waves中国社区

玩币族申明:玩币族作为开放的资讯翻译/分享平台,所提供的所有资讯仅代表作者个人观点,与玩币族平台立场无关,且不构成任何投资理财建议。文章版权归原作者所有。

LOADING...
LOADING...