Added on_network_block hook to Share manager.
authorslush <info@bitcoin.cz>
Mon, 10 Sep 2012 17:43:58 +0000 (17:43 +0000)
committerslush <info@bitcoin.cz>
Mon, 10 Sep 2012 17:43:58 +0000 (17:43 +0000)
Implementation of ShareLimiter API

launcher_demo.tac
lib/template_registry.py
mining/__init__.py
mining/interfaces.py
mining/service.py
mining/subscription.py

index 6759ad8..22e3799 100644 (file)
@@ -19,9 +19,11 @@ application = stratum.setup(on_startup)
 import mining
 
 from mining.interfaces import Interfaces
-from mining.interfaces import WorkerManagerInterface, ShareManagerInterface, TimestamperInterface
+from mining.interfaces import WorkerManagerInterface, TimestamperInterface, \
+                            ShareManagerInterface, ShareLimiterInterface
 
 Interfaces.set_share_manager(ShareManagerInterface())
+Interfaces.set_share_limiter(ShareLimiterInterface())
 Interfaces.set_worker_manager(WorkerManagerInterface())
 Interfaces.set_timestamper(TimestamperInterface())
 
index cab911f..435aeb4 100644 (file)
@@ -30,7 +30,7 @@ class TemplateRegistry(object):
     service and implements block validation and submits.'''
     
     def __init__(self, block_template_class, coinbaser, bitcoin_rpc, instance_id,
-                 on_block_callback):
+                 on_template_callback, on_block_callback):
         self.prevhashes = {}
         self.jobs = weakref.WeakValueDictionary()
         
@@ -42,6 +42,7 @@ class TemplateRegistry(object):
         self.block_template_class = block_template_class
         self.bitcoin_rpc = bitcoin_rpc
         self.on_block_callback = on_block_callback
+        self.on_template_callback = on_template_callback
         
         self.last_block = None
         self.update_in_progress = False
@@ -89,7 +90,16 @@ class TemplateRegistry(object):
                 del self.prevhashes[ph]
                 
         log.info("New template for %s" % prevhash)
-        self.on_block_callback(new_block)
+
+        if new_block:
+            # Tell the system about new block
+            # It is mostly important for share manager
+            self.on_block_callback(prevhash)
+
+        # Everything is ready, let's broadcast jobs!
+        self.on_template_callback(new_block)
+        
+
         #from twisted.internet import reactor
         #reactor.callLater(10, self.on_block_callback, new_block) 
               
index 73e6d15..588bea4 100644 (file)
@@ -35,7 +35,8 @@ def setup(on_startup):
                                 coinbaser,
                                 bitcoin_rpc,
                                 settings.INSTANCE_ID,
-                                MiningSubscription.on_block)
+                                MiningSubscription.on_template,
+                                Interfaces.share_manager.on_network_block)
 
     # Template registry is the main interface between Stratum service
     # and pool core logic
index 179c85e..1fef21a 100644 (file)
@@ -19,12 +19,28 @@ class WorkerManagerInterface(object):
     def authorize(self, worker_name, worker_password):
         return True
 
+class ShareLimiterInterface(object):
+    '''Implement difficulty adjustments here'''
+    
+    def submit(self, connection_ref, current_difficulty, timestamp):
+        '''connection - weak reference to Protocol instance
+           current_difficulty - difficulty of the connection
+           timestamp - submission time of current share
+           
+           - raise SubmitException for stop processing this request
+           - call mining.set_difficulty on connection to adjust the difficulty'''
+        pass
+    
 class ShareManagerInterface(object):
     def __init__(self):
         # Fire deferred when manager is ready
         self.on_load = defer.Deferred()
         self.on_load.callback(True)
 
+    def on_network_block(self, prevhash):
+        '''Prints when there's new block coming from the network (possibly new round)'''
+        pass
+    
     def on_submit_share(self, worker_name, block_header, block_hash, shares, timestamp, is_valid):
         log.info("%s %s %s" % (block_hash, 'valid' if is_valid else 'INVALID', worker_name))
     
@@ -49,6 +65,7 @@ class PredictableTimestamperInterface(TimestamperInterface):
 class Interfaces(object):
     worker_manager = None
     share_manager = None
+    share_limiter = None
     timestamper = None
     template_registry = None
     
@@ -59,6 +76,10 @@ class Interfaces(object):
     @classmethod        
     def set_share_manager(cls, manager):
         cls.share_manager = manager
+
+    @classmethod        
+    def set_share_limiter(cls, limiter):
+        cls.share_limiter = limiter
     
     @classmethod
     def set_timestamper(cls, manager):
index d9efa95..ff86d96 100644 (file)
@@ -26,6 +26,8 @@ class MiningService(GenericService):
         '''Connect this RPC call to 'bitcoind -blocknotify' for 
         instant notification about new block on the network.
         See blocknotify.sh in /scripts/ for more info.'''
+        
+        log.info("New block notification received")
         Interfaces.template_registry.update_block()
         return True 
     
@@ -50,13 +52,12 @@ class MiningService(GenericService):
         
         extranonce1 = Interfaces.template_registry.get_new_extranonce1()
         extranonce2_size = Interfaces.template_registry.extranonce2_size
-
+        extranonce1_hex = binascii.hexlify(extranonce1)
+        
         session = self.connection_ref().get_session()
         session['extranonce1'] = extranonce1
         session['difficulty'] = 1 # Following protocol specs, default diff is 1
 
-        extranonce1_hex = binascii.hexlify(extranonce1)
-            
         return Pubsub.subscribe(self.connection_ref(), MiningSubscription()) + (extranonce1_hex, extranonce2_size)
     
     '''    
@@ -73,7 +74,7 @@ class MiningService(GenericService):
         log.info("LEN %.03f" % (time.time() - start))
         return ret
     '''
-    
+        
     def submit(self, worker_name, job_id, extranonce2, ntime, nonce):
         '''Try to solve block candidate using given parameters.'''
         
@@ -91,9 +92,10 @@ class MiningService(GenericService):
             raise SubmitException("Connection is not subscribed for mining")
         
         difficulty = session['difficulty']
-
         submit_time = Interfaces.timestamper.time()
-        
+    
+        Interfaces.share_limiter.submit(self.connection_ref, difficulty, submit_time)
+            
         # This checks if submitted share meet all requirements
         # and it is valid proof of work.
         try:
index 3e39a60..d04c62e 100644 (file)
@@ -11,7 +11,7 @@ class MiningSubscription(Subscription):
     event = 'mining.notify'
     
     @classmethod
-    def on_block(cls, is_new_block):
+    def on_template(cls, is_new_block):
         '''This is called when TemplateRegistry registers
            new block which we have to broadcast clients.'''