yocto-sumo源码解析(八): ProcessServer

从前面章节的论述中,我们知道BitBakeServer实际上是一个ProcessServer,什么是ProcessServer不可不了解。

1. 类的声明: 首先这是一个python的多进程包里面的进程子类,关于多进程包可以参阅:https://docs.python.org/2/library/multiprocessing.html,在api的使用上尽量保持和多线程使用习惯一致。

class ProcessServer(multiprocessing.Process):

2. 构造函数:初始化一系列成员变量,变量命名非常易懂,这里在代码块里面进行注释

    def __init__(self, lock, sock, sockname):
multiprocessing.Process.__init__(self)
self.command_channel = False                 #命令通道,从名字上看应该是用于接收命令请求的。
self.command_channel_reply = False           #命令通道响应,从名字上看应该是用于构造命令响应的。
self.quit = False                            #服务是否需要退出。
self.heartbeat_seconds = 1 # default, BB_HEARTBEAT_EVENT will be checked once we have a datastore.
                                                     #心跳包间隔。
self.next_heartbeat = time.time()            #下次心跳时间。 self.event_handle = None                     #事件处理
self.haveui = False                          #是否有ui
self.lastui = False                          #上次ui
self.xmlrpc = False                          #xmlrpc,这个估计用于远程过程调用。 self._idlefuns = {}                          #空闲函数字典 self.bitbake_lock = lock                     #bitbake实例锁,从这个成员看,ProcessServer的设计似乎还是偏向于给bitbake专用。
self.sock = sock                             #套接字,从前面上下文看,可能是域套接字。
self.sockname = sockname                     #套接字名字

3. 注册空闲函数:

    def register_idle_function(self, function, data):
"""Register a function to be called while the server is idle"""
assert hasattr(function, '__call__')
self._idlefuns[function] = data

4. run函数:对于这个,熟悉多线程的应该很有似曾相识的感觉:

    def run(self):
        #若xmlrpcinterface[0]不为None,或者不为False,那么建立BitBakeXMLRPCServer,应该是为了远程模式。
if self.xmlrpcinterface[0]:
self.xmlrpc = bb.server.xmlrpcserver.BitBakeXMLRPCServer(self.xmlrpcinterface, self.cooker, self) print("Bitbake XMLRPC server address: %s, server port: %s" % (self.xmlrpc.host, self.xmlrpc.port))

        #设置心跳包间隔时长。
heartbeat_event = self.cooker.data.getVar('BB_HEARTBEAT_EVENT')
if heartbeat_event:
try:
self.heartbeat_seconds = float(heartbeat_event)
except:
bb.warn('Ignoring invalid BB_HEARTBEAT_EVENT=%s, must be a float specifying seconds.' % heartbeat_event)

        #设置服务器超时时长。
self.timeout = self.server_timeout or self.cooker.data.getVar('BB_SERVER_TIMEOUT')
try:
if self.timeout:
self.timeout = float(self.timeout)
except:
bb.warn('Ignoring invalid BB_SERVER_TIMEOUT=%s, must be a float specifying seconds.' % self.timeout)         #向锁文件写入拥有该锁的pid,如果是远程模式,同时写入主机名和端口号。
try:
self.bitbake_lock.seek(0)
self.bitbake_lock.truncate()
if self.xmlrpc:
self.bitbake_lock.write("%s %s:%s\n" % (os.getpid(), self.xmlrpc.host, self.xmlrpc.port))
else:
self.bitbake_lock.write("%s\n" % (os.getpid()))
self.bitbake_lock.flush()
except Exception as e:
print("Error writing to lock file: %s" % str(e))
pass

        #调用main函数,如果配置了画像模式则建立画像流程。
if self.cooker.configuration.profile:
try:
import cProfile as profile
except:
import profile
prof = profile.Profile() ret = profile.Profile.runcall(prof, self.main) prof.dump_stats("profile.log")
bb.utils.process_profilelog("profile.log")
print("Raw profiling information saved to profile.log and processed statistics to profile.log.processed") else:
ret = self.main() return ret
上一篇:Codeforces ZeptoLab Code Rush 2015 D.Om Nom and Necklace(kmp)


下一篇:MvcPager.dll使用实现无刷新分页以及MvcPager的Nuget程序包实现刷新分页