pthbs

Packaging Through Hashed Build Scripts
git clone https://ccx.te2000.cz/git/pthbs
Log | Files | Refs | Submodules | README

pthbs-setup-gen.awk (5432B)


      1 BEGIN {
      2 	settings["sandbox"] = 1
      3 	settings["set_path"] = 1
      4 	FS=":"
      5 	single_quote="'"
      6 	print "#!/bin/sh -e"
      7 	print "if test -n \"$pthbs_xtrace\"; then"
      8 	print "	set -x"
      9 	print "	if test -n \"$BB_ASH_VERSION\"; then PS4=\"+${0##*/}\"" single_quote ":${FUNCNAME}:${LINENO} " single_quote "; fi"
     10 	print "fi"
     11 	print "cd "q(ENVIRON["workdir"])
     12 	if(ENVIRON["pthbs_uid"]) {
     13 		print "export pthbs_uid=" ENVIRON["pthbs_uid"]
     14 	}
     15 	if(ENVIRON["pthbs_gid"]) {
     16 		print "export pthbs_gid=" ENVIRON["pthbs_gid"]
     17 	}
     18 }
     19 
     20 function q(s) {  # quote string for sh
     21 	gsub(single_quote, single_quote "\\" single_quote single_quote, s)
     22 	return single_quote s single_quote
     23 }
     24 
     25 function dirname(s) {  # strip the last path component
     26 	sub("/[^/]*$", "", s)
     27 	return s
     28 }
     29 
     30 function basename(s) {  # strip the last path component
     31 	sub("^.*/$", "", s)
     32 	return s
     33 }
     34 
     35 function fatal(msg) {
     36 	printf "FATAL: pthbs-build: %s %s:%d: \"%s\"\n", msg, FILENAME, FNR, $0 >"/dev/stderr"
     37 	exit 1
     38 }
     39 
     40 function qlink(rel) {
     41 	return q(ENVIRON["pthbs_cache"] "/link/" rel)
     42 }
     43 
     44 function at_git(commit_id, dstdir){
     45 	print "mkdir -p "q(dstdir)
     46 	print "(cd "qlink("git-commit-sha1/"commit_id)" && git archive --format=tar "q(commit_id)" ) | tar --no-same-owner --no-same-permissions -xC "q(dstdir)
     47 }
     48 
     49 function at_untar(extra_opts, hash_type, file_hash, dstdir){
     50 	print "mkdir -p "q(dstdir)
     51 	print "tar -x "extra_opts" -C "q(dstdir)" -f "qlink("file-"hash_type"/"file_hash)
     52 }
     53 
     54 function at_filehash(hash_type, file_hash, dst,    dstdir){
     55 	if(dst ~ /\//) {
     56 		dstdir = dst
     57 		sub("/[^/]*$", "", dstdir)
     58 		print "mkdir -p "q(dstdir)
     59 	}
     60 	print "cp -Lp "qlink("file-"hash_type"/"file_hash)" "q(dst)
     61 }
     62 function sydbox_ro_tree(dirpath) {
     63 	sandbox_cmd=sandbox_cmd " -m " q("allow/read,readdir,chdir+"dirpath"/***")
     64 }
     65 function sydbox_rw_tree(dirpath) {
     66 	sydbox_ro_tree(dirpath)
     67 	sandbox_cmd=sandbox_cmd " -m " q("allow/write,create,delete,rename,symlink,mkdir,chmod,mkfifo+"dirpath"/***")
     68 }
     69 
     70 function sandbox_ns_common(args,    s) {
     71 	if(length(ENVIRON["sandbox_cmd"])) {
     72 		s = ENVIRON["sandbox_cmd"]
     73 	} else {
     74 		s = q(ENVIRON["pthbs_cache"]"/venv/bin/python")" "q(ENVIRON["pthbs_source"]"/sandbox/ns_sandbox.py")
     75 	}
     76 	s = s" "args
     77 	s = s" --versions="q(ENVIRON["pthbs_versions"])
     78 	s = s" --extra-mount=tmpfs:"q(ENVIRON["pthbs_workdir"])
     79 	s = s" --extra-mount=ro_bind:"q(ENVIRON["pthbs_pkgdir"]":"ENVIRON["pthbs_pkgdir"])
     80 	s = s" --extra-mount=rw_bind:"q(ENVIRON["workdir"]":"ENVIRON["workdir"])
     81 	s = s" --extra-mount=rw_bind:"q(ENVIRON["workdir"]"/.tmp:/tmp")
     82 	s = s" -- "q(ENVIRON["pthbs_workdir"]"/root")
     83 	printf "%s\n", "mkdir -p "q(ENVIRON["workdir"]"/.tmp")" "q(ENVIRON["pthbs_workdir"]"/root")
     84 	return s
     85 }
     86 function sandbox(    s) {
     87 	if(!settings["sandbox"]) {
     88 		if(ENVIRON["pthbs_uid"]){
     89 			return "busybox chpst -u \"$pthbs_uid:$pthbs_gid\" --"
     90 		}
     91 		return ""
     92 	}
     93 	if(sandbox_mode == "rootns") {
     94 		s = " --mode=root"
     95 		s = s" --untar="q(ENVIRON["pthbs_source"]"/sandbox/root.tar")
     96 		s = s" --chdir="q(ENVIRON["workdir"])
     97 		return sandbox_ns_common(s)
     98 	} else if(sandbox_mode == "userns") {
     99 		return sandbox_ns_common("--mode=userns")
    100 	} else if(sandbox_mode == "landlock") {
    101 		s = length(ENVIRON["sandbox_cmd"]) ? ENVIRON["sandbox_cmd"] : "syd-lock"
    102 		s = s" -v"
    103 		# R/O dirs
    104 		s = s" -r "q("/bin")
    105 		s = s" -r "q(dirname(ENVIRON["envdir"]))
    106 		# R/O files
    107 		s = s" -r "q("/proc/loadavg")
    108 		s = s" -r "q("/proc/loadavg")
    109 		s = s" -r "q("/etc/passwd")
    110 		s = s" -r "q("/etc/group")
    111 		s = s" -r "q(""ENVIRON["script"])
    112 		# R/W dirs
    113 		s = s" -w "q(ENVIRON["workdir"])
    114 		s = s" -w "q("/tmp")
    115 		s = s" -w "q("/dev")
    116 		s = s" -w "q("/proc")
    117 		return s
    118 	} else if(sandbox_mode == "generic") {
    119 		s = "env"
    120 		s = s" sandbox_pthbs_versions="q(ENVIRON["pthbs_versions"])
    121 		s = s" sandbox_pthbs_workdir="q(ENVIRON["pthbs_workdir"])
    122 		s = s" sandbox_pthbs_pkgdir="q(ENVIRON["pthbs_pkgdir"])
    123 		s = s" sandbox_workdir="q(ENVIRON["workdir"])
    124 		s = s" sandbox_envdir="q(ENVIRON["envdir"])
    125 		return s" "q(ENVIRON["sandbox_cmd"])
    126 	}
    127 	fatal("unrecognized sanbox_mode " sandbox_mode)
    128 }
    129 
    130 /^#!/ { next }
    131 /^#\+/ {
    132 	if($0 == "#+*") {
    133 		settings["sandbox"] = 0
    134 	} else if(!length(ENVIRON["envdir"])) {
    135 		fatal("dependency specified but no envfile:")
    136 	}
    137 	next
    138 }
    139 /^#@/ {
    140 	if($1 == "#@git") {
    141 		if(match($0, "^#@git:[0-9a-f]+:") == 0) {
    142 			fatal("invalid syntax for @git:")
    143 		}
    144 		at_git($2, substr($0, RLENGTH+1))
    145 	} else if($1 == "#@sha256") {
    146 		if(match($0, "^#@sha256:[0-9a-f]+:") == 0) {
    147 			fatal("invalid syntax for @sha256:")
    148 		}
    149 		at_filehash("sha256", $2, substr($0, RLENGTH+1))
    150 	} else if($1 == "#@untar") {
    151 		if(match($0, "^#@untar:[^:]*:sha256:[0-9a-f]+:") == 0) {
    152 			fatal("invalid syntax for @untar:")
    153 		}
    154 		at_untar($2, $3, $4, substr($0, RLENGTH+1))
    155 	} else if($1 == "#@pragma") {
    156 		if($2 == "nosandbox") {
    157 			settings["sandbox"] = 0
    158 		} else if($2 == "nopath") {
    159 			settings["set_path"] = 0
    160 		} else {
    161 			fatal("unrecognized @pragma:")
    162 		}
    163 	} else {
    164 		fatal("unrecognized @command:")
    165 	}
    166 	next
    167 }
    168 /^$/ {
    169 	sandbox_cmd = sandbox()
    170 	if(ENVIRON["pthbs_uid"]) {
    171 		printf "%s\n", "chown -R \"$pthbs_uid:$pthbs_gid\"  "q(ENVIRON["workdir"])
    172 	}
    173 	if(length(ENVIRON["envdir"])){
    174 		cmd="env pthbs_build_environment="q(ENVIRON["envdir"])
    175 		cmd=cmd" "sandbox_cmd
    176 		if(settings["set_path"]) {
    177 			cmd=cmd" "q(ENVIRON["envdir"]"/command/pthbs-enter")
    178 		}
    179 		cmd=cmd" sh -xe "q(ENVIRON["script"])
    180 	} else {
    181 		cmd=sandbox_cmd" sh -xe "q(ENVIRON["script"])
    182 	}
    183 	print "exec >build.log 2>&1 " cmd
    184 	exit 0
    185 }
    186 {
    187 	fatal("unexpected line")
    188 }