runshare 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: cb0cad2d91fecadd6f8e1b1068f37cf8c4a44623
4
+ data.tar.gz: 67fdb4217e143f4e0fe1673807bd34fa42836885
5
+ SHA512:
6
+ metadata.gz: 9f93b3354a8a51d911895fd367092a8773bfed1c98efa515e09ab250034fe498fd03cb75add6b461b975a55db0031a273fbeacc8462f9f866a67bd5fbfacdbf1
7
+ data.tar.gz: cf463e5f29ed3f93cdf8b6c3df53077c70a2cc4db846a534c3374ab8a4e911a9fdbe289eaf4ca709a7291216141c0dbf4a510fdd13d0efa9835e4835cdf26bba
data/.gitignore ADDED
@@ -0,0 +1,21 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /_yardoc/
4
+ /coverage/
5
+ /doc/
6
+ /pkg/
7
+ /spec/reports/
8
+ /tmp/
9
+ /.idea/
10
+ .tool-versions
11
+ CMakeLists.txt
12
+ /cmake-build-debug/
13
+
14
+ *.bundle
15
+ *.so
16
+ *.o
17
+ *.a
18
+ mkmf.log
19
+
20
+ # rspec failure tracking
21
+ .rspec_status
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --format documentation
2
+ --color
3
+ --require spec_helper
data/.travis.yml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ sudo: false
3
+ language: ruby
4
+ cache: bundler
5
+ rvm:
6
+ - 2.4.10
7
+ before_install: gem install bundler -v 1.17.3
data/Gemfile ADDED
@@ -0,0 +1,6 @@
1
+ source "https://rubygems.org"
2
+
3
+ git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
4
+
5
+ # Specify your gem's dependencies in runshare.gemspec
6
+ gemspec
data/Gemfile.lock ADDED
@@ -0,0 +1,38 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ runshare (0.1.0)
5
+
6
+ GEM
7
+ remote: https://rubygems.org/
8
+ specs:
9
+ diff-lcs (1.4.4)
10
+ rake (10.5.0)
11
+ rake-compiler (1.1.1)
12
+ rake
13
+ rspec (3.10.0)
14
+ rspec-core (~> 3.10.0)
15
+ rspec-expectations (~> 3.10.0)
16
+ rspec-mocks (~> 3.10.0)
17
+ rspec-core (3.10.1)
18
+ rspec-support (~> 3.10.0)
19
+ rspec-expectations (3.10.1)
20
+ diff-lcs (>= 1.2.0, < 2.0)
21
+ rspec-support (~> 3.10.0)
22
+ rspec-mocks (3.10.2)
23
+ diff-lcs (>= 1.2.0, < 2.0)
24
+ rspec-support (~> 3.10.0)
25
+ rspec-support (3.10.2)
26
+
27
+ PLATFORMS
28
+ ruby
29
+
30
+ DEPENDENCIES
31
+ bundler (~> 1.17)
32
+ runshare!
33
+ rake (~> 10.0)
34
+ rake-compiler
35
+ rspec (~> 3.0)
36
+
37
+ BUNDLED WITH
38
+ 1.17.3
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2021 Ivan Prisyazhnyy
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,103 @@
1
+ # ruby unshare (runshare)
2
+
3
+ This tool allows to unshare Linux namespaces.
4
+ The implementation is similar to the unshare(1) tool.
5
+
6
+ ## Installation
7
+
8
+ Add this line to your application's Gemfile:
9
+
10
+ ```ruby
11
+ gem 'runshare'
12
+ ```
13
+
14
+ And then execute:
15
+
16
+ $ bundle
17
+
18
+ Or install it yourself as:
19
+
20
+ $ gem install runshare
21
+
22
+ ## Usage
23
+
24
+ > require "runshare"
25
+ > RUnshare::unshare
26
+
27
+ For example:
28
+
29
+ cat > test.rb
30
+
31
+ require "runshare"
32
+
33
+ pid = RUnshare::unshare(
34
+ :clone_newpid => true,
35
+ :clone_newns => true,
36
+ :clone_newcgroup => true,
37
+ :clone_newipc => true,
38
+ :clone_newuts => true,
39
+ :clone_newnet => true,
40
+ :clone_newtime => true,
41
+ :fork => true,
42
+ :mount_proc => "/proc",
43
+ # docker export $(docker create hello-world) | tar -xf - -C rootfs
44
+ :root => "/tmp/rootfs"
45
+ )
46
+
47
+ if pid == 0
48
+ # child
49
+ puts "--- #{Process.pid}"
50
+ if system("/hello") != true
51
+ raise "bad"
52
+ end
53
+ puts "--- done"
54
+ else
55
+ # parent
56
+ puts "-- unshare=#{pid}, pid=#{Process.pid}"
57
+ puts "-- exit=#{Process.waitpid(pid)}"
58
+ end
59
+
60
+ ^D
61
+
62
+ sudo ruby -I ./lib ./test.rb
63
+
64
+ ## Quick start
65
+
66
+ $ rake compile && echo 'require "runshare"; RUnshare::unshare(:clone_newuts => true)' | irb
67
+ install -c tmp/x86_64-linux/runshare/2.4.10/runshare.so lib/runshare/runshare.so
68
+ cp tmp/x86_64-linux/runshare/2.4.10/runshare.so tmp/x86_64-linux/stage/lib/runshare/runshare.so
69
+ Switch to inspect mode.
70
+ require "runshare"; RUnshare::unshare
71
+
72
+ ## Ruby <2.5
73
+
74
+ If your app is single threaded and you are observing:
75
+
76
+ eval:1: warning: pthread_create failed for timer: Invalid argument, scheduling broken
77
+
78
+ Just ignore it with some degree of bravity. You also
79
+ can silence it by setting:
80
+
81
+ $VERBOSE = nil
82
+
83
+ ## Development
84
+
85
+ After checking out the repo, run `bin/setup` to install dependencies.
86
+ Then, run `rake spec` to run the tests.
87
+ You can also run `bin/console` for an interactive prompt that will allow you to experiment.
88
+
89
+ To install this gem onto your local machine, run `bundle exec rake install`.
90
+ To release a new version, update the version number in `version.rb`,
91
+ and then run `bundle exec rake release`, which will create a git tag
92
+ for the version, push git commits and tags, and push the `.gem` file
93
+ to [rubygems.org](https://rubygems.org).
94
+
95
+ ## Contributing
96
+
97
+ Bug reports and pull requests are welcome on GitHub at https://github.com/sitano/runshare.
98
+ This project is intended to be a safe, welcoming space for collaboration,
99
+ and contributors are expected to adhere to the [Contributor Covenant](http://contributor-covenant.org) code of conduct.
100
+
101
+ ## License
102
+
103
+ The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
data/Rakefile ADDED
@@ -0,0 +1,14 @@
1
+ require "bundler/gem_tasks"
2
+ require "rspec/core/rake_task"
3
+
4
+ RSpec::Core::RakeTask.new(:spec)
5
+
6
+ require "rake/extensiontask"
7
+
8
+ task :build => :compile
9
+
10
+ Rake::ExtensionTask.new("runshare") do |ext|
11
+ ext.lib_dir = "lib/runshare"
12
+ end
13
+
14
+ task :default => [:clobber, :compile, :spec]
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "runshare"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start(__FILE__)
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
@@ -0,0 +1,33 @@
1
+ require "mkmf"
2
+
3
+ append_cflags('-D_GNU_SOURCE')
4
+ append_cflags('-DPACKAGE_STRING="\"runshare\""')
5
+ append_cflags('-Wno-discarded-qualifiers')
6
+
7
+ if have_func("nanosleep", "time.h")
8
+ $defs.push("-DHAVE_NANOSLEEP")
9
+ elsif have_func("usleep", "time.h")
10
+ $defs.push("-DHAVE_USLEEP")
11
+ end
12
+
13
+ if have_func("fsync", "unistd.h")
14
+ $defs.push("-DHAVE_FSYNC")
15
+ end
16
+
17
+ if have_func("vasprintf", "stdio.h")
18
+ $defs.push("-DHAVE_VASPRINTF")
19
+ end
20
+
21
+ if have_func("unshare", "sys/syscall.h")
22
+ $defs.push("-DHAVE_UNSHARE")
23
+ end
24
+ if have_func("setns", "sys/syscall.h")
25
+ $defs.push("-DHAVE_SETNS")
26
+ end
27
+ if have_func("err", "err.h")
28
+ $defs.push("-DHAVE_ERR_H")
29
+ end
30
+
31
+ $srcs = ["runshare.c", "unshare.c"]
32
+
33
+ create_makefile("runshare/runshare")
@@ -0,0 +1,115 @@
1
+ /*
2
+ * No copyright is claimed. This code is in the public domain; do with
3
+ * it what you wish.
4
+ *
5
+ * Written by Karel Zak <kzak@redhat.com>
6
+ * Petr Uzel <petr.uzel@suse.cz>
7
+ */
8
+
9
+ #ifndef UTIL_LINUX_ALL_IO_H
10
+ #define UTIL_LINUX_ALL_IO_H
11
+
12
+ #include <string.h>
13
+ #include <unistd.h>
14
+ #include <errno.h>
15
+ #include <sys/types.h>
16
+ #ifdef HAVE_SYS_SENDFILE_H
17
+ # include <sys/sendfile.h>
18
+ #endif
19
+
20
+ #include "c.h"
21
+
22
+ static inline int write_all(int fd, const void *buf, size_t count)
23
+ {
24
+ while (count) {
25
+ ssize_t tmp;
26
+
27
+ errno = 0;
28
+ tmp = write(fd, buf, count);
29
+ if (tmp > 0) {
30
+ count -= tmp;
31
+ if (count)
32
+ buf = (const void *) ((const char *) buf + tmp);
33
+ } else if (errno != EINTR && errno != EAGAIN)
34
+ return -1;
35
+ if (errno == EAGAIN) /* Try later, *sigh* */
36
+ xusleep(250000);
37
+ }
38
+ return 0;
39
+ }
40
+
41
+ static inline int fwrite_all(const void *ptr, size_t size,
42
+ size_t nmemb, FILE *stream)
43
+ {
44
+ while (nmemb) {
45
+ size_t tmp;
46
+
47
+ errno = 0;
48
+ tmp = fwrite(ptr, size, nmemb, stream);
49
+ if (tmp > 0) {
50
+ nmemb -= tmp;
51
+ if (nmemb)
52
+ ptr = (const void *) ((const char *) ptr + (tmp * size));
53
+ } else if (errno != EINTR && errno != EAGAIN)
54
+ return -1;
55
+ if (errno == EAGAIN) /* Try later, *sigh* */
56
+ xusleep(250000);
57
+ }
58
+ return 0;
59
+ }
60
+
61
+ static inline ssize_t read_all(int fd, char *buf, size_t count)
62
+ {
63
+ ssize_t ret;
64
+ ssize_t c = 0;
65
+ int tries = 0;
66
+
67
+ memset(buf, 0, count);
68
+ while (count > 0) {
69
+ ret = read(fd, buf, count);
70
+ if (ret < 0) {
71
+ if ((errno == EAGAIN || errno == EINTR) && (tries++ < 5)) {
72
+ xusleep(250000);
73
+ continue;
74
+ }
75
+ return c ? c : -1;
76
+ }
77
+ if (ret == 0)
78
+ return c;
79
+ tries = 0;
80
+ count -= ret;
81
+ buf += ret;
82
+ c += ret;
83
+ }
84
+ return c;
85
+ }
86
+
87
+ static inline ssize_t sendfile_all(int out, int in, off_t *off, size_t count)
88
+ {
89
+ #if defined(HAVE_SENDFILE) && defined(__linux__)
90
+ ssize_t ret;
91
+ ssize_t c = 0;
92
+ int tries = 0;
93
+ while (count) {
94
+ ret = sendfile(out, in, off, count);
95
+ if (ret < 0) {
96
+ if ((errno == EAGAIN || errno == EINTR) && (tries++ < 5)) {
97
+ xusleep(250000);
98
+ continue;
99
+ }
100
+ return c ? c : -1;
101
+ }
102
+ if (ret == 0)
103
+ return c;
104
+ tries = 0;
105
+ count -= ret;
106
+ c += ret;
107
+ }
108
+ return c;
109
+ #else
110
+ errno = ENOSYS;
111
+ return -1;
112
+ #endif
113
+ }
114
+
115
+ #endif /* UTIL_LINUX_ALL_IO_H */