Оценка для лотерейного контракта - PullRequest
0 голосов
/ 13 мая 2019

Я пытаюсь написать лотерейный контракт в Солидности. Я обнаружил этот подход в своем исследовании, где случайное число рассчитывается по данным игроков. Сейчас я пытаюсь улучшить этот алгоритм.

Пока это мой алгоритм: Алгоритм (png)

На этапе 1 хеш одноразового номера и хеш одноразового номера в сочетании с числом get хранится в контракте.

По сравнению со старым подходом я удалил открытый ключ из вычисления хеша, потому что он публично отправляется с каждой транзакцией. Вместо этого я добавил nonce на этапе 1. Полагаю, это помешает атакующему лучше создать радужный стол.

На втором этапе игроки освобождают число и одноразовый номер. Подобный расчет гарантирует, что игрок не может изменить число или одноразовый номер:

function stage2 (uint256 _nonce, uint256 _number) external {

    require (stage == Stage.TWO, "Stage TWO isn't active!");
    require (players [msg.sender].nonceHash == keccak256 (abi.encodePacked (_nonce)), "Nonce isn't matching!");
    require (players [msg.sender].noncePlusNumberHash == keccak256 (abi.encodePacked (_nonce + _number)), "Number isn't matching!");
    require (players [msg.sender].number == 0, "You already submitted your number!");

    players [msg.sender].number = _number;

    winning_number = (winning_number ^ _number) % max;

    // ...
}

Единственная проблема, которую я вижу, состоит в том, что последний игрок может предварительно рассчитать окончательный результат, прежде чем освободить свое число. Требуя прислать его номер, чтобы иметь право выиграть джекпот, мы можем предотвратить получение от него преимущества. Но рассмотрим случай, когда игрок A выигрывает при подаче n - 1, а игрок B выигрывает, если последний игрок представил свой номер. Последний игрок может затем выбрать, выиграют ли А или В.

Думаю, во многих случаях это не большая проблема. Но если нам все еще нужно это предотвратить, я нашел два решения:

(I) Покинуть второй этап, только если все игроки представят свой номер. Если по истечении определенного времени остается заявка, аннулируйте весь контракт (может быть полезно, если личность всех игроков известна).

(II) Каждый игрок должен отправить депозит вместе со своим представлением. Депозит возвращается игроку после отправки его номера.

У меня такой вопрос: есть ли в этом алгоритме какие-то странные случаи, которые я до сих пор не рассматривал?

...