PyBitmessage-2021-04-27/src/workprover/forkingsolver.py

110 lines
2.6 KiB
Python
Raw Normal View History

2018-06-23 08:57:34 +00:00
import multiprocessing
2018-06-23 11:00:24 +00:00
import os
2018-06-23 08:57:34 +00:00
import struct
import dumbsolver
def setIdle():
2018-06-28 14:19:50 +00:00
if hasattr(os, "nice"):
os.nice(40)
return
2018-06-23 08:57:34 +00:00
try:
import psutil
psutil.Process().nice(psutil.IDLE_PRIORITY_CLASS)
return
except:
pass
try:
import win32api
import win32con
import win32process
PID = win32api.GetCurrentProcessId()
handle = win32api.OpenProcess(win32con.PROCESS_ALL_ACCESS, True, PID)
win32process.SetPriorityClass(handle, win32process.IDLE_PRIORITY_CLASS)
except:
pass
def threadFunction(local, remote, codePath, threadNumber):
remote.close()
setIdle()
solver = dumbsolver.DumbSolver(codePath)
while True:
received = local.recv()
command = received[0]
arguments = received[1: ]
if command == "search":
initialHash, target, seed, timeout = arguments
appendedSeed = seed + struct.pack(">Q", threadNumber)
nonce, iterationsCount = solver.search(initialHash, target, appendedSeed, timeout)
local.send(("done", nonce, iterationsCount))
elif command == "shutdown":
local.close()
return
class ForkingSolver(object):
def __init__(self, codePath):
self.pipes = []
self.processes = []
2018-06-28 14:19:50 +00:00
self.status = 0
2018-06-23 08:57:34 +00:00
self.codePath = codePath
def search(self, initialHash, target, seed, timeout):
for i in self.pipes:
i.send(("search", initialHash, target, seed, timeout))
bestNonce, totalIterationsCount = None, 0
for i in self.pipes:
event, nonce, iterationsCount = i.recv()
if nonce is not None:
bestNonce = nonce
totalIterationsCount += iterationsCount
return bestNonce, totalIterationsCount
2018-06-28 14:19:50 +00:00
def setConfiguration(self, configuration):
if configuration is None:
parallelism = 0
else:
parallelism = min(4096, configuration)
2018-06-23 08:57:34 +00:00
2018-06-28 14:19:50 +00:00
for i in xrange(len(self.processes), parallelism):
2018-06-23 08:57:34 +00:00
local, remote = multiprocessing.Pipe()
process = multiprocessing.Process(target = threadFunction, args = (remote, local, self.codePath, i))
process.start()
remote.close()
self.pipes.append(local)
self.processes.append(process)
2018-06-28 14:19:50 +00:00
for i in xrange(parallelism, len(self.processes)):
2018-06-23 08:57:34 +00:00
pipe = self.pipes.pop()
pipe.send(("shutdown", ))
pipe.close()
2018-06-28 14:19:50 +00:00
for i in xrange(parallelism, len(self.processes)):
2018-06-23 08:57:34 +00:00
self.processes.pop().join()
2018-06-28 14:19:50 +00:00
self.status = parallelism