Acabou o jogo e é do Brasil.
Tx callback da Chainlink:
https://kovan.etherscan.io/tx/0x2d55a999666a9afb17bd60fdefb21db58d138acde8bedbb46adf26488826c294Mas agora tenho uma pessima notícia para os apostadores.
Dei claim no meu prêmio e me deparei com o valor errado. Fui debuggar e descobri algo que eu não tinha percebido antes.
Esse é o código que calcula o prêmio:
uint256 userInitialBets = games[_gameId].bets[winner][msg.sender].amount;
uint256 winnerPoolBets = games[_gameId].totalBets[winner];
uint256 loserPoolBets = games[_gameId].totalBets[winner == 1 ? 2 : 1];
uint256 prizeAmount = userInitialBets.div(winnerPoolBets).mul(loserPoolBets).add(userInitialBets);
Algo de errado ai? A principio, parece que não. Pega o valor do bet (0.00987), divide pela pool total de apostas no vencedor (0.05325), o que daria 0.185352113. Multiplica esse valor pela pool de apostas dos perdedores (0.04881) e dá 0.00904703664. Adiciona o valor apostado pelo usuário no time vencedor (0.00987).
Prêmio final de 0.00987 / 0.05325 * 0.04881 + 0.00987 =
0.0189170366!
https://kovan.etherscan.io/tx/0x9e6ce0b658c3dd86efd5b2989d6ffe59cfe7563610bf54e3f91d236c34e1f4cc...mas o claim foi de 0.00987... por que?
A primeira divisão (0.00987 / 0.05325) retorna 0.18, que é um número abaixo de 1. Acontece que a solidity arredonda o número para zero...
/**
* @dev Returns the integer division of two unsigned integers. Reverts on
* division by zero. The result is rounded towards zero.
*
* Counterpart to Solidity's `/` operator. Note: this function uses a
* `revert` opcode (which leaves remaining gas untouched) while Solidity
* uses an invalid opcode to revert (consuming all remaining gas).
*
* Requirements:
* - The divisor cannot be zero.
*/
function div(uint256 a, uint256 b) internal pure returns (uint256) {
return div(a, b, "SafeMath: division by zero");
}
No final das contas, a matemática fica: 0 * 0.04881 + 0.00987 = 0.00987
A solução seria primeiro multiplicar o valor para depois dividir.
#rugDoNinjabets
#rektnews