#!/usr/bin/env python3
# BootStrapBot (lol)
# BuildSystemBot
# BullShitBot :P
import os
import sys
from time import strftime
import subprocess
from subprocess import DEVNULL, PIPE, STDOUT
class Return:
def __init__(self, rv, out=None):
self.rv = rv
self.out = out
def __bool__(self):
return self.rv == 0
def __int__(self):
return self.rv
def __str__(self):
if self.out:
return self.out
return str(self.rv)
def sub(*args, **kwargs):
c = subprocess.run(*args, **kwargs)
return Return(c.returncode, c.stdout)
def subc(*args, **kwargs):
c = subprocess.run(*args, **kwargs)
if c.returncode != 0:
print("subprocess failed: ", args)
print("code:", c.returncode)
sys.exit(1)
return Return(c.returncode, c.stdout)
def subtea(cmds, log):
if not isinstance(cmds[0], list):
cmds = [cmds]
teecmd = ["tee", log ]
for cmd in cmds:
proc = subprocess.Popen(cmd, stdin=DEVNULL, stderr=STDOUT, stdout=PIPE)
tee = subprocess.Popen(teecmd, stdin=proc.stdout)
r1 = proc.wait()
tee.wait()
if r1:
print("subprocess failed: ", cmd)
print("code:", r1)
sys.exit(1)
teecmd = ["tee", "-a", log ]
if len(sys.argv) != 2:
print(f"Usage: {sys.argv[0]} <list|directory>")
sys.exit(0)
try:
with open(sys.argv[1], 'r') as pkgf:
pkgs = pkgf.readlines()
except IsADirectoryError:
pkgs = [ sys.argv[1] ]
basedir = os.getcwd()
with open("pre-rm-pkg", 'r') as f:
pre_rm_list = [ x.strip() for x in f.readlines() ]
print(pre_rm_list)
def pre_rm(pkg):
if pkg not in pre_rm_list:
return
print("Performing pre-remove")
cmd = [ "pacman", "-Rdd", "--noconfirm", pkg ]
x = sub(cmd, stdin=DEVNULL, stderr=STDOUT, stdout=DEVNULL)
print(f"Result: {str(x)}")
is_64bits = sys.maxsize > 2**32
chost = "aarch64" if is_64bits else "armv7h"
bspkg = f"/sources/pkg/{chost}/bootstrap"
try:
os.stat(bspkg)
except FileNotFoundError:
bspkg = f"/sources/pkg/{chost}/core"
def pkgbuild_check_sums():
with open('PKGBUILD', 'r') as f:
for line in f:
if 'sums=' in line:
return True
sumcmd = [ "su", "builder", "-c", "makepkg -g >> PKGBUILD" ]
subc(sumcmd)
logdir = strftime("logs-%y%m%d-%H%M%S")
os.mkdir(logdir)
for pkgline in pkgs:
p_l = pkgline.rstrip().split(' ',maxsplit=1)
pkg = p_l[0]
if len(p_l) > 1:
line = " " + p_l[1] + "=1"
ll = "-" + p_l[1]
else:
line = ""
ll = ""
os.chdir(basedir)
subc(["chown", "-R", "builder:builder", pkg])
print(f"{strftime('%H:%M:%S')} Build {pkg}{line}")
pre_rm(pkg)
logfn = logdir + '/' + pkg + ll + ".log"
with open(logfn, "w") as lf:
os.chdir(pkg)
pkgbuild_check_sums()
makepkg = "makepkg -C --holdver" + line
bcmd = [ "su", "builder", "-c", makepkg ]
print(f"Building (log: '{logfn}')..")
bres = sub(bcmd, stdin=DEVNULL, stderr=STDOUT, stdout=lf)
if not bres:
os.chdir(basedir)
print(f"Build {pkg} failed. Tail:")
sub(["tail", "-n", "100", logfn])
print(f"Tail over. Build {pkg} failed.")
sys.exit(1)
print("Done. Packaging..")
repo_pkgs = []
pacu_pkgs = []
with os.scandir() as it:
for e in it:
if e.name.endswith('.pkg.tar.xz') and e.is_file():
if "-debug-" not in e.name and "-dbginfo-" not in e.name:
pacu_pkgs.append(e.name)
repo_pkgs.append(e.name)
# Do a single pacman-U call so that inter-pkg dependencies are resolved
if len(pacu_pkgs):
#subc(["pacman", "-Udd", "--noconfirm", '--overwrite', '*'] + pacu_pkgs)
subc(["pacman", "-U", "--noconfirm"] + pacu_pkgs)
for rp in repo_pkgs:
subc(["mv", rp, bspkg + '/'])
os.chdir(bspkg)
for rp in repo_pkgs:
subc(["repo-add", "-R", "core.db.tar.gz", rp])
print("Done.")