1*33f37583SAndroid Build Coastguard Worker#!/usr/bin/env python3 2*33f37583SAndroid Build Coastguard Worker 3*33f37583SAndroid Build Coastguard Worker"""This is a wrapper function of apexer. It provides opportunity to do 4*33f37583SAndroid Build Coastguard Workersome artifact preprocessing before calling into apexer. Some of these 5*33f37583SAndroid Build Coastguard Workerartifact preprocessing are difficult or impossible to do in soong or 6*33f37583SAndroid Build Coastguard Workerbazel such as placing native shared libs in DCLA. It is better to do 7*33f37583SAndroid Build Coastguard Workerthese in a binary so that the DCLA preprocessing logic can be reused 8*33f37583SAndroid Build Coastguard Workerregardless of the build system 9*33f37583SAndroid Build Coastguard Worker""" 10*33f37583SAndroid Build Coastguard Worker 11*33f37583SAndroid Build Coastguard Workerimport argparse 12*33f37583SAndroid Build Coastguard Workerfrom glob import glob 13*33f37583SAndroid Build Coastguard Workerimport os 14*33f37583SAndroid Build Coastguard Workerimport shutil 15*33f37583SAndroid Build Coastguard Workerimport sys 16*33f37583SAndroid Build Coastguard Workerimport tempfile 17*33f37583SAndroid Build Coastguard Worker 18*33f37583SAndroid Build Coastguard Workerimport apexer_wrapper_utils 19*33f37583SAndroid Build Coastguard Worker 20*33f37583SAndroid Build Coastguard Workerdef ParseArgs(argv): 21*33f37583SAndroid Build Coastguard Worker parser = argparse.ArgumentParser( 22*33f37583SAndroid Build Coastguard Worker description='wrapper to run apexer for DCLA') 23*33f37583SAndroid Build Coastguard Worker parser.add_argument( 24*33f37583SAndroid Build Coastguard Worker '--apexer', 25*33f37583SAndroid Build Coastguard Worker help='path to apexer binary') 26*33f37583SAndroid Build Coastguard Worker parser.add_argument( 27*33f37583SAndroid Build Coastguard Worker '--canned_fs_config', 28*33f37583SAndroid Build Coastguard Worker help='path to canned_fs_config file') 29*33f37583SAndroid Build Coastguard Worker parser.add_argument( 30*33f37583SAndroid Build Coastguard Worker 'input_dir', 31*33f37583SAndroid Build Coastguard Worker metavar='INPUT_DIR', 32*33f37583SAndroid Build Coastguard Worker help='the directory having files to be packaged') 33*33f37583SAndroid Build Coastguard Worker parser.add_argument( 34*33f37583SAndroid Build Coastguard Worker 'output', 35*33f37583SAndroid Build Coastguard Worker metavar='OUTPUT', 36*33f37583SAndroid Build Coastguard Worker help='name of the APEX file') 37*33f37583SAndroid Build Coastguard Worker parser.add_argument( 38*33f37583SAndroid Build Coastguard Worker 'rest_args', 39*33f37583SAndroid Build Coastguard Worker nargs='*', 40*33f37583SAndroid Build Coastguard Worker help='remaining flags that will be passed as-is to apexer') 41*33f37583SAndroid Build Coastguard Worker return parser.parse_args(argv) 42*33f37583SAndroid Build Coastguard Worker 43*33f37583SAndroid Build Coastguard Workerdef PlaceDCLANativeSharedLibs(image_dir: str, canned_fs_config: str) -> str: 44*33f37583SAndroid Build Coastguard Worker """Place native shared libs for DCLA in a special way. 45*33f37583SAndroid Build Coastguard Worker 46*33f37583SAndroid Build Coastguard Worker Traditional apex has native shared libs placed under /lib(64)? inside 47*33f37583SAndroid Build Coastguard Worker the apex. However, for DCLA, it needs to be placed in a special way: 48*33f37583SAndroid Build Coastguard Worker 49*33f37583SAndroid Build Coastguard Worker /lib(64)?/foo.so/<sha512 foo.so>/foo.so 50*33f37583SAndroid Build Coastguard Worker 51*33f37583SAndroid Build Coastguard Worker This function moves the shared libs to desired location and update 52*33f37583SAndroid Build Coastguard Worker canned_fs_config file accordingly 53*33f37583SAndroid Build Coastguard Worker """ 54*33f37583SAndroid Build Coastguard Worker 55*33f37583SAndroid Build Coastguard Worker # remove all .so entries from canned_fs_config 56*33f37583SAndroid Build Coastguard Worker parent_dir = os.path.dirname(canned_fs_config) 57*33f37583SAndroid Build Coastguard Worker updated_canned_fs_config = os.path.join(parent_dir, 'updated_canned_fs_config') 58*33f37583SAndroid Build Coastguard Worker with open(canned_fs_config, 'r') as f: 59*33f37583SAndroid Build Coastguard Worker lines = f.readlines() 60*33f37583SAndroid Build Coastguard Worker with open(updated_canned_fs_config, 'w') as f: 61*33f37583SAndroid Build Coastguard Worker for line in lines: 62*33f37583SAndroid Build Coastguard Worker segs = line.split(' ') 63*33f37583SAndroid Build Coastguard Worker if not segs[0].endswith('.so'): 64*33f37583SAndroid Build Coastguard Worker f.write(line) 65*33f37583SAndroid Build Coastguard Worker else: 66*33f37583SAndroid Build Coastguard Worker with tempfile.TemporaryDirectory() as tmp_dir: 67*33f37583SAndroid Build Coastguard Worker # move native libs 68*33f37583SAndroid Build Coastguard Worker lib_file = os.path.join(image_dir, segs[0][1:]) 69*33f37583SAndroid Build Coastguard Worker digest = apexer_wrapper_utils.GetDigest(lib_file) 70*33f37583SAndroid Build Coastguard Worker lib_name = os.path.basename(lib_file) 71*33f37583SAndroid Build Coastguard Worker dest_dir = os.path.join(lib_file, digest) 72*33f37583SAndroid Build Coastguard Worker 73*33f37583SAndroid Build Coastguard Worker shutil.move(lib_file, os.path.join(tmp_dir, lib_name)) 74*33f37583SAndroid Build Coastguard Worker os.makedirs(dest_dir, exist_ok=True) 75*33f37583SAndroid Build Coastguard Worker shutil.move(os.path.join(tmp_dir, lib_name), 76*33f37583SAndroid Build Coastguard Worker os.path.join(dest_dir, lib_name)) 77*33f37583SAndroid Build Coastguard Worker 78*33f37583SAndroid Build Coastguard Worker # add canned_fs_config entries 79*33f37583SAndroid Build Coastguard Worker f.write(f'{segs[0]} 0 2000 0755\n') 80*33f37583SAndroid Build Coastguard Worker f.write(f'{os.path.join(segs[0], digest)} 0 2000 0755\n') 81*33f37583SAndroid Build Coastguard Worker f.write(f'{os.path.join(segs[0], digest, lib_name)} 1000 1000 0644\n') 82*33f37583SAndroid Build Coastguard Worker 83*33f37583SAndroid Build Coastguard Worker # return the modified canned_fs_config 84*33f37583SAndroid Build Coastguard Worker return updated_canned_fs_config 85*33f37583SAndroid Build Coastguard Worker 86*33f37583SAndroid Build Coastguard Workerdef main(argv): 87*33f37583SAndroid Build Coastguard Worker args = ParseArgs(argv) 88*33f37583SAndroid Build Coastguard Worker args.canned_fs_config = PlaceDCLANativeSharedLibs( 89*33f37583SAndroid Build Coastguard Worker args.input_dir, args.canned_fs_config) 90*33f37583SAndroid Build Coastguard Worker 91*33f37583SAndroid Build Coastguard Worker cmd = [args.apexer, '--canned_fs_config', args.canned_fs_config] 92*33f37583SAndroid Build Coastguard Worker cmd.extend(args.rest_args) 93*33f37583SAndroid Build Coastguard Worker cmd.extend([args.input_dir, args.output]) 94*33f37583SAndroid Build Coastguard Worker 95*33f37583SAndroid Build Coastguard Worker apexer_wrapper_utils.RunCommand(cmd) 96*33f37583SAndroid Build Coastguard Worker 97*33f37583SAndroid Build Coastguard Workerif __name__ == "__main__": 98*33f37583SAndroid Build Coastguard Worker main(sys.argv[1:]) 99