@@ -208,6 +208,68 @@ function teardown() {
208208 grep -E ' ^boottime\s+1337\s+3141519$' <<< " $output"
209209}
210210
211+ # issue: https://github.com/opencontainers/runc/issues/4390
212+ @test " runc run [joining more than one container namespaces]" {
213+ requires timens root
214+
215+ update_config ' .process.args = ["sleep", "infinity"]'
216+
217+ if [ $EUID -eq 0 ]; then
218+ update_config ' .linux.namespaces += [{"type": "user"}]
219+ | .linux.uidMappings = [{"containerID": 0, "hostID": 100000, "size": 100}]
220+ | .linux.gidMappings = [{"containerID": 0, "hostID": 200000, "size": 200}]'
221+ remap_rootfs
222+ fi
223+ runc run -d --console-socket " $CONSOLE_SOCKET " target_ctr1
224+ [ " $status " -eq 0 ]
225+ pid1=" $( __runc state target_ctr1 | jq .pid) "
226+
227+ update_config ' .linux.namespaces += [{"type": "time"}]
228+ | .linux.timeOffsets = {
229+ "monotonic": { "secs": 7881, "nanosecs": 2718281 },
230+ "boottime": { "secs": 1337, "nanosecs": 3141519 }
231+ }'
232+ runc run -d --console-socket " $CONSOLE_SOCKET " target_ctr2
233+ [ " $status " -eq 0 ]
234+ pid2=" $( __runc state target_ctr2 | jq .pid) "
235+
236+ update_config ' .linux.namespaces |= map_values(.path = if .type == "user" then "/proc/' " $pid1 " ' /ns/user"
237+ elif .type == "pid" then "/proc/' " $pid1 " ' /ns/pid"
238+ elif .type == "time" then "/proc/' " $pid2 " ' /ns/time"
239+ else "" end)'
240+ # Remove the userns and timens configuration (they cannot be changed).
241+ update_config ' .linux |= (del(.uidMappings) | del(.gidMappings) | del(.timeOffsets))'
242+ runc run -d --console-socket " $CONSOLE_SOCKET " attached_ctr
243+ [ " $status " -eq 0 ]
244+
245+ # Make sure there are two sleep processes in our container.
246+ runc exec attached_ctr ps aux
247+ [ " $status " -eq 0 ]
248+ run -0 grep " sleep infinity" <<< " $output"
249+ [ " ${# lines[@]} " -eq 2 ]
250+
251+ # ... that the userns mappings are the same...
252+ runc exec attached_ctr cat /proc/self/uid_map
253+ [ " $status " -eq 0 ]
254+ if [ $EUID -eq 0 ]; then
255+ grep -E ' ^\s+0\s+100000\s+100$' <<< " $output"
256+ else
257+ grep -E ' ^\s+0\s+' $EUID ' \s+1$' <<< " $output"
258+ fi
259+ runc exec attached_ctr cat /proc/self/gid_map
260+ [ " $status " -eq 0 ]
261+ if [ $EUID -eq 0 ]; then
262+ grep -E ' ^\s+0\s+200000\s+200$' <<< " $output"
263+ else
264+ grep -E ' ^\s+0\s+' $EUID ' \s+1$' <<< " $output"
265+ fi
266+
267+ # ... as well as the timens offsets.
268+ runc exec attached_ctr cat /proc/self/timens_offsets
269+ grep -E ' ^monotonic\s+7881\s+2718281$' <<< " $output"
270+ grep -E ' ^boottime\s+1337\s+3141519$' <<< " $output"
271+ }
272+
211273@test " runc run [execve error]" {
212274 cat << EOF >rootfs/run.sh
213275#!/mmnnttbb foo bar
0 commit comments