Esempio n. 1
0
        public async Task <Share> SubmitShareAsync(StratumClient worker,
                                                   MoneroSubmitShareRequest request, MoneroWorkerJob workerJob, double stratumDifficultyBase)
        {
            Contract.RequiresNonNull(worker, nameof(worker));
            Contract.RequiresNonNull(request, nameof(request));

            logger.LogInvoke(LogCat, new[] { worker.ConnectionId });
            var context = worker.GetContextAs <MoneroWorkerContext>();

            var job = currentJob;

            if (workerJob.Height != job?.BlockTemplate.Height)
            {
                throw new StratumException(StratumError.MinusOne, "block expired");
            }

            // validate & process
            var(share, blobHex, blobHash) = job.ProcessShare(request.Nonce, workerJob.ExtraNonce, request.Hash, worker);

            // enrich share with common data
            share.PoolId            = poolConfig.Id;
            share.IpAddress         = worker.RemoteEndpoint.Address.ToString();
            share.Miner             = context.MinerName;
            share.Worker            = context.WorkerName;
            share.PayoutInfo        = context.PaymentId;
            share.UserAgent         = context.UserAgent;
            share.Source            = clusterConfig.ClusterName;
            share.NetworkDifficulty = job.BlockTemplate.Difficulty;
            share.Created           = clock.Now;

            // if block candidate, submit & check if accepted by network
            if (share.IsBlockCandidate)
            {
                logger.Info(() => $"[{LogCat}] Submitting block {share.BlockHeight} [{blobHash.Substring(0, 6)}]");

                share.IsBlockCandidate = await SubmitBlockAsync(share, blobHex, blobHash);

                if (share.IsBlockCandidate)
                {
                    logger.Info(() => $"[{LogCat}] Daemon accepted block {share.BlockHeight} [{blobHash.Substring(0, 6)}] submitted by {context.MinerName}");
                    blockSubmissionSubject.OnNext(Unit.Default);

                    share.TransactionConfirmationData = blobHash;
                }

                else
                {
                    // clear fields that no longer apply
                    share.TransactionConfirmationData = null;
                }
            }

            return(share);
        }
Esempio n. 2
0
        public async Task <IShare> SubmitShareAsync(StratumClient <MoneroWorkerContext> worker,
                                                    MoneroSubmitShareRequest request, MoneroWorkerJob workerJob,
                                                    double stratumDifficulty, double stratumDifficultyBase)
        {
            MoneroJob job;

            lock (jobLock)
            {
                if (workerJob.Height != currentJob.BlockTemplate.Height)
                {
                    throw new StratumException(StratumError.MinusOne, "block expired");
                }

                job = currentJob;
            }

            // validate & process
            var share = job?.ProcessShare(request.Nonce, workerJob.ExtraNonce, request.Hash, stratumDifficulty);

            // if block candidate, submit & check if accepted by network
            if (share.IsBlockCandidate)
            {
                logger.Info(() => $"[{LogCat}] Submitting block {share.BlockHeight} [{share.BlobHash.Substring(0, 6)}]");

                share.IsBlockCandidate = await SubmitBlockAsync(share);

                if (share.IsBlockCandidate)
                {
                    logger.Info(() => $"[{LogCat}] Daemon accepted block {share.BlockHeight} [{share.BlobHash.Substring(0, 6)}]");

                    share.TransactionConfirmationData = share.BlobHash;
                }

                else
                {
                    // clear fields that no longer apply
                    share.TransactionConfirmationData = null;
                }
            }

            // enrich share with common data
            share.PoolId                = poolConfig.Id;
            share.IpAddress             = worker.RemoteEndpoint.Address.ToString();
            share.Miner                 = worker.Context.MinerName;
            share.Worker                = worker.Context.WorkerName;
            share.PayoutInfo            = worker.Context.PaymentId;
            share.UserAgent             = worker.Context.UserAgent;
            share.NetworkDifficulty     = BlockchainStats.NetworkDifficulty;
            share.StratumDifficulty     = stratumDifficulty;
            share.StratumDifficultyBase = stratumDifficultyBase;
            share.Created               = DateTime.UtcNow;

            return(share);
        }