import subprocess import sys import os import shutil import time from engine.DiskLib import * from engine.FileSystemLib import * from engine.FileLib import * from engine.NetLib import * # Example usage: #rsync("-a", "-v", "source/", "destination/") def rsync(*args): RSYNC = subprocess.check_output(["which", "rsync"]).decode().strip() if sys.platform == "linux" and sys.maxsize <= 2**32 and RSYNC == "": RSYNC = "/opt/opengnsys/bin/rsync" subprocess.run([RSYNC] + list(args)) def ogCreateFileImage(): SIZEREQUIRED = int(sys.argv[4]) if SIZEREQUIRED < 300000: SIZEREQUIRED = 300000 KERNELVERSION = ".".join([str(int(num)) for num in platform.release().split(".")]) if sys.argv[1] == "CACHE" or sys.argv[1] == "cache": IMGDIR = ogGetParentPath(sys.argv[1], "/" + sys.argv[2]) if sys.argv[3] == "img": IMGEXT = "img" else: IMGEXT = "img.diff" IMGFILE = f"{IMGDIR}/{os.path.basename('/' + sys.argv[2])}.{IMGEXT}" if not os.path.exists(IMGDIR): ogEcho("log session", f" {MSG_HELP_ogMakeDir} \"{sys.argv[1]} {os.path.dirname('/' + sys.argv[2])}.\"") ogMakeDir(sys.argv[1], os.path.dirname('/' + sys.argv[2])) IMGDIR = ogGetParentPath(sys.argv[1], "/" + sys.argv[2]) DIRMOUNT = f"/tmp/{ogGetMountImageDir(sys.argv[2], sys.argv[3])}" os.makedirs(DIRMOUNT, exist_ok=True) LOOPDEVICE = subprocess.run(["losetup", "-f"], capture_output=True, text=True).stdout.strip() if os.path.isfile(IMGFILE): if os.path.isfile(f"{IMGFILE}.ant"): if BACKUP == "true" or BACKUP == "TRUE": ogEcho("log session", f" {MSG_SCRIPTS_FILE_RENAME} \"{IMGFILE}\" -> \"{IMGFILE}.ant\".") shutil.copy2(IMGFILE, f"{IMGFILE}.ant") os.rename(f"{IMGFILE}.torrent", f"{IMGFILE}.torrent.ant") os.remove(f"{IMGFILE}.sum") IMGSIZE = os.path.getsize(IMGFILE) if IMGSIZE < SIZEREQUIRED: ogEcho("log session", f" {MSG_SYNC_RESIZE}") print(f" truncate --size=>{SIZEREQUIRED}k {IMGFILE}") subprocess.run(["truncate", f"--size={SIZEREQUIRED}k", IMGFILE], capture_output=True, text=True) if "ext4 filesystem" in subprocess.run(["file", IMGFILE], capture_output=True, text=True).stdout.lower(): subprocess.run(["losetup", LOOPDEVICE, IMGFILE]) print(f" resize2fs -f {LOOPDEVICE}") subprocess.run(["resize2fs", "-f", LOOPDEVICE], capture_output=True, text=True) else: print(f" ogMountImage {sys.argv[1]} {sys.argv[2]} {sys.argv[3]}") ogMountImage(sys.argv[1], sys.argv[2], sys.argv[3]) print(f" btrfs filesystem resize max {DIRMOUNT}") subprocess.run(["btrfs", "filesystem", "resize", "max", DIRMOUNT], capture_output=True, text=True) else: open(IMGFILE, "w").close() print(f" truncate --size=>{SIZEREQUIRED}k {IMGFILE}") subprocess.run(["truncate", f"--size={SIZEREQUIRED}k", IMGFILE], capture_output=True, text=True) subprocess.run(["losetup", LOOPDEVICE, IMGFILE]) if KERNELVERSION < "3.07": IMGFS = "EXT4" else: IMGFS = os.environ.get("IMGFS", "BTRFS") if IMGFS == "EXT4": print(f" mkfs.ext4 -i 4096 -b 4096 -L {os.path.basename(sys.argv[2])} {LOOPDEVICE}") subprocess.run(["mkfs.ext4", "-i", "4096", "-b", "4096", "-L", os.path.basename(sys.argv[2]), LOOPDEVICE], capture_output=True, text=True) else: print(f" mkfs.btrfs -L {os.path.basename(sys.argv[2])} {LOOPDEVICE}") subprocess.run(["mkfs.btrfs", "-L", os.path.basename(sys.argv[2]), LOOPDEVICE], capture_output=True, text=True) ogMountImage(sys.argv[1], sys.argv[2], sys.argv[3]) if not os.path.exists(IMGFILE + ".lock"): open(IMGFILE + ".lock", "w").write("mounted") if LOOPDEVICE: subprocess.run(["losetup", "-d", LOOPDEVICE], capture_output=True, text=True) else: REPOIP = ogGetRepoIp() print(f" hose {REPOIP} 2009 --out sh -c \"echo -ne CREATE_IMAGE {sys.argv[2]} {sys.argv[3]} {SIZEREQUIRED} \"") subprocess.run(["hose", REPOIP, "2009", "--out", "sh", "-c", f"echo -ne CREATE_IMAGE \"{sys.argv[2]}\" {sys.argv[3]} {SIZEREQUIRED}\""], capture_output=True, text=True) def ogCreateInfoImage(): FUNCNAME = ogCreateInfoImage.__name__ IMGTYPE = None IMGDIRAUX = None DIRMOUNT = None DESTRSYNC = None PASSWORD = None USERRSYNC = None ORIG = None FSTYPE = None PART = None DIREMPTY = None IMGLIST = None IMGINFO = None IMGACL = None KERNELVERSION = None if len(sys.argv) < 5 or (len(sys.argv) < 6 and sys.argv[3] != "img"): ogHelp(FUNCNAME, f"{FUNCNAME} num_disk num_part [ REPO|CACHE ] [ base_image_name ] extension", f"base image -> {FUNCNAME} 1 2 img", f"diff image -> {FUNCNAME} 1 1 CACHE Windows7 diff") return if len(sys.argv) < 3: ogRaiseError(OG_ERR_FORMAT, f"{MSG_FORMAT}: {FUNCNAME} num_disk num_part [ REPO|CACHE ] [ base_image_name] extension") return PART = ogDiskToDev(sys.argv[1], sys.argv[2]) if not PART: return ORIG = ogMount(sys.argv[1], sys.argv[2]) if not ORIG: return if sys.argv[3] == "img": IMGTYPE = "img" else: if not ogCheckStringInGroup(sys.argv[5], "img diff"): ogRaiseError(OG_ERR_FORMAT, MSG_SYNC_EXTENSION) return IMGTYPE = sys.argv[5] if IMGTYPE == "diff": IMGDIRAUX = ogGetMountImageDir(sys.argv[4], "img") if sys.argv[3] == "CACHE" or sys.argv[3] == "cache": DIRMOUNT = f"/tmp/{IMGDIRAUX}" DESTRSYNC = DIRMOUNT else: if not REPOIP: REPOIP = ogGetRepoIp() DIRMOUNT = f"{OGIMG}/{IMGDIRAUX}" USERRSYNC = "opengnsys" PASSWORD = "--password-file=/scripts/passrsync" DESTRSYNC = f"{USERRSYNC}@{REPOIP}::ogimages/{IMGDIRAUX}" FSTYPE = ogGetFsType(sys.argv[1], sys.argv[2]) DIREMPTY = "/tmp/empty$$" IMGLIST = "/tmp/ogimg.list" IMGINFO = "/tmp/ogimg.info" IMGACL = "/tmp/ogimg.acl" os.system(f"rm -f /tmp/ogimg.* 2>/dev/null") os.system(f"rm -f {ORIG}/ogimg.* 2>/dev/null") SIZEDATA = os.environ.get("SIZEDATA", "SIZEDATA") KERNELVERSION = ".".join([str(int(num)) for num in platform.release().split(".")]) if KERNELVERSION < "3.07": IMGFS = "EXT4" else: IMGFS = os.environ.get("IMGFS", "BTRFS") with open(IMGINFO, "w") as f: f.write(f"#{IMGFS}:NO:{FSTYPE}:{SIZEDATA}\n") if IMGTYPE == "img": print(f" rsync -aHAXWvn --delete {ORIG}/ {DIREMPTY} >> {IMGINFO}") subprocess.run(["rsync", "-aHAXWvn", "--delete", f"{ORIG}/", DIREMPTY], stdout=subprocess.PIPE, stderr=subprocess.PIPE) os.system(f"sed -i -e s/\"^sent.*.bytes\\/sec\"//g -e s/^total.*.speedup.*.$//g -e s/\"sending.*.list\"//g {IMGINFO}") os.system(f"sed -i '/^\\.\\//d' {IMGINFO}") else: print(f" rsync -aHAXWvn --delete {ORIG}/ {DESTRSYNC} a {IMGLIST}") subprocess.run(["rsync", "-aHAXWvn", "--delete", f"{ORIG}/", DESTRSYNC], stdout=subprocess.PIPE, stderr=subprocess.PIPE) os.system(f"sed -i -e s/\"^sent.*.bytes\\/sec\"//g -e s/^total.*.speedup.*.$//g -e s/\"sending.*.list\"//g {IMGLIST}") os.system(f"sed -i '/^\\.\\//d' {IMGLIST}") with open(IMGINFO, "a") as f: subprocess.run(["grep", "-e", "\\->", "-e", "\\=>", IMGLIST], stdout=f) subprocess.run(["grep", "-e", "^deleting", IMGLIST], stdout=subprocess.PIPE, stderr=subprocess.PIPE).stdout.decode().replace("deleting ", "").split("\n") subprocess.run(["grep", "-v", "-e", "\\->", "-e", "\\=>", "-e", "^deleting", "-e", "^created", IMGLIST], stdout=f) os.system(f"rm -f {IMGLIST}") if subprocess.run(["grep", "-v", "-e", "^$", "-e", "^#", IMGINFO, "/tmp/ogimg.ln", "/tmp/ogimg.rm"], stdout=subprocess.PIPE, stderr=subprocess.PIPE).stdout.decode().count("\n") == 0: ogRaiseError(OG_ERR_NOTDIFFERENT, " ".join(sys.argv[1:])) return if FSTYPE == "NTFS": print(f" ntfs-3g.secaudit -b {PART} /") subprocess.run(["ntfs-3g.secaudit", "-b", PART, "/"], stdout=subprocess.PIPE, stderr=subprocess.PIPE) def ogAclFilter(): FUNCNAME = ogAclFilter.__name__ IMGACL = "/tmp/ogimg.acl" IMGINFO = "/tmp/ogimg.info" FILES = "/tmp/files$$" ACLTMP = "/tmp/acl$$.tmp" ACLFILES = "/tmp/aclfiles$$" # Ayuda if len(sys.argv) == 2 and sys.argv[1] == "help": ogHelp(FUNCNAME, FUNCNAME) return # comprobamos que existan los archivos de origen. Si no salimos sin error. if not (os.path.isfile(IMGACL) and os.path.isfile(IMGINFO)): return with open(ACLTMP, "w") as f: with open(IMGINFO, "r") as info_file: for line in info_file: line = line.strip() if line.startswith("#") or line == "": continue line_number = line.split(":")[0] acl_lines = [] with open(ACLFILES, "r") as acl_file: acl_lines = acl_file.readlines() end_line, start_line = None, None for i, acl_line in enumerate(acl_lines): acl_line = acl_line.strip() if acl_line == "File" or acl_line == "Directory": if acl_lines[i-1].startswith(line_number): start_line = i if acl_lines[i+1].startswith(line_number): end_line = i break if start_line is not None and end_line is not None: acl_lines = acl_lines[start_line+1:end_line] f.writelines(acl_lines) ogEcho("aclfilter", line) shutil.copy2(ACLTMP, IMGACL) os.remove(FILES) os.remove(ACLTMP) os.remove(ACLFILES) def ogRestoreInfoImage(): FUNCNAME = ogRestoreInfoImage.__name__ DEST = None PART = None IMGACL = "ogimg.acl" IMGLN = "ogimg.ln" IMGINFO = "ogimg.info" # Ayuda o menos de 5 parametros y la imagen no es basica if len(sys.argv) < 3 or (len(sys.argv) < 4 and sys.argv[3] != "img"): ogHelp(FUNCNAME, f"{FUNCNAME} num_disk num_part", f"base image -> {FUNCNAME} 1 2", f"diff image -> {FUNCNAME} 1 1") return PART = ogDiskToDev(sys.argv[1], sys.argv[2]) if not PART: return DEST = ogMount(sys.argv[1], sys.argv[2]) if not DEST: return # Copiamos informacion de la imagen a /tmp (para basicas) if os.path.isfile(f"{DEST}/{IMGINFO}"): shutil.copy2(f"{DEST}/ogimg.*", "/tmp") # Creamos o modificamos los enlaces. # La imagen diferencial tiene ogimg.ln # para la completa lo generamos con los enlaces que contengan /mnt/ if not os.path.isfile(f"/tmp/{IMGLN}"): with open(f"/tmp/{IMGINFO}", "r") as info_file: for line in info_file: line = line.strip() if "->" in line or "=>" in line: if "/mnt/" in line: with open(f"/tmp/{IMGLN}", "a") as ln_file: ln_file.write(line.split(">")[0] + "\n") if os.path.isfile(f"/tmp/{IMGLN}"): with open(f"/tmp/{IMGLN}", "r") as ln_file: for line in ln_file: line = line.strip() ORIGLN = line.split("> ")[1] if "/mnt/" in ORIGLN: ORIGLN = f"{DEST}/{ORIGLN.replace('/mnt/*/', '')}" TYPELN = line.split(" ")[-1] DESTLN = line.split(" ")[0] if TYPELN == "-": OPTLN = "-s" else: OPTLN = "" os.chdir(f"{DEST}/{os.path.dirname(DESTLN)}") os.remove(os.path.basename(DESTLN)) os.symlink(ORIGLN, os.path.basename(DESTLN)) print(".", end="") print("") os.chdir("/") def ogRestoreAclImage(): PART = None IMGACL = "ogimg.acl" if len(sys.argv) < 3 or (len(sys.argv) < 4 and sys.argv[3] != "img"): ogHelp(FUNCNAME, f"{FUNCNAME} num_disk num_part", f"base image -> {FUNCNAME} 1 2", f"diff image -> {FUNCNAME} 1 1") return PART = ogDiskToDev(sys.argv[1], sys.argv[2]) if not PART: return # Restauramos acl if ogGetFsType(sys.argv[1], sys.argv[2]) == "NTFS" and os.path.isfile(f"/tmp/{IMGACL}"): os.chdir("/") ogUnmount(sys.argv[1], sys.argv[2]) print(f" ntfs-3g.secaudit -se {PART} /tmp/{IMGACL}") subprocess.run(["ntfs-3g.secaudit", "-se", PART, f"/tmp/{IMGACL}"], capture_output=True, text=True) # Para evitar que de falso error print("") def ogSyncCreate(): ORIG = ogMount(sys.argv[1], sys.argv[2]) DIRAUX = ogGetMountImageDir(sys.argv[4], sys.argv[5]) DIRMOUNT = f"/tmp/{DIRAUX}" DESTRSYNC = None USERRSYNC = None PASSWORD = None OPTRSYNC = None RETVAL = None if sys.argv[3] == "CACHE" or sys.argv[3] == "cache": DESTRSYNC = DIRMOUNT else: if not REPOIP: REPOIP = ogGetRepoIp() PASSWORD = "--password-file=/scripts/passrsync" if ogrsyncz == "true": OPTRSYNC = "z " if ogrsyncw == "true": OPTRSYNC = f"W{OPTRSYNC}" USERRSYNC = "opengnsys" DESTRSYNC = f"{USERRSYNC}@{REPOIP}::ogimages/{DIRMOUNT}" print(f" rsync -aHAX{OPTRSYNC} --progress --inplace --delete {ORIG}/ {DESTRSYNC}") subprocess.run(["rsync", "-aHAX" + OPTRSYNC, "--progress", "--inplace", "--delete", f"{ORIG}/", DESTRSYNC], stderr=subprocess.PIPE, shell=True) print(f" rsync -aHAX{OPTRSYNC} --inplace /tmp/ogimg* {DESTRSYNC}") subprocess.run(["rsync", "-aHAX" + OPTRSYNC, "--inplace", "/tmp/ogimg*", DESTRSYNC], stderr=subprocess.PIPE, shell=True) return RETVAL def ogSyncRestore(): DIRMOUNT = ogGetMountImageDir(sys.argv[2], sys.argv[3]) DESTRSYNC = ogGetMountPoint(sys.argv[4], sys.argv[5]) # Borramos ficheros de informacion de restauraciones antiguas os.system(f"rm -rf {DESTRSYNC}/ogimg.*") os.system("rm -rf /tmp/ogimg.*") # Origen y destino de la sincronizacion y en REPO opciones rsync if sys.argv[1] == "CACHE" or sys.argv[1] == "cache": ORIG = f"/tmp/{DIRMOUNT}" else: REPOIP = ogGetRepoIp() PASSWORD = "--password-file=/scripts/passrsync" OPTRSYNC = "" if ogrsyncz == "true": OPTRSYNC += "z " if ogrsyncw == "true": OPTRSYNC += "W" + OPTRSYNC USERRSYNC = "opengnsys" ORIG = f"{USERRSYNC}@{REPOIP}::ogimages/{DIRMOUNT}" # Opciones rsync en cache y repo # Para la imagen basica, opcion de borrar archivos de la particion que no existen en la imagen if sys.argv[3] == "img" and ogrsyncdel != "false": OPTRSYNC += "--delete" # Nos traemos listado ficheros y bajamos la imagen ogEcho("log session", f" {MSG_SYNC_RESTORE}") # Si la imagen es diferencial nos traemos los archivos de informacion de la imagen. if sys.argv[3] == "diff": # Lista de archivos a copiar: IMGINFO = "ogimg.info" FILESFROM = f"--files-from=/tmp/{IMGINFO}" print(f" rsync -aHAX{OPTRSYNC} --progress {ORIG}/ogimg* /tmp") subprocess.run(["rsync", "-aHAX" + OPTRSYNC, "--progress", f"{ORIG}/ogimg*", "/tmp"]) # Borramos linea de información de la imagen, sino busca un fichero con ese nombre os.system("sed -i '/^#/d' /tmp/{IMGINFO}") os.chdir(DESTRSYNC) # Diferencial: Borramos archivos sobrantes. ogEcho("log session", f" {MSG_SYNC_DELETE}") os.system(f"sed -e s/^/\"/g -e s/$/\"/g \"/tmp/ogimg.rm\" 2>/dev/null | xargs rm -rf") print(f" rsync -aHAX{OPTRSYNC} --progress {FILESFROM} {ORIG}/ {DESTRSYNC}") subprocess.run(["rsync", "-aHAX" + OPTRSYNC, "--progress", FILESROM, f"{ORIG}/", DESTRSYNC], stderr=subprocess.PIPE, shell=True) RETVAL = subprocess.PIPESTATUS[0] os.chdir("/") def ogMountImage(repo_cache, image_name, extension=None): FUNCNAME = ogMountImage.__name__ if repo_cache == "help": ogHelp(FUNCNAME, f"{FUNCNAME} [ REPO|CACHE ] image_name [ extension ]", f"{FUNCNAME} REPO Ubuntu12", f"{FUNCNAME} CACHE Windows7 diff") return if len(sys.argv) < 2: ogRaiseError(OG_ERR_FORMAT, f"{MSG_FORMAT}: {FUNCNAME} [ REPO|CACHE ] image_name [ extension ]") return if not extension or extension == "img": IMGEXT = "img" else: IMGEXT = "img.diff" DIRMOUNT = ogGetMountImageDir(image_name, IMGEXT.split(".")[1]) if repo_cache == "REPO" or repo_cache == "repo": REPOIP = ogGetRepoIp() print(f" hose {REPOIP} 2009 --out sh -c \"echo -ne MOUNT_IMAGE {image_name} {IMGEXT.split('.')[1]}\"") return f"{OGIMG}/{DIRMOUNT}" else: # Check if already mounted if subprocess.run(["df"], capture_output=True, text=True).stdout.count(f"{DIRMOUNT}\n") > 0: return f"/tmp/{DIRMOUNT}" IMGFILE = ogGetPath(repo_cache, f"/{image_name}.{IMGEXT}") if not IMGFILE: ogRaiseError(OG_ERR_NOTFOUND, f"{repo_cache} {image_name}.{IMGEXT}") return os.makedirs(f"/tmp/{DIRMOUNT}", exist_ok=True) if "ext4 filesystem" in subprocess.run(["file", IMGFILE], capture_output=True, text=True).stdout.lower(): print(f" mount -t ext4 -o loop {IMGFILE} /tmp/{DIRMOUNT}") subprocess.run(["mount", "-t", "ext4", "-o", "loop", IMGFILE, f"/tmp/{DIRMOUNT}"], capture_output=True, text=True) else: print(f" mount -o compress=lzo {IMGFILE} /tmp/{DIRMOUNT}") subprocess.run(["mount", "-o", "compress=lzo", IMGFILE, f"/tmp/{DIRMOUNT}"], capture_output=True, text=True) if subprocess.run(["mount"], capture_output=True, text=True).stdout.count(f"/tmp/{DIRMOUNT}\n") == 0: ogRaiseError(OG_ERR_DONTMOUNT_IMAGE, f"{repo_cache} {image_name} {extension}") return return f"/tmp/{DIRMOUNT}" def ogUnmountImage(): FUNCNAME = ogUnmountImage.__name__ IMGTYPE = None DIRMOUNT = None if len(sys.argv) < 2 or (len(sys.argv) < 3 and sys.argv[2] != "img"): ogHelp(FUNCNAME, f"{FUNCNAME} [ REPO|CACHE ] image_name [ extension ]", f"{FUNCNAME} REPO Ubuntu12", f"{FUNCNAME} CACHE Windows7 diff") return if not sys.argv[3] or sys.argv[3] == "img": IMGTYPE = "img" else: IMGTYPE = sys.argv[3] if sys.argv[1] == "CACHE" or sys.argv[1] == "cache": DIRMOUNT = f"/tmp/{ogGetMountImageDir(sys.argv[2], IMGTYPE)}" subprocess.run(["umount", DIRMOUNT], capture_output=True, text=True) subprocess.run(["rmdir", DIRMOUNT], capture_output=True, text=True) if os.path.exists(f"{IMGFILE}.lock"): os.system(f"sed -i s/\"mounted\"//g {IMGFILE}.lock") else: if not REPOIP: REPOIP = ogGetRepoIp() print(f" hose {REPOIP} 2009 --out sh -c \"echo -ne UMOUNT_IMAGE {sys.argv[2]} {IMGTYPE}\"") subprocess.run(["hose", REPOIP, "2009", "--out", "sh", "-c", f"echo -ne UMOUNT_IMAGE \"{sys.argv[2]}\" {IMGTYPE}\""], capture_output=True, text=True) def ogGetMountImageDir(image_name, extension=None): FUNCNAME = ogGetMountImageDir.__name__ if image_name == "help": ogHelp(FUNCNAME, f"{FUNCNAME} image_name [ extension ]", f"{FUNCNAME} Ubuntu12", f"{FUNCNAME} Windows7 diff") return if len(sys.argv) < 2: ogRaiseError(OG_ERR_FORMAT, f"{MSG_FORMAT}: {FUNCNAME} image_name [ extension ]") return DIRMOUNT = f"mount/{image_name}" if extension == "diff": DIRMOUNT = f"{DIRMOUNT}.diff" return DIRMOUNT def ogWaitSyncImage(): SIZE = int(sys.argv[5]) if len(sys.argv) >= 6 else 300000 STATE = sys.argv[4] ogCheckStringInGroup(STATE, "mounted reduced") or return ogRaiseError(OG_ERR_FORMAT, "STATE = [ mounted | reduced ]") IMGDIR = ogGetParentPath(sys.argv[1], f"/{sys.argv[2]}") IMGEXT = "img" if sys.argv[3] == "img" else "img.diff" LOCKFILE = f"{IMGDIR}/{os.path.basename(f'/{sys.argv[2]}')}.{IMGEXT}.lock" if sys.argv[1] == "CACHE" or sys.argv[1] == "cache": DIRMOUNT = f"/tmp/{ogGetMountImageDir(sys.argv[2], sys.argv[3])}" else: DIRMOUNT = f"{OGIMG}/{ogGetMountImageDir(sys.argv[2], sys.argv[3])}" print(f" {MSG_SYNC_SLEEP}: {DIRMOUNT}") print(" #") TIMEOUT = SIZE // CREATESPEED if TIMEOUT < 60: TIMEOUT = 60 while True: if STATE == "mounted" and os.path.isfile(f"{DIRMOUNT}/ogimg.info"): ogEcho("log session", "") return 0 TIMEAUX = SECONDS - TIME if TIMEAUX >= TIMEOUT: return ogRaiseError(OG_ERR_DONTMOUNT_IMAGE, f"{sys.argv[3]} {sys.argv[4]} {IMGEXT}: time_out.") print("#") time.sleep(5) print("") def ogReduceImage(): FUNCNAME = ogReduceImage.__name__ IMGEXT = None DIRMOUNT = None AVAILABLE = None USED = None IMGDIR = None IMGFILE = None ENDSIZE = None LOOPDEVICE = None if len(sys.argv) < 2 or (len(sys.argv) < 3 and sys.argv[3] != "img"): ogHelp(FUNCNAME, f"{FUNCNAME} [ REPO|CACHE ] image_name [ extension ]", f"{FUNCNAME} REPO Ubuntu12", f"{FUNCNAME} CACHE Windows7 diff") return if not sys.argv[3] or sys.argv[3] == "img": IMGEXT = "img" else: IMGEXT = sys.argv[3] IMGDIR = ogGetParentPath(sys.argv[1], f"/{sys.argv[2]}") IMGFILE = f"{IMGDIR}/{os.path.basename(f'/{sys.argv[2]}')}.{IMGEXT}" if sys.argv[1] == "CACHE" or sys.argv[1] == "cache": if "ext4 filesystem" in subprocess.run(["file", IMGFILE], capture_output=True, text=True).stdout.lower(): DIRMOUNT = ogMountImage(sys.argv[1], sys.argv[2], IMGEXT.split(".")[1]) AVAILABLE = int(subprocess.run(["df", "-k"], capture_output=True, text=True).stdout.split(f"{DIRMOUNT}\n")[1].split()[3]) if AVAILABLE < 200000: ogUnmountImage(sys.argv[1], sys.argv[2], IMGEXT.split(".")[1]) os.system(f"echo \"reduced\" > \"{IMGFILE}.lock\"") return 0 EXTSIZE = int(subprocess.run(["ls", "-l", "--block-size=1024", IMGFILE], capture_output=True, text=True).stdout.split()[4]) INTSIZE = int(subprocess.run(["df", "-k"], capture_output=True, text=True).stdout.split(f"{DIRMOUNT}\n")[1].split()[1]) EDGESIZE = EXTSIZE - INTSIZE ogUnmountImage(sys.argv[1], sys.argv[2], IMGEXT.split(".")[1]) LOOPDEVICE = subprocess.run(["losetup", "-f"], capture_output=True, text=True).stdout.strip() os.system(f"losetup {LOOPDEVICE} \"{IMGFILE}\"") os.system(f"resize2fs -fpM {LOOPDEVICE}") ogMountImage(sys.argv[1], sys.argv[2], IMGEXT.split(".")[1]) INTSIZE = int(subprocess.run(["df", "-k"], capture_output=True, text=True).stdout.split(f"{DIRMOUNT}\n")[1].split()[1]) EXTSIZE = INTSIZE + EDGESIZE os.system(f"umount \"{DIRMOUNT}\"") if LOOPDEVICE: os.system(f"losetup -d {LOOPDEVICE}") os.system(f"truncate --size=\"{EXTSIZE}\"k \"{IMGFILE}\"") else: os.system(f"umount \"{DIRMOUNT}\"") os.system(f"echo \"reduced\" > \"{IMGFILE}.lock\"") os.system(f"rmdir \"{DIRMOUNT}\"") def ogIsSyncImage(): FUNCNAME = ogIsSyncImage.__name__ IMGEXT = None IMGDIR = None IMGFILE = None if len(sys.argv) < 2 or (len(sys.argv) < 3 and sys.argv[3] != "img"): ogHelp(FUNCNAME, f"{FUNCNAME} [ REPO|CACHE ] image_name [ extension ]", f"{FUNCNAME} REPO Ubuntu12", f"{FUNCNAME} CACHE Windows7 diff") return if not sys.argv[3] or sys.argv[3] == "img": IMGEXT = "img" else: IMGEXT = sys.argv[3] IMGDIR = ogGetParentPath(sys.argv[1], f"/{sys.argv[2]}") IMGFILE = f"{IMGDIR}/{os.path.basename(f'/{sys.argv[2]}')}.{IMGEXT}" if "BTRFS Filesystem" in subprocess.run(["file", IMGFILE], capture_output=True, text=True).stdout.lower() or "ext4 filesystem" in subprocess.run(["file", IMGFILE], capture_output=True, text=True).stdout.lower(): return 0 else: return OG_ERR_DONTSYNC_IMAGE def ogCheckSyncImage(): FUNCNAME = ogCheckSyncImage.__name__ IMGEXT = None IMGDIR = None IMGFILE = None DIRMOUNT = None ISMOUNT = None RETVAL = None if len(sys.argv) < 2 or (len(sys.argv) < 3 and sys.argv[3] != "img"): ogHelp(FUNCNAME, f"{FUNCNAME} [ REPO|CACHE ] image_name [ extension ]", f"{FUNCNAME} REPO Ubuntu12", f"{FUNCNAME} CACHE Windows7 diff") return if not sys.argv[3] or sys.argv[3] == "img": IMGEXT = "img" else: IMGEXT = sys.argv[3] IMGDIR = ogGetParentPath(sys.argv[1], f"/{sys.argv[2]}") IMGFILE = f"{IMGDIR}/{os.path.basename(f'/{sys.argv[2]}')}.{IMGEXT}" if "ext4 filesystem" in subprocess.run(["file", IMGFILE], capture_output=True, text=True).stdout.lower(): DIRMOUNT = f"/tmp/ogCheckImage$$" os.makedirs(DIRMOUNT, exist_ok=True) subprocess.run(["mount", "-t", "ext4", "-o", "loop", IMGFILE, DIRMOUNT], capture_output=True, text=True) RETVAL = subprocess.PIPESTATUS[0] else: DIRMOUNT = f"/tmp/ogCheckImage$$" os.makedirs(DIRMOUNT, exist_ok=True) subprocess.run(["mount", "-o", "compress=lzo", IMGFILE, DIRMOUNT], capture_output=True, text=True) RETVAL = subprocess.PIPESTATUS[0] print("\n".join(os.listdir(DIRMOUNT))) subprocess.run(["umount", DIRMOUNT], capture_output=True, text=True) os.rmdir(DIRMOUNT) return RETVAL