##// END OF EJS Templates
worker: ability to disable thread unsafe tasks...
Gregory Szorc -
r38754:ef3838a4 default
parent child Browse files
Show More
@@ -63,18 +63,27 b' def _numworkers(ui):'
63
63
64 if pycompat.isposix or pycompat.iswindows:
64 if pycompat.isposix or pycompat.iswindows:
65 _STARTUP_COST = 0.01
65 _STARTUP_COST = 0.01
66 # The Windows worker is thread based. If tasks are CPU bound, threads
67 # in the presence of the GIL result in excessive context switching and
68 # this overhead can slow down execution.
69 _DISALLOW_THREAD_UNSAFE = pycompat.iswindows
66 else:
70 else:
67 _STARTUP_COST = 1e30
71 _STARTUP_COST = 1e30
72 _DISALLOW_THREAD_UNSAFE = False
68
73
69 def worthwhile(ui, costperop, nops):
74 def worthwhile(ui, costperop, nops, threadsafe=True):
70 '''try to determine whether the benefit of multiple processes can
75 '''try to determine whether the benefit of multiple processes can
71 outweigh the cost of starting them'''
76 outweigh the cost of starting them'''
77
78 if not threadsafe and _DISALLOW_THREAD_UNSAFE:
79 return False
80
72 linear = costperop * nops
81 linear = costperop * nops
73 workers = _numworkers(ui)
82 workers = _numworkers(ui)
74 benefit = linear - (_STARTUP_COST * workers + linear / workers)
83 benefit = linear - (_STARTUP_COST * workers + linear / workers)
75 return benefit >= 0.15
84 return benefit >= 0.15
76
85
77 def worker(ui, costperarg, func, staticargs, args):
86 def worker(ui, costperarg, func, staticargs, args, threadsafe=True):
78 '''run a function, possibly in parallel in multiple worker
87 '''run a function, possibly in parallel in multiple worker
79 processes.
88 processes.
80
89
@@ -88,9 +97,13 b' def worker(ui, costperarg, func, statica'
88
97
89 args - arguments to split into chunks, to pass to individual
98 args - arguments to split into chunks, to pass to individual
90 workers
99 workers
100
101 threadsafe - whether work items are thread safe and can be executed using
102 a thread-based worker. Should be disabled for CPU heavy tasks that don't
103 release the GIL.
91 '''
104 '''
92 enabled = ui.configbool('worker', 'enabled')
105 enabled = ui.configbool('worker', 'enabled')
93 if enabled and worthwhile(ui, costperarg, len(args)):
106 if enabled and worthwhile(ui, costperarg, len(args), threadsafe=threadsafe):
94 return _platformworker(ui, func, staticargs, args)
107 return _platformworker(ui, func, staticargs, args)
95 return func(*staticargs + (args,))
108 return func(*staticargs + (args,))
96
109
@@ -65,7 +65,7 b' update with worker processes'
65
65
66 $ cat <<EOF > forceworker.py
66 $ cat <<EOF > forceworker.py
67 > from mercurial import extensions, worker
67 > from mercurial import extensions, worker
68 > def nocost(orig, ui, costperop, nops):
68 > def nocost(orig, ui, costperop, nops, threadsafe=True):
69 > return worker._numworkers(ui) > 1
69 > return worker._numworkers(ui) > 1
70 > def uisetup(ui):
70 > def uisetup(ui):
71 > extensions.wrapfunction(worker, 'worthwhile', nocost)
71 > extensions.wrapfunction(worker, 'worthwhile', nocost)
General Comments 0
You need to be logged in to leave comments. Login now