1
- #! /bin/sh
1
+ #! /bin/bash
2
2
3
3
# Copyright (c) 2023 The PaSh Authors.
4
4
#
@@ -21,6 +21,12 @@ export TRY_COMMAND
21
21
# Run a command (in `$@`) in an overlay (in `$SANDBOX_DIR`)
22
22
# ###############################################################################
23
23
24
+ breakpoint () {
25
+ declare -p > /tmp/vars.sh
26
+ declare -f >> /tmp/vars.sh
27
+ bash --rcfile /tmp/vars -i
28
+ }
29
+
24
30
try () {
25
31
START_DIR=" $PWD "
26
32
@@ -65,9 +71,11 @@ try() {
65
71
# # Find all the directories and mounts that need to be mounted
66
72
DIRS_AND_MOUNTS=" $( mktemp) "
67
73
export DIRS_AND_MOUNTS
68
- find / -maxdepth 1 > " $DIRS_AND_MOUNTS "
69
- findmnt --real -r -o target -n >> " $DIRS_AND_MOUNTS "
70
- sort -u -o " $DIRS_AND_MOUNTS " " $DIRS_AND_MOUNTS "
74
+ export DIRS_AND_MOUNTS
75
+ # find / -maxdepth 1 >"$DIRS_AND_MOUNTS" 2>/dev/null
76
+ # findmnt --real -r -o target -n >>"$DIRS_AND_MOUNTS"
77
+ # sort -u -o "$DIRS_AND_MOUNTS" "$DIRS_AND_MOUNTS"
78
+ printf " /\n/dev\n/home\n/tmp\n/proc" > $DIRS_AND_MOUNTS
71
79
72
80
# Calculate UPDATED_DIRS_AND_MOUNTS that contains the merge arguments in LOWER_DIRS
73
81
UPDATED_DIRS_AND_MOUNTS=" $( mktemp) "
@@ -96,7 +104,6 @@ try() {
96
104
echo " $new_mountpoint " >> " $UPDATED_DIRS_AND_MOUNTS "
97
105
done < " $DIRS_AND_MOUNTS "
98
106
99
-
100
107
# we will overlay-mount each root directory separately (instead of all at once) because some directories cannot be overlayed
101
108
# so we set up the mount points now
102
109
#
@@ -115,7 +122,7 @@ try() {
115
122
if [ -d " $mountpoint " ] && ! [ -L " $mountpoint " ]
116
123
then
117
124
# shellcheck disable=SC2174 # warning acknowledged, "When used with -p, -m only applies to the deepest directory."
118
- mkdir -m " $( stat -c %a " $mountpoint " ) " -p " ${SANDBOX_DIR} /upperdir/${mountpoint} " " ${SANDBOX_DIR} /workdir/ ${mountpoint} " " ${SANDBOX_DIR} /temproot/ ${mountpoint} "
125
+ mkdir -m " $( stat -c %a " $mountpoint " ) " -p " ${SANDBOX_DIR} /upperdir/${mountpoint} "
119
126
fi
120
127
done < " $DIRS_AND_MOUNTS "
121
128
@@ -127,9 +134,14 @@ try() {
127
134
128
135
export chroot_executable
129
136
export script_to_execute
130
-
131
137
cat > " $mount_and_execute " << "EOF "
132
- #!/bin/sh
138
+ #!/bin/bash
139
+
140
+ breakpoint() {
141
+ declare -p > /tmp/vars.sh
142
+ declare -f >> /tmp/vars.sh
143
+ bash --rcfile /tmp/vars -i
144
+ }
133
145
134
146
TRY_COMMAND="$TRY_COMMAND($0)"
135
147
@@ -149,7 +161,6 @@ mount_devices() {
149
161
sandbox_dir="$1"
150
162
for dev in $devices_to_mount
151
163
do
152
- touch "$sandbox_dir/temproot/dev/$dev"
153
164
mount -o bind /dev/$dev "$sandbox_dir/temproot/dev/$dev"
154
165
done
155
166
}
@@ -174,10 +185,10 @@ autodetect_union_helper() {
174
185
}
175
186
176
187
# notify the mapper that we're up
177
- echo "a" > "$SOCKET"
188
+ # echo "a" > "$SOCKET"
178
189
179
190
# wait for mapper to finish
180
- cat "$SOCKET" > /dev/null
191
+ # cat "$SOCKET" > /dev/null
181
192
182
193
# Detect if union_helper is set, if not, we try to autodetect them
183
194
if [ -z "$UNION_HELPER" ]
@@ -187,104 +198,88 @@ then
187
198
fi
188
199
189
200
# actually mount the overlays
190
- for mountpoint in $(cat "$UPDATED_DIRS_AND_MOUNTS")
191
- do
192
- pure_mountpoint=${mountpoint##*:}
193
-
194
- ## We are not interested in mounts that are not directories
195
- if ! [ -d "$pure_mountpoint" ]
196
- then
197
- continue
198
- fi
199
-
200
- ## Symlinks
201
- if [ -L "$pure_mountpoint" ]
202
- then
203
- ln -s $(readlink "$pure_mountpoint") "$SANDBOX_DIR/temproot/$pure_mountpoint"
204
- continue
205
- fi
206
-
207
- ## Don't do anything for the root and skip if it is /dev or /proc, we will mount it later
208
- case "$pure_mountpoint" in
209
- (/| /dev|/proc) continue;;
210
- esac
201
+ # for mountpoint in $(cat "$UPDATED_DIRS_AND_MOUNTS")
202
+ # do
203
+ # pure_mountpoint=${mountpoint##*:}
204
+
205
+ # ## We are not interested in mounts that are not directories
206
+ # if ! [ -d "$pure_mountpoint" ]
207
+ # then
208
+ # continue
209
+ # fi
210
+
211
+ # ## Symlinks
212
+ # if [ -L "$pure_mountpoint" ]
213
+ # then
214
+ # ln -s $(readlink "$pure_mountpoint") "$SANDBOX_DIR/temproot/$pure_mountpoint"
215
+ # continue
216
+ # fi
217
+
218
+ # ## Don't do anything for the root and skip if it is /dev or /proc, we will mount it later
219
+ # case "$pure_mountpoint" in
220
+ # ( /dev|/proc) continue;;
221
+ # esac
211
222
212
223
# Try mounting everything normally
213
- make_overlay "$SANDBOX_DIR" "$mountpoint" "$pure_mountpoint" 2>>"$try_mount_log"
214
- # If mounting everything normally fails, we try using either using mergerfs or unionfs to mount them.
224
+ make_overlay "$SANDBOX_DIR" /fake_root/ / 2>>"$try_mount_log"
225
+ # If mounting everything normally fails, we try using either using mergerfs or unionfs to mount them.
215
226
if [ "$?" -ne 0 ]
216
227
then
217
- ## If the overlay failed, it means that there is a nested mount inside the target mount, e.g., both `/home` and `/home/user/mnt` are mounts.
218
- ## To address this, we use unionfs/mergerfs (they support the same functionality) to show all mounts under the target mount as normal directories.
219
- ## Then we can normally make the overlay on the new union directory.
220
- ##
221
- ## KK 2023-06-29 Since this uses findmnt, it performs the union+overlay for both the outside and the inside mount.
222
- ## In the best case scenario this is only causing extra work (the internal mount is already shown through the unionfs),
223
- ## but in the worst case this could lead to bugs due to the extra complexity (e.g., because we are doing mounts on top of each other).
224
- ## We should try to investigate either:
225
- ## 1. Not doing another overlay if we have done it for a parent directory (we can keep around a list of overlays and skip if we are in a child)
226
- ## 2. Do one unionfs+overlay at the root `/` once and be done with it!
227
-
228
- if [ -z "$UNION_HELPER" ]
229
- then
230
- ## We can ignore this mountpoint, if the user program tries to use it, it will crash, but if not we can run normally
231
- printf "%s: Warning: Failed mounting $mountpoint as an overlay and mergerfs or unionfs not set and could not be found, see \"$try_mount_log\"\n" "$TRY_COMMAND" >&2
232
- else
233
- merger_dir=$(mktemp -d)
234
-
235
- ## Create a union directory
236
- "$UNION_HELPER" $mountpoint $merger_dir 2>>"$try_mount_log" ||
237
- printf "%s: Warning: Failed mounting $mountpoint via $UNION_HELPER, see \"$try_mount_log\"\n" "$TRY_COMMAND" >&2
238
- make_overlay "$SANDBOX_DIR" "$merger_dir" "$pure_mountpoint" 2>>"$try_mount_log" ||
239
- printf "%s: Warning: Failed mounting $mountpoint as an overlay via $UNION_HELPER, see \"$try_mount_log\"\n" "$TRY_COMMAND" >&2
240
- fi
228
+ echo Error mounting overlay
229
+ breakpoint
241
230
fi
242
- done
231
+ # done
243
232
244
233
## Mount a few select devices in /dev
245
234
mount_devices "$SANDBOX_DIR"
235
+ mount -t proc proc ${SANDBOX_DIR}/temproot/proc
246
236
247
237
## Check if chroot_executable exists, #29
248
238
if ! [ -f "$SANDBOX_DIR/temproot/$chroot_executable" ]
249
239
then
250
240
cp $chroot_executable "$SANDBOX_DIR/temproot/$chroot_executable"
251
241
fi
252
242
253
- unshare -- root="$SANDBOX_DIR/temproot" /bin/sh "$chroot_executable"
243
+ unshare -r -- root="$SANDBOX_DIR/temproot" /bin/bash "$chroot_executable"
254
244
exitcode="$?"
255
245
256
246
# unmount the devices
257
- sync
258
247
unmount_devices "$SANDBOX_DIR"
259
- rm "$sandbox_dir/temproot/dev/stdin"
260
- rm "$sandbox_dir/temproot/dev/stdout"
261
- rm "$sandbox_dir/temproot/dev/stderr"
262
-
248
+ # rm "$sandbox_dir/temproot/dev/stdin"
249
+ # rm "$sandbox_dir/temproot/dev/stdout"
250
+ # rm "$sandbox_dir/temproot/dev/stderr"
251
+ umount ${SANDBOX_DIR}/temproot/proc
252
+ umount ${SANDBOX_DIR}/temproot
253
+ sync
263
254
exit $exitcode
264
255
EOF
265
256
266
257
# NB we substitute in the heredoc, so the early unsets are okay!
267
258
cat > " $chroot_executable " << EOF
268
- #!/bin/sh
259
+ #!/bin/bash
260
+
261
+ breakpoint() {
262
+ declare -p > /tmp/vars.sh
263
+ declare -f >> /tmp/vars.sh
264
+ bash --rcfile /tmp/vars -i
265
+ }
269
266
270
267
unset START_DIR SANDBOX_DIR UNION_HELPER DIRS_AND_MOUNTS TRY_EXIT_STATUS SOCKET
271
268
unset script_to_execute chroot_executable try_mount_log
272
269
273
- mount -t proc proc /proc &&
274
- cd /dev &&
275
- ln -s /proc/self/fd/0 stdin &&
276
- ln -s /proc/self/fd/1 stdout &&
277
- ln -s /proc/self/fd/2 stderr &&
278
- cd "$START_DIR " &&
270
+ # cd /dev &&
271
+ # ln -s /proc/self/fd/0 stdin &&
272
+ # ln -s /proc/self/fd/1 stdout &&
273
+ # ln -s /proc/self/fd/2 stderr &&
274
+ cd "$START_DIR "
279
275
if [ "$EUSER " ]
280
276
then
281
- su - $EUSER -c "cd " $START_DIR " && sh $script_to_execute "
277
+ su - $EUSER -c "cd $START_DIR && sh $script_to_execute "
282
278
else
283
279
cd "$START_DIR " &&
284
280
. "$script_to_execute "
285
281
fi
286
282
EOF
287
-
288
283
echo " $@ " > " $script_to_execute "
289
284
290
285
# `$script_to_execute` need not be +x to be sourced
@@ -298,33 +293,33 @@ EOF
298
293
# enable job control so interactive commands will play nicely with try asking for user input later(for committing). #5
299
294
[ -t 0 ] && set -m
300
295
301
- SOCKET=" $( mktemp -u) "
302
- mkfifo " $SOCKET "
303
- export SOCKET
296
+ # SOCKET="$(mktemp -u)"
297
+ # mkfifo "$SOCKET"
298
+ # export SOCKET
304
299
305
300
# Running mapper in a subshell to suppress job control [1] + Done message
306
- (mapper& )
301
+ # (mapper&)
307
302
308
303
# --mount: mounting and unmounting filesystems will not affect the rest of the system outside the unshare
309
304
# --user: the process will have a distinct set of UIDs, GIDs and capabilities.
310
305
# --pid: create a new process namespace (needed fr procfs to work right)
311
306
# --fork: necessary if we do --pid
312
307
# "Creation of a persistent PID namespace will fail if the --fork option is not also specified."
313
308
# shellcheck disable=SC2086 # we want field splitting!
314
- unshare --mount --user --pid --fork $EXTRA_NS " $mount_and_execute "
309
+ unshare -r - -mount --user --pid --fork $EXTRA_NS " $mount_and_execute "
315
310
TRY_EXIT_STATUS=$?
316
311
317
312
# remove symlink
318
313
# first set temproot to be writible, rhel derivatives defaults / to r-xr-xr-x
319
- chmod 755 " ${SANDBOX_DIR} /temproot"
320
- while IFS=" " read -r mountpoint
321
- do
322
- pure_mountpoint=${mountpoint##*: }
323
- if [ -L " $pure_mountpoint " ]
324
- then
325
- rm " ${SANDBOX_DIR} /temproot/${mountpoint} "
326
- fi
327
- done < " $DIRS_AND_MOUNTS "
314
+ # chmod 755 "${SANDBOX_DIR}/temproot"
315
+ # while IFS="" read -r mountpoint
316
+ # do
317
+ # pure_mountpoint=${mountpoint##*:}
318
+ # if [ -L "$pure_mountpoint" ]
319
+ # then
320
+ # rm "${SANDBOX_DIR}/temproot/${mountpoint}"
321
+ # fi
322
+ # done <"$DIRS_AND_MOUNTS"
328
323
329
324
# ###############################################################################
330
325
# commit?
@@ -451,6 +446,10 @@ ignore_changes() {
451
446
grep -v -f " $ignore_file "
452
447
}
453
448
449
+ ignore_devs () {
450
+ grep -v " /dev/"
451
+ }
452
+
454
453
# ###############################################################################
455
454
# # Lists all upperdir changes in raw format
456
455
# ###############################################################################
@@ -459,7 +458,7 @@ find_upperdir_changes() {
459
458
sandbox_dir=" $1 "
460
459
ignore_file=" $2 "
461
460
462
- find " $sandbox_dir /upperdir/" -type f -o \( -type c -size 0 \) -o -type d -o -type l | ignore_changes " $ignore_file "
461
+ find " $sandbox_dir /upperdir/" -type f -o \( -type c -size 0 \) -o -type d -o -type l | ignore_changes " $ignore_file " | ignore_devs
463
462
}
464
463
465
464
# ###############################################################################
0 commit comments