pwrake 2.2.0 → 2.2.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/bin/pwrake +2 -0
- data/lib/pwrake/branch/communicator_set.rb +1 -1
- data/lib/pwrake/branch/shell.rb +2 -6
- data/lib/pwrake/branch/shell_profiler.rb +4 -3
- data/lib/pwrake/master/master.rb +13 -8
- data/lib/pwrake/master/master_application.rb +4 -0
- data/lib/pwrake/mpi/branch.rb +1 -0
- data/lib/pwrake/queue/queue_array.rb +9 -9
- data/lib/pwrake/queue/task_queue.rb +15 -15
- data/lib/pwrake/report/parallelism.rb +74 -84
- data/lib/pwrake/report/report.rb +36 -12
- data/lib/pwrake/task/task_algorithm.rb +32 -21
- data/lib/pwrake/task/task_wrapper.rb +9 -9
- data/lib/pwrake/version.rb +1 -1
- data/lib/pwrake/worker/executor.rb +38 -1
- data/lib/pwrake/worker/invoker.rb +21 -6
- data/lib/pwrake/worker/writer.rb +20 -24
- metadata +3 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 165b50b8450d65b495aefffe22cc3a8e02ae3828
|
4
|
+
data.tar.gz: 210a2fcb2b42cb1b70696e84595e20dd71332c83
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ce57a49375d39fc42a4a785bb9e703fe4f90af8f5ec2db63c4a1d5fb7beb3c3d3f44b37742a1cbb8c9f40621cbc3d66a8c458cb17a6d530d9ad43374bda829e9
|
7
|
+
data.tar.gz: fae5ad1e68b9b7f87ab12428e9826a50ed8809120c2f4a5a45215518ff7e590f82051d6e4fb7e63914222b81c6dbea762c8ef7cfaf8e88a4823f6e176d325df0
|
data/bin/pwrake
CHANGED
@@ -15,6 +15,7 @@ require "pwrake/master/master_application"
|
|
15
15
|
require "pwrake/task/task_manager"
|
16
16
|
require "pwrake/task/task_algorithm"
|
17
17
|
require "pwrake/branch/branch_application"
|
18
|
+
|
18
19
|
class Rake::Application
|
19
20
|
include Pwrake::BranchApplication
|
20
21
|
prepend Pwrake::MasterApplication
|
@@ -22,6 +23,7 @@ class Rake::Application
|
|
22
23
|
end
|
23
24
|
class Rake::Task
|
24
25
|
include Pwrake::TaskAlgorithm
|
26
|
+
prepend Pwrake::TaskInvoke
|
25
27
|
end
|
26
28
|
|
27
29
|
# does NOT exit when writing to broken pipe
|
data/lib/pwrake/branch/shell.rb
CHANGED
@@ -72,11 +72,6 @@ module Pwrake
|
|
72
72
|
false
|
73
73
|
end
|
74
74
|
|
75
|
-
def set_current_task(task_id,task_name)
|
76
|
-
@task_id = task_id
|
77
|
-
@task_name = task_name
|
78
|
-
end
|
79
|
-
|
80
75
|
def backquote(*command)
|
81
76
|
command = command.join(' ')
|
82
77
|
@lock.synchronize do
|
@@ -156,7 +151,7 @@ module Pwrake
|
|
156
151
|
ensure
|
157
152
|
end_time = Time.now
|
158
153
|
@status = @@profiler.profile(@task_id, @task_name, cmd,
|
159
|
-
|
154
|
+
start_time, end_time, host, @ncore, @status)
|
160
155
|
end
|
161
156
|
end
|
162
157
|
|
@@ -232,6 +227,7 @@ module Pwrake
|
|
232
227
|
@task_id = task_id
|
233
228
|
@task_name = task_name
|
234
229
|
task = Rake.application[task_name]
|
230
|
+
@ncore = task.wrapper.n_used_cores
|
235
231
|
begin
|
236
232
|
task.execute(task.arguments) if task.needed?
|
237
233
|
result = "taskend:#{@id}:#{task.name}"
|
@@ -6,7 +6,7 @@ module Pwrake
|
|
6
6
|
|
7
7
|
HEADER_FOR_PROFILE =
|
8
8
|
%w[exec_id task_id task_name command
|
9
|
-
start_time end_time elap_time host status]
|
9
|
+
start_time end_time elap_time host ncore status]
|
10
10
|
|
11
11
|
HEADER_FOR_GNU_TIME =
|
12
12
|
%w[realtime systime usrtime maxrss averss memsz
|
@@ -85,7 +85,8 @@ module Pwrake
|
|
85
85
|
t.strftime("%F %T.%L")
|
86
86
|
end
|
87
87
|
|
88
|
-
def profile(task_id, task_name, cmd, start_time, end_time,
|
88
|
+
def profile(task_id, task_name, cmd, start_time, end_time,
|
89
|
+
host=nil, ncore=nil, status=nil)
|
89
90
|
id = @lock.synchronize do
|
90
91
|
id = @id
|
91
92
|
@id += 1
|
@@ -96,7 +97,7 @@ module Pwrake
|
|
96
97
|
format_time(start_time),
|
97
98
|
format_time(end_time),
|
98
99
|
"%.3f" % (end_time-start_time),
|
99
|
-
host, status ]
|
100
|
+
host, ncore, status ]
|
100
101
|
end
|
101
102
|
case status
|
102
103
|
when ""
|
data/lib/pwrake/master/master.rb
CHANGED
@@ -144,7 +144,6 @@ module Pwrake
|
|
144
144
|
@task_queue = queue_class.new(@hostinfo_by_id)
|
145
145
|
|
146
146
|
@branch_setup_thread = Thread.new do
|
147
|
-
#@channels.each do |chan|
|
148
147
|
create_fiber(@hdl_set) do |hdl|
|
149
148
|
while s = hdl.get_line
|
150
149
|
case s
|
@@ -158,12 +157,6 @@ module Pwrake
|
|
158
157
|
end
|
159
158
|
end
|
160
159
|
@selector.run
|
161
|
-
@killed = 0
|
162
|
-
[:TERM,:INT].each do |sig|
|
163
|
-
Signal.trap(sig) do
|
164
|
-
signal_trap(sig)
|
165
|
-
end
|
166
|
-
end
|
167
160
|
end
|
168
161
|
|
169
162
|
end
|
@@ -190,8 +183,11 @@ module Pwrake
|
|
190
183
|
end
|
191
184
|
|
192
185
|
def invoke(t, args)
|
186
|
+
Log.debug "Master#invoke start: #{t.class}[#{t.name}]"
|
193
187
|
@failed = false
|
194
188
|
t.pw_search_tasks(args)
|
189
|
+
return if @running
|
190
|
+
@running = true
|
195
191
|
|
196
192
|
if @option['GRAPH_PARTITION']
|
197
193
|
setup_postprocess0
|
@@ -210,8 +206,17 @@ module Pwrake
|
|
210
206
|
|
211
207
|
setup_postprocess1
|
212
208
|
@branch_setup_thread.join
|
209
|
+
@killed = 0
|
210
|
+
[:TERM,:INT].each do |sig|
|
211
|
+
Signal.trap(sig) do
|
212
|
+
signal_trap(sig)
|
213
|
+
end
|
214
|
+
end
|
213
215
|
send_task_to_idle_core
|
214
|
-
|
216
|
+
setup_fiber(t)
|
217
|
+
end
|
218
|
+
|
219
|
+
def setup_fiber(t)
|
215
220
|
n_retry = @option["RETRY"]
|
216
221
|
create_fiber(@hdl_set) do |hdl|
|
217
222
|
while s = hdl.get_line
|
data/lib/pwrake/mpi/branch.rb
CHANGED
@@ -68,18 +68,18 @@ module Pwrake
|
|
68
68
|
|
69
69
|
def shift(host_info=nil)
|
70
70
|
return super() unless host_info
|
71
|
-
|
71
|
+
i_found = nil
|
72
72
|
(size-1).downto(0) do |i|
|
73
73
|
tw = at(i)
|
74
74
|
if tw.acceptable_for(host_info)
|
75
75
|
if tw.untried_host?(host_info)
|
76
76
|
return delete_at(i)
|
77
77
|
else
|
78
|
-
|
78
|
+
i_found ||= i
|
79
79
|
end
|
80
80
|
end
|
81
81
|
end
|
82
|
-
|
82
|
+
(i_found) ? delete_at(i_found) : nil
|
83
83
|
end
|
84
84
|
end
|
85
85
|
|
@@ -90,18 +90,18 @@ module Pwrake
|
|
90
90
|
|
91
91
|
def shift(host_info=nil)
|
92
92
|
return super() unless host_info
|
93
|
-
|
93
|
+
i_found = nil
|
94
94
|
size.times do |i|
|
95
95
|
tw = at(i)
|
96
96
|
if tw.acceptable_for(host_info)
|
97
97
|
if tw.untried_host?(host_info)
|
98
98
|
return delete_at(i)
|
99
99
|
else
|
100
|
-
|
100
|
+
i_found ||= i
|
101
101
|
end
|
102
102
|
end
|
103
103
|
end
|
104
|
-
|
104
|
+
(i_found) ? delete_at(i_found) : nil
|
105
105
|
end
|
106
106
|
end
|
107
107
|
|
@@ -172,18 +172,18 @@ module Pwrake
|
|
172
172
|
end
|
173
173
|
|
174
174
|
def pop_last_rank(r,host_info)
|
175
|
-
|
175
|
+
i_found = nil
|
176
176
|
(size-1).downto(0) do |i|
|
177
177
|
tw = at(i)
|
178
178
|
if tw.rank == r && tw.acceptable_for(host_info)
|
179
179
|
if tw.untried_host?(host_info)
|
180
180
|
return delete_at(i)
|
181
181
|
else
|
182
|
-
|
182
|
+
i_found ||= i
|
183
183
|
end
|
184
184
|
end
|
185
185
|
end
|
186
|
-
|
186
|
+
(i_found) ? delete_at(i_found) : nil
|
187
187
|
end
|
188
188
|
|
189
189
|
def hrf_delete(t)
|
@@ -88,23 +88,23 @@ module Pwrake
|
|
88
88
|
@hostinfo_by_id.each_value do |host_info|
|
89
89
|
#Log.debug "TaskQueue#deq_turn host_info=#{host_info.name}"
|
90
90
|
if (n = host_info.idle_cores) && n > 0
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
91
|
+
if turn_empty?(turn)
|
92
|
+
return queued
|
93
|
+
elsif tw = deq_impl(host_info,turn)
|
94
|
+
n_task_cores = tw.n_used_cores(host_info)
|
95
|
+
Log.debug "deq: #{tw.name} n_task_cores=#{n_task_cores}"
|
96
|
+
if host_info.idle_cores < n_task_cores
|
97
|
+
m = "task.n_used_cores=#{n_task_cores} must be "+
|
98
|
+
"<= host_info.idle_cores=#{host_info.idle_cores}"
|
99
|
+
Log.fatal m
|
100
|
+
raise RuntimeError,m
|
101
|
+
else
|
102
|
+
yield(tw,host_info,n_task_cores)
|
103
|
+
count += 1
|
104
|
+
queued += 1
|
105
|
+
end
|
105
106
|
end
|
106
107
|
end
|
107
|
-
end
|
108
108
|
end
|
109
109
|
break if count == 0
|
110
110
|
end
|
@@ -3,22 +3,28 @@ module Pwrake
|
|
3
3
|
module Parallelism
|
4
4
|
module_function
|
5
5
|
|
6
|
+
def push_time_event(a, row, start_time)
|
7
|
+
command = row['command']
|
8
|
+
if command == 'pwrake_profile_start'
|
9
|
+
start_time[0] = Time.parse(row['start_time'])
|
10
|
+
elsif command == 'pwrake_profile_end'
|
11
|
+
t = Time.parse(row['start_time']) - start_time[0]
|
12
|
+
a << [t,0]
|
13
|
+
elsif start_time[0]
|
14
|
+
n = begin Integer(row['ncore']) rescue 1 end
|
15
|
+
t = Time.parse(row['start_time']) - start_time[0]
|
16
|
+
a << [t,+n]
|
17
|
+
t = Time.parse(row['end_time']) - start_time[0]
|
18
|
+
a << [t,-n]
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
6
22
|
def count_start_end_from_csv(file)
|
7
23
|
a = []
|
8
|
-
start_time =
|
24
|
+
start_time = []
|
9
25
|
|
10
26
|
CSV.foreach(file,:headers=>true) do |row|
|
11
|
-
|
12
|
-
start_time = Time.parse(row['start_time'])
|
13
|
-
elsif row['command'] == 'pwrake_profile_end'
|
14
|
-
t = Time.parse(row['start_time']) - start_time
|
15
|
-
a << [t,0]
|
16
|
-
elsif start_time
|
17
|
-
t = Time.parse(row['start_time']) - start_time
|
18
|
-
a << [t,+1]
|
19
|
-
t = Time.parse(row['end_time']) - start_time
|
20
|
-
a << [t,-1]
|
21
|
-
end
|
27
|
+
push_time_event(a, row, start_time)
|
22
28
|
end
|
23
29
|
|
24
30
|
a.sort{|x,y| x[0]<=>y[0]}
|
@@ -26,20 +32,10 @@ module Pwrake
|
|
26
32
|
|
27
33
|
def count_start_end_from_csv_table(csvtable)
|
28
34
|
a = []
|
29
|
-
start_time =
|
35
|
+
start_time = []
|
30
36
|
|
31
37
|
csvtable.each do |row|
|
32
|
-
|
33
|
-
start_time = Time.parse(row['start_time'])
|
34
|
-
elsif row['command'] == 'pwrake_profile_end'
|
35
|
-
t = Time.parse(row['start_time']) - start_time
|
36
|
-
a << [t,0]
|
37
|
-
elsif start_time
|
38
|
-
t = Time.parse(row['start_time']) - start_time
|
39
|
-
a << [t,+1]
|
40
|
-
t = Time.parse(row['end_time']) - start_time
|
41
|
-
a << [t,-1]
|
42
|
-
end
|
38
|
+
push_time_event(a, row, start_time)
|
43
39
|
end
|
44
40
|
|
45
41
|
a.sort{|x,y| x[0]<=>y[0]}
|
@@ -48,16 +44,15 @@ module Pwrake
|
|
48
44
|
def exec_density(a)
|
49
45
|
reso = 0.1
|
50
46
|
delta = 1/reso
|
51
|
-
t_end =
|
52
|
-
n = (t_end/reso).
|
53
|
-
i = 0
|
54
|
-
t_next = reso
|
47
|
+
t_end = a.last[0]
|
48
|
+
n = (t_end/reso).round + 1
|
55
49
|
d = (n+1).times.map{|i| [reso*i,0]}
|
50
|
+
i = 0
|
56
51
|
a.each do |x|
|
57
52
|
while d[i+1][0] <= x[0]
|
58
53
|
i += 1
|
59
54
|
end
|
60
|
-
if x[1]
|
55
|
+
if x[1] > 0
|
61
56
|
d[i][1] += delta
|
62
57
|
end
|
63
58
|
end
|
@@ -68,21 +63,21 @@ module Pwrake
|
|
68
63
|
a = count_start_end_from_csv(file)
|
69
64
|
return if a.size < 4
|
70
65
|
|
71
|
-
density = exec_density(a)
|
66
|
+
#density = exec_density(a)
|
72
67
|
|
73
68
|
base = file.sub(/\.csv$/,"")
|
74
69
|
fpara = base+"_para.dat"
|
75
70
|
|
76
71
|
n = a.size
|
77
|
-
i = 0
|
78
72
|
y = 0
|
79
73
|
y_max = 0
|
80
74
|
|
81
75
|
File.open(fpara,"w") do |f|
|
76
|
+
i = 0
|
77
|
+
t = 0
|
78
|
+
y_pre = 0
|
82
79
|
begin
|
83
|
-
|
84
|
-
y_pre = 0
|
85
|
-
n.times do |i|
|
80
|
+
while i < n
|
86
81
|
if a[i][0]-t > 0.001
|
87
82
|
f.printf "%.3f %d\n", t, y_pre
|
88
83
|
t = a[i][0]
|
@@ -91,6 +86,7 @@ module Pwrake
|
|
91
86
|
y += a[i][1]
|
92
87
|
y_pre = y
|
93
88
|
y_max = y if y > y_max
|
89
|
+
i += 1
|
94
90
|
end
|
95
91
|
rescue
|
96
92
|
p a[i]
|
@@ -136,7 +132,7 @@ plot '#{fpara}' w l axis x1y1 title 'parallelism'
|
|
136
132
|
begin
|
137
133
|
t = 0
|
138
134
|
y_pre = 0
|
139
|
-
|
135
|
+
while i < n
|
140
136
|
if a[i][0]-t > 0.001
|
141
137
|
para.push "%.3f %d" % [t, y_pre]
|
142
138
|
t = a[i][0]
|
@@ -145,6 +141,7 @@ plot '#{fpara}' w l axis x1y1 title 'parallelism'
|
|
145
141
|
y += a[i][1]
|
146
142
|
y_pre = y
|
147
143
|
y_max = y if y > y_max
|
144
|
+
i += 1
|
148
145
|
end
|
149
146
|
rescue
|
150
147
|
p a[i]
|
@@ -185,72 +182,65 @@ plot '-' w l axis x1y1 title 'parallelism', '-' w l axis x1y2 title 'exec/sec'
|
|
185
182
|
fimg
|
186
183
|
end
|
187
184
|
|
185
|
+
|
186
|
+
def push_time_by_key(h, row, key, start_time)
|
187
|
+
command = row['command']
|
188
|
+
if command == 'pwrake_profile_start'
|
189
|
+
start_time[0] = Time.parse(row['start_time'])
|
190
|
+
elsif command == 'pwrake_profile_end'
|
191
|
+
t = Time.parse(row['start_time']) - start_time[0]
|
192
|
+
h.each_value do |v|
|
193
|
+
v << [t,0]
|
194
|
+
end
|
195
|
+
elsif start_time[0]
|
196
|
+
a = (h[key] ||= [])
|
197
|
+
n = begin Integer(row['ncore']) rescue 1 end
|
198
|
+
t = Time.parse(row['start_time']) - start_time[0]
|
199
|
+
a << [t,+n]
|
200
|
+
t = Time.parse(row['end_time']) - start_time[0]
|
201
|
+
a << [t,-n]
|
202
|
+
end
|
203
|
+
end
|
204
|
+
|
188
205
|
def read_time_by_host_from_csv(csvtable)
|
189
206
|
a = {}
|
190
|
-
start_time =
|
207
|
+
start_time = []
|
191
208
|
|
192
209
|
csvtable.each do |row|
|
193
|
-
|
194
|
-
if row['command'] == 'pwrake_profile_start'
|
195
|
-
start_time = Time.parse(row['start_time'])
|
196
|
-
elsif row['command'] == 'pwrake_profile_end'
|
197
|
-
t = Time.parse(row['start_time']) - start_time
|
198
|
-
a.each do |h,v|
|
199
|
-
v << [t,0]
|
200
|
-
end
|
201
|
-
elsif start_time
|
202
|
-
a[host] ||= []
|
203
|
-
t = Time.parse(row['start_time']) - start_time
|
204
|
-
a[host] << [t,+1]
|
205
|
-
t = Time.parse(row['end_time']) - start_time
|
206
|
-
a[host] << [t,-1]
|
207
|
-
end
|
210
|
+
push_time_by_key(a, row, row['host'], start_time)
|
208
211
|
end
|
209
212
|
a
|
210
213
|
end
|
211
214
|
|
212
215
|
|
213
|
-
def get_command_key(s, pattern)
|
216
|
+
def get_command_key(s, pattern=[])
|
214
217
|
pattern.each do |cmd,regex|
|
215
218
|
if regex =~ s
|
216
219
|
return cmd
|
217
220
|
end
|
218
221
|
end
|
219
|
-
|
220
|
-
|
221
|
-
|
222
|
-
|
223
|
-
|
224
|
-
if
|
225
|
-
|
226
|
-
|
227
|
-
|
222
|
+
case s
|
223
|
+
when /^\s*\((.*)$/
|
224
|
+
get_command_key($1)
|
225
|
+
when /^\s*([\w.,~^\/=+-]+)(.*)$/
|
226
|
+
cmd, rest = $1, $2
|
227
|
+
if cmd == "cd" && /[^;]*;(.*)$/ =~ rest
|
228
|
+
return get_command_key($1)
|
229
|
+
else
|
230
|
+
cmd
|
228
231
|
end
|
232
|
+
else
|
233
|
+
s[0..15]
|
229
234
|
end
|
230
|
-
nil
|
231
235
|
end
|
232
236
|
|
233
237
|
def count_start_end_by_pattern(csvtable, pattern)
|
234
238
|
h = Hash.new
|
235
|
-
start_time =
|
239
|
+
start_time = []
|
236
240
|
|
237
241
|
csvtable.each do |row|
|
238
|
-
|
239
|
-
|
240
|
-
start_time = Time.parse(row['start_time'])
|
241
|
-
elsif command == 'pwrake_profile_end'
|
242
|
-
t = Time.parse(row['start_time']) - start_time
|
243
|
-
h.values.each do |a|
|
244
|
-
a << [t,0]
|
245
|
-
end
|
246
|
-
elsif start_time
|
247
|
-
cmd = get_command_key(command, pattern)
|
248
|
-
h[cmd] ||= []
|
249
|
-
t = Time.parse(row['start_time']) - start_time
|
250
|
-
h[cmd] << [t,+1]
|
251
|
-
t = Time.parse(row['end_time']) - start_time
|
252
|
-
h[cmd] << [t,-1]
|
253
|
-
end
|
242
|
+
cmd = get_command_key(row['command'], pattern)
|
243
|
+
push_time_by_key(h, row, cmd, start_time)
|
254
244
|
end
|
255
245
|
|
256
246
|
h.each do |k,a|
|
@@ -272,7 +262,7 @@ plot '-' w l axis x1y1 title 'parallelism', '-' w l axis x1y2 title 'exec/sec'
|
|
272
262
|
begin
|
273
263
|
t = 0
|
274
264
|
y_pre = 0
|
275
|
-
|
265
|
+
while i < n
|
276
266
|
if a[i][0]-t > 0.001
|
277
267
|
dat.push "%.3f %d" % [t, y_pre]
|
278
268
|
t = a[i][0]
|
@@ -281,6 +271,7 @@ plot '-' w l axis x1y1 title 'parallelism', '-' w l axis x1y2 title 'exec/sec'
|
|
281
271
|
y += a[i][1]
|
282
272
|
y_pre = y
|
283
273
|
y_max = y if y > y_max
|
274
|
+
i += 1
|
284
275
|
end
|
285
276
|
rescue
|
286
277
|
p a[i]
|
@@ -303,7 +294,7 @@ set xlabel 'time (sec)'
|
|
303
294
|
set ylabel 'parallelism'
|
304
295
|
"
|
305
296
|
f.print "plot "
|
306
|
-
f.puts para.map{|cmd,re| "'-' w l title
|
297
|
+
f.puts para.map{|cmd,re| "'-' w l title #{cmd.inspect}"}.join(",")
|
307
298
|
para.each do |cmd,dat|
|
308
299
|
dat.each do |x|
|
309
300
|
f.puts x
|
@@ -321,9 +312,8 @@ set ylabel 'parallelism'
|
|
321
312
|
resolution = Rational(1,10)
|
322
313
|
|
323
314
|
a = a.sort{|x,y| x[0]<=>y[0]}
|
324
|
-
t_end = (a.last)[0]
|
325
|
-
|
326
|
-
ngrid = (t_end/resolution).floor
|
315
|
+
#t_end = (a.last)[0]
|
316
|
+
#ngrid = (t_end/resolution).floor
|
327
317
|
grid = [[0,0]]
|
328
318
|
|
329
319
|
j = 0
|
data/lib/pwrake/report/report.rb
CHANGED
@@ -135,18 +135,42 @@ EOL
|
|
135
135
|
end
|
136
136
|
|
137
137
|
def get_command(s)
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
|
138
|
+
case s
|
139
|
+
when /^\s*\((.*)$/
|
140
|
+
get_command($1)
|
141
|
+
when /^\s*([\w.,~^\/=+-]+)(.*)$/
|
142
|
+
cmd, rest = $1, $2
|
143
|
+
case cmd
|
144
|
+
when "cd"
|
145
|
+
if /[^;]*;(.*)$/ =~ rest
|
146
|
+
return get_command($1)
|
147
|
+
end
|
148
|
+
when /^ruby[\d.]*$/
|
149
|
+
case rest
|
150
|
+
when /([\w.,~^\/=+-]+\.rb)\b/
|
151
|
+
return "#{cmd} #{$1}"
|
152
|
+
when /\s+-e\s+("[^"]*"|'[^']*'|\S+)/
|
153
|
+
return "#{cmd} -e #{$1}"
|
154
|
+
end
|
155
|
+
when /^python[\d.]*$/
|
156
|
+
case rest
|
157
|
+
when /([\w.,~^\/=+-]+\.py)\b/
|
158
|
+
return "#{cmd} #{$1}"
|
159
|
+
when /\s+-c\s+("[^"]*"|'[^']*'|\S+)/
|
160
|
+
return "python -c #{$1}"
|
161
|
+
end
|
162
|
+
when /^perl[\d.]*$/
|
163
|
+
case rest
|
164
|
+
when /([\w.,~^\/=+-]+\.pl)\b/
|
165
|
+
return "#{cmd} #{$1}"
|
166
|
+
when /\s+-e\s+("[^"]*"|'[^']*'|\S+)/
|
167
|
+
return "#{cmd} -e #{$1}"
|
168
|
+
end
|
147
169
|
end
|
170
|
+
cmd
|
171
|
+
else
|
172
|
+
s[0..15]
|
148
173
|
end
|
149
|
-
nil
|
150
174
|
end
|
151
175
|
|
152
176
|
def make_cmd_stat
|
@@ -299,9 +323,9 @@ set logscale x
|
|
299
323
|
set title 'histogram of elapsed time'"
|
300
324
|
a = []
|
301
325
|
|
302
|
-
command_list.each_with_index do |
|
326
|
+
command_list.each_with_index do |cmd,i|
|
303
327
|
a << "'-' w histeps ls #{i+1} title ''"
|
304
|
-
a << "'-' w lines ls #{i+1} title
|
328
|
+
a << "'-' w lines ls #{i+1} title #{cmd.inspect}"
|
305
329
|
end
|
306
330
|
f.puts "plot "+ a.join(',')
|
307
331
|
|
@@ -5,22 +5,25 @@ module Pwrake
|
|
5
5
|
|
6
6
|
module TaskAlgorithm
|
7
7
|
|
8
|
-
attr_reader :wrapper
|
9
8
|
attr_reader :subsequents
|
10
9
|
attr_reader :arguments
|
11
10
|
attr_reader :property
|
12
11
|
attr_reader :unfinished_prereq
|
13
12
|
|
13
|
+
def wrapper
|
14
|
+
if @wrapper.nil?
|
15
|
+
raise "TaskWrapper is not defined for #{self.class}[#{name}]"
|
16
|
+
end
|
17
|
+
@wrapper
|
18
|
+
end
|
19
|
+
|
14
20
|
def pw_search_tasks(args)
|
15
|
-
Log.debug "#{self.class}#pw_search_tasks start, args=#{args.inspect}"
|
21
|
+
Log.debug "#{self.class}#pw_search_tasks start, task=#{name} args=#{args.inspect}"
|
16
22
|
tm = Time.now
|
17
23
|
task_args = TaskArguments.new(arg_names, args)
|
18
|
-
#
|
19
|
-
|
20
|
-
#
|
21
|
-
search_with_call_chain(nil, task_args, InvocationChain::EMPTY)
|
22
|
-
#end
|
23
|
-
#timer.finish
|
24
|
+
# not synchronize owing to fiber
|
25
|
+
search_with_call_chain(nil, task_args, InvocationChain::EMPTY)
|
26
|
+
#
|
24
27
|
Log.debug "#{self.class}#pw_search_tasks end #{Time.now-tm}"
|
25
28
|
end
|
26
29
|
|
@@ -30,7 +33,7 @@ module Pwrake
|
|
30
33
|
new_chain = InvocationChain.append(self, invocation_chain)
|
31
34
|
@lock.synchronize do
|
32
35
|
if application.options.trace
|
33
|
-
#Log.
|
36
|
+
#Log.debug "** Search #{name} #{format_search_flags}"
|
34
37
|
application.trace "** Search #{name} #{format_search_flags}"
|
35
38
|
end
|
36
39
|
|
@@ -48,7 +51,7 @@ module Pwrake
|
|
48
51
|
search_prerequisites(task_args, new_chain)
|
49
52
|
end
|
50
53
|
#check_and_enq
|
51
|
-
if @unfinished_prereq.empty?
|
54
|
+
if !@already_finished && @unfinished_prereq.empty?
|
52
55
|
application.task_queue.enq(@wrapper)
|
53
56
|
end
|
54
57
|
end
|
@@ -82,23 +85,18 @@ module Pwrake
|
|
82
85
|
private :format_search_flags
|
83
86
|
|
84
87
|
def pw_enq_subsequents
|
85
|
-
#
|
86
|
-
#
|
87
|
-
|
88
|
-
|
89
|
-
#u = t.unfinished_prereq.keys
|
90
|
-
#Log.debug "enq_subseq: self=#{self.name} subseq=#{t.name} @unfin_preq=#{u.inspect}"
|
91
|
-
if t && t.check_prereq_finished(self.name)
|
92
|
-
application.task_queue.enq(t.wrapper)
|
93
|
-
end
|
88
|
+
# not synchronize owing to fiber
|
89
|
+
@subsequents.each do |t| # <<--- competition !!!
|
90
|
+
if t && t.check_prereq_finished(self.name)
|
91
|
+
application.task_queue.enq(t.wrapper)
|
94
92
|
end
|
95
|
-
|
93
|
+
end
|
96
94
|
@already_finished = true # <<--- competition !!!
|
97
95
|
end
|
98
96
|
|
99
97
|
def check_prereq_finished(preq_name=nil)
|
100
98
|
@unfinished_prereq.delete(preq_name)
|
101
|
-
@unfinished_prereq.empty?
|
99
|
+
!@already_finished && @unfinished_prereq.empty?
|
102
100
|
end
|
103
101
|
|
104
102
|
def pw_set_property(property)
|
@@ -106,5 +104,18 @@ module Pwrake
|
|
106
104
|
self
|
107
105
|
end
|
108
106
|
|
107
|
+
end # TaskAlgorithm
|
108
|
+
|
109
|
+
|
110
|
+
module TaskInvoke
|
111
|
+
|
112
|
+
def invoke(*args)
|
113
|
+
Rake.application.invoke(self,*args)
|
114
|
+
end
|
115
|
+
|
116
|
+
def reenable
|
117
|
+
@already_invoked = false
|
118
|
+
@already_searched = false
|
119
|
+
end
|
109
120
|
end
|
110
121
|
end
|
@@ -53,8 +53,9 @@ module Pwrake
|
|
53
53
|
fn = File.join(dir,option['TASK_CSV_FILE'])
|
54
54
|
@@task_logger = CSV.open(fn,'w')
|
55
55
|
@@task_logger.puts %w[
|
56
|
-
task_id task_name start_time end_time elap_time preq
|
57
|
-
exec_host shell_id has_action executed
|
56
|
+
task_id task_name start_time end_time elap_time preq
|
57
|
+
preq_host preq_loc exec_host shell_id has_action executed ncore
|
58
|
+
file_size file_mtime file_host write_loc
|
58
59
|
]
|
59
60
|
end
|
60
61
|
end
|
@@ -64,9 +65,6 @@ module Pwrake
|
|
64
65
|
end
|
65
66
|
|
66
67
|
def preprocess
|
67
|
-
if @shell = Pwrake::Shell.current
|
68
|
-
@shell.current_task = self
|
69
|
-
end
|
70
68
|
@time_start = Time.now
|
71
69
|
end
|
72
70
|
|
@@ -90,7 +88,6 @@ module Pwrake
|
|
90
88
|
end
|
91
89
|
#Log.debug "postprocess time=#{Time.now-tm_taskend}"
|
92
90
|
log_task
|
93
|
-
@shell.current_task = nil if @shell
|
94
91
|
end
|
95
92
|
|
96
93
|
def retry_or_subsequent
|
@@ -142,18 +139,21 @@ module Pwrake
|
|
142
139
|
write_loc = file_locality(@location)
|
143
140
|
#
|
144
141
|
if @file_stat
|
145
|
-
fstat = [@file_stat.size, @file_stat.mtime,
|
142
|
+
fstat = [ @file_stat.size, @file_stat.mtime,
|
143
|
+
self.location.join('|'), write_loc ]
|
146
144
|
else
|
147
145
|
fstat = [nil]*4
|
148
146
|
end
|
149
147
|
#
|
150
|
-
# task_id task_name start_time end_time elap_time preq preq_host
|
151
|
-
# exec_host shell_id has_action executed
|
148
|
+
# task_id task_name start_time end_time elap_time preq preq_host
|
149
|
+
# preq_loc exec_host shell_id has_action executed ncore
|
150
|
+
# file_size file_mtime file_host write_loc
|
152
151
|
#
|
153
152
|
row = [ @task_id, name, @time_start, @time_end, elap,
|
154
153
|
prerequisites, sug_host, preq_loc, @exec_host, @shell_id,
|
155
154
|
(actions.empty?) ? 0 : 1,
|
156
155
|
(@executed) ? 1 : 0,
|
156
|
+
@n_used_cores,
|
157
157
|
] + fstat
|
158
158
|
row.map!{|x|
|
159
159
|
if x.kind_of?(Time)
|
data/lib/pwrake/version.rb
CHANGED
@@ -2,6 +2,43 @@ module Pwrake
|
|
2
2
|
|
3
3
|
class Executor
|
4
4
|
|
5
|
+
ENV = {
|
6
|
+
"OMPI_APP_CTX_NUM_PROCS" => nil,
|
7
|
+
"OMPI_COMM_WORLD_LOCAL_RANK" => nil,
|
8
|
+
"OMPI_COMM_WORLD_LOCAL_SIZE" => nil,
|
9
|
+
"OMPI_COMM_WORLD_NODE_RANK" => nil,
|
10
|
+
"OMPI_COMM_WORLD_RANK" => nil,
|
11
|
+
"OMPI_COMM_WORLD_SIZE" => nil,
|
12
|
+
"OMPI_FILE_LOCATION" => nil,
|
13
|
+
"OMPI_FIRST_RANKS" => nil,
|
14
|
+
"OMPI_MCA_db" => nil,
|
15
|
+
"OMPI_MCA_ess" => nil,
|
16
|
+
"OMPI_MCA_ess_base_jobid" => nil,
|
17
|
+
"OMPI_MCA_ess_base_vpid" => nil,
|
18
|
+
"OMPI_MCA_grpcomm" => nil,
|
19
|
+
"OMPI_MCA_initial_wdir" => nil,
|
20
|
+
"OMPI_MCA_mpi_yield_when_idle" => nil,
|
21
|
+
"OMPI_MCA_orte_app_num" => nil,
|
22
|
+
"OMPI_MCA_orte_bound_at_launch" => nil,
|
23
|
+
"OMPI_MCA_orte_ess_jobid" => nil,
|
24
|
+
"OMPI_MCA_orte_ess_node_rank" => nil,
|
25
|
+
"OMPI_MCA_orte_ess_num_procs" => nil,
|
26
|
+
"OMPI_MCA_orte_ess_vpid" => nil,
|
27
|
+
"OMPI_MCA_orte_hnp_uri" => nil,
|
28
|
+
"OMPI_MCA_orte_local_daemon_uri" => nil,
|
29
|
+
"OMPI_MCA_orte_num_nodes" => nil,
|
30
|
+
"OMPI_MCA_orte_num_restarts" => nil,
|
31
|
+
"OMPI_MCA_orte_tmpdir_base" => nil,
|
32
|
+
"OMPI_MCA_plm" => nil,
|
33
|
+
"OMPI_MCA_pubsub" => nil,
|
34
|
+
"OMPI_MCA_shmem_RUNTIME_QUERY_hint" => nil,
|
35
|
+
"OMPI_NUM_APP_CTX" => nil,
|
36
|
+
"OMPI_UNIVERSE_SIZE" => nil,
|
37
|
+
"PMI_RANK" => nil,
|
38
|
+
"PMI_FD" => nil,
|
39
|
+
"PMI_SIZE" => nil,
|
40
|
+
}
|
41
|
+
|
5
42
|
def initialize(selector,dir_class,id)
|
6
43
|
@selector = selector
|
7
44
|
@id = id
|
@@ -74,7 +111,7 @@ module Pwrake
|
|
74
111
|
@sh_out, @spawn_out = IO.pipe
|
75
112
|
@sh_err, @spawn_err = IO.pipe
|
76
113
|
|
77
|
-
@pid = Kernel.spawn(command,
|
114
|
+
@pid = Kernel.spawn(ENV, command,
|
78
115
|
:in=>@spawn_in,
|
79
116
|
:out=>@spawn_out,
|
80
117
|
:err=>@spawn_err,
|
@@ -86,15 +86,18 @@ module Pwrake
|
|
86
86
|
end
|
87
87
|
|
88
88
|
def run
|
89
|
+
run_setup
|
90
|
+
run_command
|
91
|
+
ensure
|
92
|
+
close_all
|
93
|
+
end
|
94
|
+
|
95
|
+
def run_setup
|
89
96
|
setup_option
|
90
97
|
Fiber.new{setup_loop}.resume
|
91
98
|
@selector.run
|
92
|
-
Fiber.new{command_callback}.resume
|
93
|
-
@selector.run
|
94
99
|
rescue => exc
|
95
100
|
@log.error(([exc.to_s]+exc.backtrace).join("\n"))
|
96
|
-
ensure
|
97
|
-
close_all
|
98
101
|
end
|
99
102
|
|
100
103
|
def setup_option
|
@@ -123,6 +126,14 @@ module Pwrake
|
|
123
126
|
end
|
124
127
|
end
|
125
128
|
|
129
|
+
def run_command
|
130
|
+
Fiber.new{command_callback}.resume
|
131
|
+
@selector.run
|
132
|
+
rescue => exc
|
133
|
+
@log.error(([exc.to_s]+exc.backtrace).join("\n"))
|
134
|
+
kill_all("TERM")
|
135
|
+
end
|
136
|
+
|
126
137
|
def command_callback
|
127
138
|
while line = get_line(@rd)
|
128
139
|
case line
|
@@ -152,8 +163,7 @@ module Pwrake
|
|
152
163
|
when /^kill:(.*)$/o
|
153
164
|
sig = $1
|
154
165
|
sig = sig.to_i if /^\d+$/o =~ sig
|
155
|
-
|
156
|
-
@ex_list.each{|id,ex| ex.kill(sig)}
|
166
|
+
kill_all(sig)
|
157
167
|
return false
|
158
168
|
#
|
159
169
|
when /^p$/o
|
@@ -167,6 +177,11 @@ module Pwrake
|
|
167
177
|
end
|
168
178
|
end
|
169
179
|
|
180
|
+
def kill_all(sig)
|
181
|
+
@log.warn "killing worker, signal=#{sig}"
|
182
|
+
@ex_list.each{|id,ex| ex.kill(sig)}
|
183
|
+
end
|
184
|
+
|
170
185
|
def close_all
|
171
186
|
@log.info "close_all"
|
172
187
|
@heartbeat_thread.kill if @heartbeat_thread
|
data/lib/pwrake/worker/writer.rb
CHANGED
@@ -8,9 +8,8 @@ module Pwrake
|
|
8
8
|
def initialize
|
9
9
|
@out = $stderr
|
10
10
|
@mutex = Mutex.new
|
11
|
-
@mutex_hb = Mutex.new
|
12
11
|
@cond_hb = true
|
13
|
-
@heartbeat =
|
12
|
+
@heartbeat = 120
|
14
13
|
@thread = Thread.new{ heartbeat_loop }
|
15
14
|
end
|
16
15
|
|
@@ -22,14 +21,13 @@ module Pwrake
|
|
22
21
|
end
|
23
22
|
|
24
23
|
def heartbeat_loop
|
24
|
+
sleep
|
25
25
|
loop do
|
26
|
-
|
27
|
-
@
|
28
|
-
|
29
|
-
_puts "heartbeat"
|
30
|
-
end
|
31
|
-
@cond_hb = true
|
26
|
+
sleep(@heartbeat)
|
27
|
+
if @cond_hb
|
28
|
+
_puts "heartbeat"
|
32
29
|
end
|
30
|
+
@cond_hb = true
|
33
31
|
end
|
34
32
|
end
|
35
33
|
|
@@ -38,25 +36,11 @@ module Pwrake
|
|
38
36
|
end
|
39
37
|
|
40
38
|
def puts(s)
|
41
|
-
@
|
42
|
-
|
43
|
-
@thread.run
|
44
|
-
end
|
39
|
+
@cond_hb = false
|
40
|
+
@thread.run
|
45
41
|
_puts(s)
|
46
42
|
end
|
47
43
|
|
48
|
-
def _puts(s)
|
49
|
-
begin
|
50
|
-
@mutex.synchronize do
|
51
|
-
@out.print s+"\n"
|
52
|
-
end
|
53
|
-
@out.flush
|
54
|
-
rescue Errno::EPIPE => e
|
55
|
-
@log.info "<#{e.inspect}" if @log
|
56
|
-
end
|
57
|
-
@log.info "<#{s}" if @log
|
58
|
-
end
|
59
|
-
|
60
44
|
def flush
|
61
45
|
begin
|
62
46
|
@out.flush
|
@@ -68,5 +52,17 @@ module Pwrake
|
|
68
52
|
puts(s) if $DEBUG
|
69
53
|
end
|
70
54
|
|
55
|
+
private
|
56
|
+
def _puts(s)
|
57
|
+
begin
|
58
|
+
@mutex.synchronize do
|
59
|
+
@out.print s+"\n"
|
60
|
+
end
|
61
|
+
@out.flush
|
62
|
+
rescue Errno::EPIPE => e
|
63
|
+
@log.info "<#{e.inspect}" if @log
|
64
|
+
end
|
65
|
+
@log.info "<#{s}" if @log
|
66
|
+
end
|
71
67
|
end
|
72
68
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pwrake
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.2.
|
4
|
+
version: 2.2.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Masahiro TANAKA
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-
|
11
|
+
date: 2017-04-30 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: parallel
|
@@ -136,7 +136,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
136
136
|
version: '0'
|
137
137
|
requirements: []
|
138
138
|
rubyforge_project:
|
139
|
-
rubygems_version: 2.6.
|
139
|
+
rubygems_version: 2.6.11
|
140
140
|
signing_key:
|
141
141
|
specification_version: 4
|
142
142
|
summary: Parallel Workflow engine based on Rake
|