ruby-cute 0.13 → 0.24
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitlab-ci.yml +20 -1
- data/README.md +12 -1
- data/bin/cute +2 -1
- data/bin/grd +701 -0
- data/debian/.gitattributes +3 -0
- data/debian/changelog +96 -0
- data/debian/control +22 -5
- data/debian/ruby-cute.docs +1 -1
- data/debian/rules +3 -11
- data/debian/watch +2 -2
- data/examples/distem-bootstrap +16 -22
- data/examples/g5k-tutorial.md +25 -18
- data/examples/g5k_exp_virt.rb +1 -1
- data/lib/cute/bash.rb +7 -7
- data/lib/cute/configparser.rb +14 -12
- data/lib/cute/execute.rb +6 -4
- data/lib/cute/extensions.rb +3 -4
- data/lib/cute/g5k_api.rb +56 -38
- data/lib/cute/net-ssh-exec3.rb +10 -7
- data/lib/cute/net-ssh.rb +2 -2
- data/lib/cute/net.rb +5 -7
- data/lib/cute/synchronization.rb +1 -3
- data/lib/cute/taktuk.rb +4 -5
- data/lib/cute/version.rb +1 -1
- data/ruby-cute.gemspec +6 -3
- data/spec/g5k_api_check_spec.rb +1 -1
- data/spec/g5k_api_spec.rb +2 -12
- data/spec/spec_helper.rb +1 -0
- data/test/test_execute.rb +0 -0
- metadata +54 -11
- data/debian/compat +0 -1
data/debian/changelog
CHANGED
@@ -1,3 +1,99 @@
|
|
1
|
+
ruby-cute (0.24) unstable; urgency=low
|
2
|
+
|
3
|
+
* 05ab1f4 --armor should imply deploy
|
4
|
+
|
5
|
+
-- Lucas Nussbaum <lucas.nussbaum@inria.fr> Fri, 08 Dec 2023 13:34:40 +0100
|
6
|
+
|
7
|
+
ruby-cute (0.23) unstable; urgency=low
|
8
|
+
|
9
|
+
* d56f254 Document some test cases
|
10
|
+
* a65b612 Add --armor
|
11
|
+
* e6a311c [grd] add VLAN support
|
12
|
+
* 0af5b85 [CI] add 'allow_failure: true' for manual jobs
|
13
|
+
|
14
|
+
-- Lucas Nussbaum <lucas.nussbaum@inria.fr> Thu, 07 Dec 2023 15:14:43 +0100
|
15
|
+
|
16
|
+
ruby-cute (0.22) unstable; urgency=low
|
17
|
+
|
18
|
+
* 9570af74 allow to set the timeout for Rest request
|
19
|
+
|
20
|
+
-- Alexandre MERLIN <alexandre.merlin@inria.fr> Thu, 29 Sep 2022 08:54:15 +0200
|
21
|
+
|
22
|
+
ruby-cute (0.21) unstable; urgency=low
|
23
|
+
|
24
|
+
* 402efe5 Support specifying OAR project
|
25
|
+
|
26
|
+
-- Lucas Nussbaum <lucas.nussbaum@loria.fr> Thu, 30 Jun 2022 10:40:50 +0200
|
27
|
+
|
28
|
+
ruby-cute (0.20) unstable; urgency=low
|
29
|
+
|
30
|
+
* ffac6af add --terminate-after-script
|
31
|
+
* 9363689 Do not raise exception when script fails
|
32
|
+
* e3bbe02 Improve help
|
33
|
+
* 75ff6db Add list of relevant Grid5000 bugs
|
34
|
+
* 6d3a407 Fix bug introduced by rubocop fixes
|
35
|
+
* 91773ae Merge branch 'feature/update-ci' into 'master'
|
36
|
+
* 6412d1c Run rspec tests in gitlab-ci
|
37
|
+
* 5507306 Fix Rubocop warnings.
|
38
|
+
* 9355eef [ci] add rubocop
|
39
|
+
* 3c6cc7e fix display of jobs that are not started
|
40
|
+
|
41
|
+
-- Lucas Nussbaum <lucas.nussbaum@loria.fr> Mon, 13 Jun 2022 21:04:25 +0200
|
42
|
+
|
43
|
+
ruby-cute (0.19) unstable; urgency=low
|
44
|
+
|
45
|
+
* fef0ea7 Better error handling when reservation fails
|
46
|
+
* 9ea4d3d Various improvements to grd list
|
47
|
+
* 95dbe26 Add debug mode
|
48
|
+
* 8805c55 Update packaging
|
49
|
+
* 10fcfd1 Add 'grd list'
|
50
|
+
* 5f1ae78 more rubocop warnings
|
51
|
+
* b8420ac resolve rubocop warnings
|
52
|
+
* 0d55e0e Improve documentation about grd
|
53
|
+
|
54
|
+
-- Lucas Nussbaum <lucas.nussbaum@inria.fr> Tue, 10 May 2022 09:56:47 +0200
|
55
|
+
|
56
|
+
ruby-cute (0.18) unstable; urgency=low
|
57
|
+
|
58
|
+
* f43a834 Minor bugfixes
|
59
|
+
* d1d538f Upgrade packaging to dh 13 and build on bullseye
|
60
|
+
|
61
|
+
-- Lucas Nussbaum <lucas.nussbaum@inria.fr> Wed, 13 Apr 2022 09:26:08 +0200
|
62
|
+
|
63
|
+
ruby-cute (0.17) unstable; urgency=low
|
64
|
+
|
65
|
+
* b81c224 Merge remote-tracking branch 'gh/master'
|
66
|
+
* 6dc473b Merge pull request #36 from deadlybore/master
|
67
|
+
* a3341ff Exit immediately if interrupted
|
68
|
+
* a44218f Improve 'bs -h'
|
69
|
+
* a7f2649 Improve output
|
70
|
+
* a91b0e7 Make walltime non-mandatory
|
71
|
+
* 234aa96 Add dep on ruby-net-scp
|
72
|
+
* 0ce884b update changelog
|
73
|
+
* 0a10f78 update of the documentation
|
74
|
+
|
75
|
+
-- Lucas Nussbaum <lucas.nussbaum@inria.fr> Wed, 13 Apr 2022 08:04:26 +0200
|
76
|
+
|
77
|
+
ruby-cute (0.16) unstable; urgency=low
|
78
|
+
|
79
|
+
* 1cedd61 Downgrade version requirement of net-ssh so that it is installable on Debian stretch
|
80
|
+
|
81
|
+
-- Lucas Nussbaum <lucas.nussbaum@inria.fr> Tue, 12 Apr 2022 22:01:51 +0200
|
82
|
+
|
83
|
+
ruby-cute (0.15) unstable; urgency=low
|
84
|
+
|
85
|
+
* 78de76f Add inital version of grd
|
86
|
+
* 2fc8bda exec3: add some timing information
|
87
|
+
* 1676cf9 Refresh packaging and bump version to 0.15
|
88
|
+
|
89
|
+
-- Lucas Nussbaum <lucas.nussbaum@inria.fr> Tue, 12 Apr 2022 21:56:20 +0200
|
90
|
+
|
91
|
+
ruby-cute (0.14) unstable; urgency=medium
|
92
|
+
|
93
|
+
* 57fcd01 Fix issue when catching errors from Grid'5000 API
|
94
|
+
|
95
|
+
-- Samir Noir <samir.noir@inria.fr> Wed, 15 Dec 2021 11:39:02 +0100
|
96
|
+
|
1
97
|
ruby-cute (0.13) unstable; urgency=medium
|
2
98
|
|
3
99
|
* New release.
|
data/debian/control
CHANGED
@@ -2,18 +2,35 @@ Source: ruby-cute
|
|
2
2
|
Section: ruby
|
3
3
|
Priority: optional
|
4
4
|
Maintainer: Lucas Nussbaum <lucas@debian.org>
|
5
|
-
Build-Depends: debhelper (
|
6
|
-
|
5
|
+
Build-Depends: debhelper-compat (= 13),
|
6
|
+
gem2deb,
|
7
|
+
rake,
|
8
|
+
ruby,
|
9
|
+
ruby-ipaddress (>= 0.8),
|
10
|
+
ruby-json (>= 1.8),
|
11
|
+
ruby-net-scp (>= 1.2),
|
12
|
+
ruby-net-ssh (>= 3.2),
|
13
|
+
ruby-net-ssh-multi (>= 1.2),
|
14
|
+
ruby-peach (>= 0.5.1),
|
15
|
+
ruby-rest-client (>= 1.6),
|
16
|
+
ruby-rspec,
|
17
|
+
ruby-simplecov,
|
18
|
+
ruby-webmock,
|
19
|
+
yard
|
20
|
+
Standards-Version: 4.5.0
|
7
21
|
Vcs-Git: git://github.com/ruby-cute/ruby-cute
|
8
22
|
Vcs-Browser: https://github.com/ruby-cute/ruby-cute
|
9
23
|
Homepage: http://ruby-cute.github.io/
|
10
|
-
Testsuite: autopkgtest
|
24
|
+
Testsuite: autopkgtest-pkg-ruby
|
11
25
|
XS-Ruby-Versions: all
|
26
|
+
Rules-Requires-Root: no
|
12
27
|
|
13
28
|
Package: ruby-cute
|
14
29
|
Architecture: all
|
15
30
|
XB-Ruby-Versions: ${ruby:Versions}
|
16
|
-
Depends: ${
|
17
|
-
|
31
|
+
Depends: ${misc:Depends},
|
32
|
+
${ruby:Depends},
|
33
|
+
${shlibs:Depends}
|
34
|
+
Recommends: ruby-terminal-table
|
18
35
|
Description: Critically Useful Tools for Experiments
|
19
36
|
Ruby library for controlling experiments
|
data/debian/ruby-cute.docs
CHANGED
data/debian/rules
CHANGED
@@ -1,15 +1,7 @@
|
|
1
1
|
#!/usr/bin/make -f
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
#export DH_RUBY_IGNORE_TESTS=all
|
6
|
-
#
|
7
|
-
# Uncomment to ignore some test failures (but the tests will run anyway).
|
8
|
-
# Valid values:
|
9
|
-
#export DH_RUBY_IGNORE_TESTS=ruby2.1 require-rubygems
|
10
|
-
#
|
11
|
-
# If you need to specify the .gemspec (eg there is more than one)
|
12
|
-
#export DH_RUBY_GEMSPEC=gem.gemspec
|
2
|
+
|
3
|
+
export GEM2DEB_TEST_RUNNER = --check-dependencies
|
4
|
+
export DH_RUBY = --gem-install
|
13
5
|
|
14
6
|
%:
|
15
7
|
dh $@ --buildsystem=ruby --with ruby
|
data/debian/watch
CHANGED
@@ -1,2 +1,2 @@
|
|
1
|
-
version=
|
2
|
-
|
1
|
+
version=4
|
2
|
+
https://gemwatch.debian.net/ruby-cute .*/ruby-cute-(.*).tar.gz
|
data/examples/distem-bootstrap
CHANGED
@@ -132,7 +132,7 @@ optparse = OptionParser.new do |opts|
|
|
132
132
|
opts.on( '-c', '--coordinator <coordinator_address>', 'Address of the coordinator (default: first node)' ) do |c|
|
133
133
|
options[:coordinator] = c || nil
|
134
134
|
end
|
135
|
-
opts.on( '-x', '--no-init-pnodes', 'Do not initialize all pnodes' ) do
|
135
|
+
opts.on( '-x', '--no-init-pnodes', 'Do not initialize all pnodes' ) do
|
136
136
|
options[:init_pnodes] = false
|
137
137
|
end
|
138
138
|
opts.on( '--max-vifaces <nb>', 'Set the maximum number of vifaces on a physical node (used only without --no-init-pnodes)' ) do |n|
|
@@ -174,7 +174,7 @@ optparse = OptionParser.new do |opts|
|
|
174
174
|
opts.on( '-B', '--branch <branch_name>', "Checkout a specific branch and rebuild a Debian package" ) do |n|
|
175
175
|
options[:branch] = n
|
176
176
|
end
|
177
|
-
opts.on( '-S', '--stealth-mode', 'Do not report usage statistics (Grid\'5000 only)' ) do
|
177
|
+
opts.on( '-S', '--stealth-mode', 'Do not report usage statistics (Grid\'5000 only)' ) do
|
178
178
|
options[:stats] = false
|
179
179
|
end
|
180
180
|
opts.on( '--btrfs-format <tmp_device>', 'Format the device with btrfs support to allow COW on Vnodes (experimental)' ) do |d|
|
@@ -184,10 +184,7 @@ optparse = OptionParser.new do |opts|
|
|
184
184
|
options[:ci] = path
|
185
185
|
end
|
186
186
|
opts.on( '-n', '--network-mode <mode>', 'Define the network mode (classical or vxlan)') do |mode|
|
187
|
-
|
188
|
-
when 'classical'
|
189
|
-
when 'vxlan'
|
190
|
-
else
|
187
|
+
if mode != 'classical' and mode != 'vxlan'
|
191
188
|
puts 'Invalid network mode'
|
192
189
|
exit 1
|
193
190
|
end
|
@@ -411,7 +408,7 @@ Net::SSH::Multi.start do |session|
|
|
411
408
|
session.with(:coord).exec! "cd #{gitdir} && git fetch origin #{options[:branch]}"
|
412
409
|
session.with(:coord).exec! "cd #{gitdir} && git checkout #{options[:branch]}"
|
413
410
|
end
|
414
|
-
|
411
|
+
elsif option[:gerrit] # gerrit
|
415
412
|
logger.info("Setting up git repository from gerrit ref:#{options[:gerrit]} on #{coordinator}")
|
416
413
|
session.with(:coord).exec! "git clone #{GERRIT_REPOSITORY} #{gitdir}"
|
417
414
|
session.with(:coord).exec! "cd #{gitdir} && git fetch #{GERRIT_REPOSITORY} #{options[:gerrit]} && git checkout FETCH_HEAD"
|
@@ -497,7 +494,6 @@ Net::SSH::Multi.start do |session|
|
|
497
494
|
session.with(:coord).exec! "mkdir -p #{PATH_DISTEMD_LOGS}"
|
498
495
|
begin
|
499
496
|
Timeout.timeout(10) do
|
500
|
-
root_iface_opt = options[:network_interface] ? "--network-interface #{options[:network_interface]}" : ''
|
501
497
|
distem_cmd = "LANG=C distemd #{options[:verbose] ? '--verbose' : ''} -d &>#{File.join(PATH_DISTEMD_LOGS,'distemd.log')}&"
|
502
498
|
|
503
499
|
session.with(:coord).exec! distem_cmd
|
@@ -545,19 +541,16 @@ Net::SSH::Multi.start do |session|
|
|
545
541
|
|
546
542
|
if ARGV[0]
|
547
543
|
begin
|
548
|
-
|
549
|
-
|
550
|
-
|
551
|
-
|
552
|
-
|
553
|
-
|
554
|
-
|
555
|
-
|
556
|
-
|
557
|
-
|
558
|
-
#session.with(:coord).exec! "export #{VAR_DISTEM_NODES}='#{(nodelist + [coordinator]) * "\n"}'; export #{VAR_DISTEM_COORD}='#{coordinator}';#{filename} #{script_args}"
|
559
|
-
session.with(:coord).exec! "rm #{filename}"
|
560
|
-
end
|
544
|
+
filename = session.with(:coord).exec!('tempfile')[coordinator][:stdout]
|
545
|
+
logger.info("Copying script file in '#{filename}' on #{coordinator}")
|
546
|
+
`scp #{ARGV[0]} root@#{coordinator}:#{filename}`
|
547
|
+
session.with(:coord).exec! "chmod +x #{filename}"
|
548
|
+
logger.info("Executing script file '#{filename}' on #{coordinator}")
|
549
|
+
|
550
|
+
argv_dup = ARGV.dup
|
551
|
+
argv_dup.shift
|
552
|
+
#session.with(:coord).exec! "export #{VAR_DISTEM_NODES}='#{(nodelist + [coordinator]) * "\n"}'; export #{VAR_DISTEM_COORD}='#{coordinator}';#{filename} #{script_args}"
|
553
|
+
session.with(:coord).exec! "rm #{filename}"
|
561
554
|
logger.info 'Script execution done'
|
562
555
|
rescue Errno::ENOENT
|
563
556
|
logger.error "script file '#{ARGV[0]}' not found"
|
@@ -582,6 +575,7 @@ Net::SSH::Multi.start do |session|
|
|
582
575
|
sock.send(stats.to_yaml,0)
|
583
576
|
sock.close
|
584
577
|
rescue SocketError, Errno::ECONNREFUSED, Errno::ECONNRESET, Errno::ETIMEDOUT, Errno::EHOSTUNREACH
|
585
|
-
|
578
|
+
logger.error("An error occured while sending stats to #{STATS_SERV}:#{STATS_PORT}.")
|
579
|
+
end
|
586
580
|
end
|
587
581
|
end
|
data/examples/g5k-tutorial.md
CHANGED
@@ -1,7 +1,6 @@
|
|
1
1
|
# @title Grid'5000 tutorial
|
2
2
|
# Grid'5000 tutorial
|
3
3
|
|
4
|
-
|
5
4
|
This tutorial aims at showing how **Ruby-Cute** can be used to
|
6
5
|
help the scripting of an experiment in the context of the Grid'5000 testbed.
|
7
6
|
The programming language used, as you would expect, is {https://www.ruby-lang.org/en/ Ruby}.
|
@@ -35,6 +34,12 @@ Before using **Ruby-Cute** you have to create the following file:
|
|
35
34
|
$ version: 3.0
|
36
35
|
$ EOF
|
37
36
|
|
37
|
+
You will also need 2 gems to do this tutorial:
|
38
|
+
- net-ssh
|
39
|
+
- net-scp
|
40
|
+
|
41
|
+
If you want to use taktuk you will need to have the executable on the machine where you are running the ruby script
|
42
|
+
|
38
43
|
## Getting acquainted with the pry console
|
39
44
|
|
40
45
|
After instaling `ruby-cute` and `pry` gems you can lunch a pry console
|
@@ -117,7 +122,7 @@ For this particular experiment we have the following requirements:
|
|
117
122
|
|
118
123
|
- A pair of SSH keys
|
119
124
|
- Use of standard environment (no deploy)
|
120
|
-
- Two nodes connected with infiniband
|
125
|
+
- Two nodes connected with infiniband
|
121
126
|
- MPI benchmark NETPIPE
|
122
127
|
- A MPI runtime (OpenMPI or MPICH)
|
123
128
|
|
@@ -169,7 +174,7 @@ see [SSH Configuration](https://www.grid5000.fr/mediawiki/index.php/SSH_and_Grid
|
|
169
174
|
Now that we have found the sites, let's submit a job. You can use between
|
170
175
|
Grenoble and Nancy sites. If you take a look at
|
171
176
|
{https://www.grid5000.fr/mediawiki/index.php/Status Monika} you will see that in
|
172
|
-
Nancy we
|
177
|
+
Nancy we can use the OAR property 'ib_rate=20' and in Grenoble we can use
|
173
178
|
'ib_rate=10'. More simply you can use the property ib_count=1 which will give
|
174
179
|
you nodes with infiniband whatever the rate.
|
175
180
|
|
@@ -250,7 +255,7 @@ Here to illustrate the use of temporary files, let's type the following:
|
|
250
255
|
and copy-paste the following code:
|
251
256
|
|
252
257
|
Net::SSH.start(nodes.first, "oar", grid5000_opt) do |ssh|
|
253
|
-
puts ssh.exec("cat /tmp/machine_file")
|
258
|
+
puts ssh.exec!("cat /tmp/machine_file")
|
254
259
|
end
|
255
260
|
|
256
261
|
If we save and quit the editor, the code will be evaluated in Pry context.
|
@@ -271,12 +276,12 @@ the benchmark. Create a Ruby file called netpipe:
|
|
271
276
|
With the following content:
|
272
277
|
|
273
278
|
Net::SSH.start(nodes.first, "oar", grid5000_opt) do |ssh|
|
274
|
-
netpipe_url = "
|
279
|
+
netpipe_url = "https://fossies.org/linux/privat/NetPIPE-3.7.2.tar.gz"
|
275
280
|
ssh.exec!("mkdir -p netpipe_exp")
|
276
281
|
ssh.exec!("wget -O ~/netpipe_exp/NetPIPE.tar.gz #{netpipe_url}")
|
277
282
|
ssh.exec!("cd netpipe_exp && tar -zvxf NetPIPE.tar.gz")
|
278
|
-
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.
|
279
|
-
ssh.exec("mpirun --mca plm_rsh_agent \"oarsh\" -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.
|
283
|
+
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.2 && make mpi")
|
284
|
+
puts ssh.exec!("mpirun --mca plm_rsh_agent \"oarsh\" -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.2/NPmpi")
|
280
285
|
end
|
281
286
|
|
282
287
|
Then, execute the created script:
|
@@ -308,14 +313,16 @@ We can fix this problem by prefixing the `mpirun` command with `export OAR_JOB_K
|
|
308
313
|
Now the code will look like this:
|
309
314
|
|
310
315
|
Net::SSH.start(nodes.first, "oar", grid5000_opt) do |ssh|
|
311
|
-
netpipe_url = "
|
316
|
+
netpipe_url = "https://fossies.org/linux/privat/NetPIPE-3.7.2.tar.gz"
|
312
317
|
ssh.exec!("mkdir -p netpipe_exp")
|
313
318
|
ssh.exec!("wget -O ~/netpipe_exp/NetPIPE.tar.gz #{netpipe_url}")
|
314
319
|
ssh.exec!("cd netpipe_exp && tar -zvxf NetPIPE.tar.gz")
|
315
|
-
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.
|
316
|
-
ssh.exec("export OAR_JOB_KEY_FILE=~/my_ssh_jobkey;mpirun --mca plm_rsh_agent \"oarsh\" -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.
|
320
|
+
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.2 && make mpi")
|
321
|
+
puts ssh.exec!("export OAR_JOB_KEY_FILE=~/my_ssh_jobkey;mpirun --mca plm_rsh_agent \"oarsh\" -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.2/NPmpi")
|
317
322
|
end
|
318
323
|
|
324
|
+
[comment]: # output of the last ssh.exec still doesn't show
|
325
|
+
|
319
326
|
After running the script, it will show the output of the benchmark in the `pry` console:
|
320
327
|
|
321
328
|
[34] pry(main)> play netpipe.rb
|
@@ -341,13 +348,13 @@ The latency is given by the last column for a 1 byte message; the maximum throug
|
|
341
348
|
We can try to performn the same test without using infiniband, in order to observe the difference in bandwidth and latency:
|
342
349
|
|
343
350
|
Net::SSH.start(nodes.first, "oar", grid5000_opt) do |ssh|
|
344
|
-
netpipe_url = "
|
351
|
+
netpipe_url = "https://fossies.org/linux/privat/NetPIPE-3.7.2.tar.gz"
|
345
352
|
ssh.exec!("mkdir -p netpipe_exp")
|
346
353
|
ssh.exec!("wget -O ~/netpipe_exp/NetPIPE.tar.gz #{netpipe_url}")
|
347
354
|
ssh.exec!("cd netpipe_exp && tar -zvxf NetPIPE.tar.gz")
|
348
|
-
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.
|
355
|
+
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.2 && make mpi")
|
349
356
|
mpi_command = "export OAR_JOB_KEY_FILE=~/my_ssh_jobkey;"
|
350
|
-
mpi_command+= "mpirun --mca plm_rsh_agent \"oarsh\" --mca btl self,sm,tcp -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.
|
357
|
+
mpi_command+= "mpirun --mca plm_rsh_agent \"oarsh\" --mca btl self,sm,tcp -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.2/NPmpi"
|
351
358
|
ssh.exec(mpi_command)
|
352
359
|
end
|
353
360
|
|
@@ -355,14 +362,14 @@ We can modify slightly the previous script to write the result into a file.
|
|
355
362
|
We need to use `ssh.exec!` to capture the output of the commands.
|
356
363
|
|
357
364
|
Net::SSH.start(nodes.first, "oar", grid5000_opt) do |ssh|
|
358
|
-
netpipe_url = "
|
365
|
+
netpipe_url = "https://fossies.org/linux/privat/NetPIPE-3.7.2.tar.gz"
|
359
366
|
ssh.exec!("mkdir -p netpipe_exp")
|
360
367
|
ssh.exec!("wget -O ~/netpipe_exp/NetPIPE.tar.gz #{netpipe_url}")
|
361
368
|
ssh.exec!("cd netpipe_exp && tar -zvxf NetPIPE.tar.gz")
|
362
|
-
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.
|
369
|
+
ssh.exec!("cd netpipe_exp/NetPIPE-3.7.2 && make mpi")
|
363
370
|
|
364
371
|
File.open("output_netpipe.txt", 'w') do |f|
|
365
|
-
f.puts ssh.exec!("OAR_JOB_KEY_FILE=~/my_ssh_jobkey; mpirun --mca plm_rsh_agent \"oarsh\" -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.
|
372
|
+
f.puts ssh.exec!("OAR_JOB_KEY_FILE=~/my_ssh_jobkey; mpirun --mca plm_rsh_agent \"oarsh\" -machinefile /tmp/machine_file ~/netpipe_exp/NetPIPE-3.7.2/NPmpi")
|
366
373
|
end
|
367
374
|
end
|
368
375
|
|
@@ -447,7 +454,7 @@ and type the following code:
|
|
447
454
|
job = {}
|
448
455
|
|
449
456
|
sites.each do |site|
|
450
|
-
job = $g5k.reserve(:site => site, :cluster => 1, :nodes => 4, :wait => false, :walltime => "01:00:00")
|
457
|
+
job = $g5k.reserve(:site => site, :cluster => 1, :nodes => 4, :wait => false, :walltime => "01:00:00", :type => :allow_classic_ssh)
|
451
458
|
begin
|
452
459
|
job = $g5k.wait_for_job(job, :wait_time => 60)
|
453
460
|
puts "Nodes assigned #{job['assigned_nodes']}"
|
@@ -554,7 +561,7 @@ Open the editor in pry console:
|
|
554
561
|
|
555
562
|
Then, type:
|
556
563
|
|
557
|
-
SOURCE_NAS = "http://public.rennes.grid5000.fr/~
|
564
|
+
SOURCE_NAS = "http://public.rennes.grid5000.fr/~ddelabroye/NPB3.3.tar"
|
558
565
|
|
559
566
|
`wget #{SOURCE_NAS} -O /tmp/NAS.tar`
|
560
567
|
|
data/examples/g5k_exp_virt.rb
CHANGED
data/lib/cute/bash.rb
CHANGED
@@ -55,7 +55,7 @@ module Cute; module Bash
|
|
55
55
|
return Digest::SHA512.hexdigest(randee).to_s
|
56
56
|
end
|
57
57
|
|
58
|
-
def _run(cmd,
|
58
|
+
def _run(cmd, _opts)
|
59
59
|
# it's a kind of magic
|
60
60
|
$stderr.write("\nBASH CMD: #{cmd}\n") if @debug
|
61
61
|
nonce = _nonce()
|
@@ -74,7 +74,7 @@ module Cute; module Bash
|
|
74
74
|
return output, status.to_i
|
75
75
|
end
|
76
76
|
|
77
|
-
def _run_block(cmd,
|
77
|
+
def _run_block(cmd, _opts)
|
78
78
|
@stdin.write("#{cmd}; printf '%04d#{nonce}' $?\n")
|
79
79
|
end
|
80
80
|
|
@@ -110,7 +110,7 @@ module Cute; module Bash
|
|
110
110
|
end
|
111
111
|
|
112
112
|
def run_status(cmd, opts = {})
|
113
|
-
|
113
|
+
_out, status = _run(cmd, opts)
|
114
114
|
return status
|
115
115
|
end
|
116
116
|
|
@@ -278,7 +278,7 @@ module Cute; module Bash
|
|
278
278
|
|
279
279
|
def packages
|
280
280
|
list = run("dpkg -l")
|
281
|
-
|
281
|
+
_unlines(list).map do |p|
|
282
282
|
s, n, v = p.split
|
283
283
|
{ :status => s, :name => n, :version => v }
|
284
284
|
end
|
@@ -313,13 +313,13 @@ module Cute; module Bash
|
|
313
313
|
|
314
314
|
def self.bash(cmd = 'bash', debug = false, &block)
|
315
315
|
if not block_given?
|
316
|
-
sin, sout,
|
316
|
+
sin, sout, _serr, _thr = Open3.popen3(cmd)
|
317
317
|
return Bash.new(sin, sout, debug)
|
318
318
|
end
|
319
319
|
# run bash interpreter using this command
|
320
320
|
result = nil
|
321
|
-
Open3.popen3(cmd) do |
|
322
|
-
dsl = Bash.new(
|
321
|
+
Open3.popen3(cmd) do |cmdsin, cmdsout, _cmdserr, _cmdthr|
|
322
|
+
dsl = Bash.new(cmdsin, cmdsout, debug)
|
323
323
|
dsl.cd('~') # go to the home dir
|
324
324
|
result = dsl.parse(&block)
|
325
325
|
end
|
data/lib/cute/configparser.rb
CHANGED
@@ -97,7 +97,9 @@ module Cute
|
|
97
97
|
@path.compact.each do |field|
|
98
98
|
begin
|
99
99
|
field = Integer(field)
|
100
|
-
rescue ArgumentError
|
100
|
+
rescue ArgumentError => e
|
101
|
+
puts "Error: #{e.message}"
|
102
|
+
puts "#{e.backtrace}"
|
101
103
|
end
|
102
104
|
|
103
105
|
if ret[field]
|
@@ -164,7 +166,7 @@ module Cute
|
|
164
166
|
end
|
165
167
|
end
|
166
168
|
|
167
|
-
def check_array(val, array,
|
169
|
+
def check_array(val, array, _fieldname)
|
168
170
|
unless array.include?(val)
|
169
171
|
raise ParserError.new(
|
170
172
|
"Invalid value '#{val}', allowed value"\
|
@@ -183,7 +185,7 @@ module Cute
|
|
183
185
|
check_array(val, range.entries, fieldname)
|
184
186
|
end
|
185
187
|
|
186
|
-
def check_regexp(val, regexp,
|
188
|
+
def check_regexp(val, regexp, _fieldname)
|
187
189
|
unless val =~ regexp
|
188
190
|
raise ParserError.new(
|
189
191
|
"Invalid value '#{val}', the value must have the form (ruby-regexp): "\
|
@@ -193,8 +195,8 @@ module Cute
|
|
193
195
|
end
|
194
196
|
|
195
197
|
# A file, checking if exists (creating it otherwise) and writable
|
196
|
-
def check_file(val,
|
197
|
-
if File.
|
198
|
+
def check_file(val, _file, _fieldname)
|
199
|
+
if File.exist?(val)
|
198
200
|
unless File.file?(val)
|
199
201
|
raise ParserError.new("The file '#{val}' is not a regular file")
|
200
202
|
end
|
@@ -204,7 +206,7 @@ module Cute
|
|
204
206
|
end
|
205
207
|
|
206
208
|
# A directory, checking if exists (creating it otherwise) and writable
|
207
|
-
def check_dir(val,
|
209
|
+
def check_dir(val, _dir, _fieldname)
|
208
210
|
if File.exist?(val)
|
209
211
|
unless File.directory?(val)
|
210
212
|
raise ParserError.new("'#{val}' is not a regular directory")
|
@@ -215,7 +217,7 @@ module Cute
|
|
215
217
|
end
|
216
218
|
|
217
219
|
# A pathname, checking if exists (creating it otherwise) and writable
|
218
|
-
def check_pathname(val,
|
220
|
+
def check_pathname(val, _pathname, _fieldname)
|
219
221
|
begin
|
220
222
|
Pathname.new(val)
|
221
223
|
rescue
|
@@ -223,7 +225,7 @@ module Cute
|
|
223
225
|
end
|
224
226
|
end
|
225
227
|
|
226
|
-
def check_string(val, str,
|
228
|
+
def check_string(val, str, _fieldname)
|
227
229
|
unless val == str
|
228
230
|
raise ParserError.new(
|
229
231
|
"Invalid value '#{val}', allowed values are: '#{str}'"
|
@@ -231,7 +233,7 @@ module Cute
|
|
231
233
|
end
|
232
234
|
end
|
233
235
|
|
234
|
-
def customcheck_code(
|
236
|
+
def customcheck_code(_val, _fieldname, args)
|
235
237
|
begin
|
236
238
|
eval("#{args[:prefix]}#{args[:code]}#{args[:suffix]}")
|
237
239
|
rescue
|
@@ -239,11 +241,11 @@ module Cute
|
|
239
241
|
end
|
240
242
|
end
|
241
243
|
|
242
|
-
def customcheck_file(val,
|
244
|
+
def customcheck_file(val, _fieldname, args)
|
243
245
|
return if args[:disable]
|
244
246
|
val = File.join(args[:prefix],val) if args[:prefix]
|
245
247
|
val = File.join(val,args[:suffix]) if args[:suffix]
|
246
|
-
if File.
|
248
|
+
if File.exist?(val)
|
247
249
|
if File.file?(val)
|
248
250
|
if args[:writable]
|
249
251
|
unless File.stat(val).writable?
|
@@ -274,7 +276,7 @@ module Cute
|
|
274
276
|
end
|
275
277
|
end
|
276
278
|
|
277
|
-
def customcheck_dir(val,
|
279
|
+
def customcheck_dir(val, _fieldname, args)
|
278
280
|
return if args[:disable]
|
279
281
|
val = File.join(args[:prefix],val) if args[:prefix]
|
280
282
|
val = File.join(val,args[:suffix]) if args[:suffix]
|
data/lib/cute/execute.rb
CHANGED
@@ -2,8 +2,7 @@
|
|
2
2
|
module Cute
|
3
3
|
|
4
4
|
class Execute
|
5
|
-
|
6
|
-
require 'fcntl'
|
5
|
+
require 'fcntl'
|
7
6
|
attr_reader :command, :exec_pid, :stdout, :stderr, :status,:emptypipes
|
8
7
|
@@forkmutex = Mutex.new
|
9
8
|
|
@@ -254,14 +253,17 @@ module Cute
|
|
254
253
|
f_IO=IO.new(fd)
|
255
254
|
f_IO.close if !f_IO.closed?
|
256
255
|
end
|
257
|
-
rescue
|
256
|
+
rescue StandardError
|
258
257
|
#Some file descriptor are reserved for the rubyVM.
|
259
258
|
#So the function 'IO.new' raises an exception. We ignore that.
|
260
259
|
end
|
261
260
|
end
|
262
261
|
end
|
263
262
|
exec(*@command)
|
264
|
-
rescue SystemCallError
|
263
|
+
rescue SystemCallError => e
|
264
|
+
STDERR.puts "Fork Error: #{e.message} (#{e.class.name})"
|
265
|
+
STDERR.puts e.backtrace
|
266
|
+
rescue StandardError => e
|
265
267
|
STDERR.puts "Fork Error: #{e.message} (#{e.class.name})"
|
266
268
|
STDERR.puts e.backtrace
|
267
269
|
end
|
data/lib/cute/extensions.rb
CHANGED
@@ -42,11 +42,10 @@ module Cute
|
|
42
42
|
class OARSSHopts < Hash
|
43
43
|
|
44
44
|
def initialize(opts={})
|
45
|
-
|
45
|
+
super
|
46
46
|
raise "The argument must be a Hash" unless opts.is_a?(Hash)
|
47
|
-
|
48
|
-
|
49
|
-
|
47
|
+
self.merge!({:user => "oar", :keys => ["~/my_ssh_jobkey"], :port => 6667 })
|
48
|
+
self.merge!(opts)
|
50
49
|
end
|
51
50
|
|
52
51
|
end
|