Beispiel #1
0
    def _do_inject_ssh_key(self):
        """
        Inject ssh key into the mounted virtual hard drive
        """
        logger.info("Injecting ssh key")
        source_file = os.path.join(self._MODULE_DATA_PATH,
                                   self._HARNESS_AUTHORIZED_KEYS_FILE)

        ssh_path = os.path.join(
            os.curdir,
            self._MOUNT_DIRECTORY, "home", "root", ".ssh")

        ssh_file = os.path.join(ssh_path, "authorized_keys")

        logger.info("Injecting ssh key from '" + source_file + "' to '" +
                     ssh_file + "'")

        common.make_directory(ssh_path)
        shutil.copy(source_file, ssh_file)

        sha1sum = misc.local_execute(("sha1sum " +
                ssh_file).split())

        sha1sum = sha1sum.split()[0] # discard the file path

        logger.info("Adding IMA attribute to the ssh-key")

        # The setfattr command requires root privileges to run, and in general
        # we would like to run AFT without root privileges. However, we can add
        # a shell script to the sudoers file, which allows us to invoke it with
        # sudo, without the whole program requiring sudo. Hence, the below commands
        # will succeed even without root privileges.

        # The script also validates that the ssh_file path is at least somewhat
        # sane. This should be taken account if file or directory names are
        # changed

        # Note: Assumes that this file is under aft/devices, and that the shell
        # script is under aft/tools
        setfattr_script = os.path.join(os.path.dirname(__file__), os.path.pardir,
                                     "tools", "setfattr_script.sh")

        misc.local_execute(
            [
                "sudo",
                setfattr_script,
                "0x01" + sha1sum + " ",
                ssh_file
            ])


        logger.info("Fixing ownership and permissions")
        # ensure .ssh directory and authorized key file is owned by root
        os.chown(ssh_path, 0, 0)
        os.chown(ssh_file, 0, 0)

        # and ensure the permissions are correct
        # Note: incompatibility with Python 3 in chmod octal numbers
        os.chmod(ssh_path, 0700)
        os.chmod(ssh_file, 0600)
Beispiel #2
0
    def _mount_local(self, file_name_no_extension):
        """
        Mount a image-file to a class-defined folder.

        Aborts if the mount command fails.

        Args:
            file_name_no_extension (str):
                The file name of the image that will be flashed on the device

        Returns:
            None
        """
        logger.info(
            "Mounting the root partition for ssh-key and USB-networking " +
            "service injection.")
        try:
            common.make_directory(self._LOCAL_MOUNT_DIR)

            root_file_system_file = file_name_no_extension + "." + \
                self._root_extension

            # guestmount allows us to mount the image without root privileges
            subprocess32.check_call(
                ["guestmount", "-a", root_file_system_file, "-m", "/dev/sda", self._LOCAL_MOUNT_DIR])
        except subprocess32.CalledProcessError as err:
            logger.info("Failed to mount.")
            common.log_subprocess32_error_and_abort(err)
Beispiel #3
0
    def _mount_local(self, file_name_no_extension):
        """
        Mount a image-file to a class-defined folder.
        Aborts if the mount command fails.

        Args:
            file_name_no_extension (str):
                The file name of the image that will be flashed on the device

        Returns:
            None
        """
        logger.info(
            "Mounting the root partition for ssh-key and USB-networking " +
            "service injection.")
        try:
            common.make_directory(self._LOCAL_MOUNT_DIR)

            root_file_system_file = file_name_no_extension + "." + \
                self._root_extension

            subprocess32.check_call(
                ["mount", root_file_system_file, self._LOCAL_MOUNT_DIR])

        except subprocess32.CalledProcessError as err:
            logger.info("Failed to mount.")
            common.log_subprocess32_error_and_abort(err)
Beispiel #4
0
    def _prepare_support_fs(self, root_tarball):
        """
        Create directories and copy all the necessary files to the support fs
        working directory.

        This is done before booting the support image, as the rootfs might be
        read only when accessed through nfs

        Args:
            root_tarball:
                The name of the root fs tarball

        Returns:
            None
        """
        # Note: need to remove the first '/' from file paths when building
        # absolute paths on the testing harness, as these paths are
        # absolute path intended for the support image operations (e.g. /usr/foo
        # rather than usr/foo, when we want to build
        # /path/to/nfs/path/to/rootfs/usr/foo)
        #
        # The need to remove the '/' is due to os.path.join behaviour, where it
        # will discard the current path string when encourtering an absolute
        # path

        logger.info("Creating directories and copying image files")

        local_execute([
            "mount", "-o", "loop,offset=1048576",
            "/root/support_image/support.img", "/root/support_fs/beaglebone/"
        ])

        common.make_directory(
            os.path.join(self.nfs_path, self.working_directory[1:]))
        common.make_directory(os.path.join(self.nfs_path, self.mount_dir[1:]))
        shutil.copy(os.path.join(self.parameters["mlo_file"]),
                    os.path.join(self.nfs_path, self.mlo_file[1:]))
        shutil.copy(os.path.join(self.parameters["u-boot_file"]),
                    os.path.join(self.nfs_path, self.u_boot_file[1:]))

        if "tar.bz2" in root_tarball:
            logger.info("Using command line arg for root tarball")
            shutil.copy(os.path.join(root_tarball),
                        os.path.join(self.nfs_path, self.root_tarball[1:]))
        else:
            logger.info("No tarball name passed - using default value")
            shutil.copy(self.parameters["root_tarball"],
                        os.path.join(self.nfs_path, self.root_tarball[1:]))

        shutil.copy(os.path.join(self.parameters["dtb_file"]),
                    os.path.join(self.nfs_path, self.dtb_file[1:]))
        ssh_file = os.path.join(os.path.dirname(__file__), 'data',
                                "authorized_keys")
        shutil.copy(ssh_file, os.path.join(self.nfs_path, self.ssh_file[1:]))

        local_execute(["umount", "/root/support_fs/beaglebone"])
Beispiel #5
0
    def _prepare_support_fs(self, image_directory):
        """
        Create directories and copy all the necessary files to the support fs
        working directory.

        This is done before booting the support image, as the rootfs might be
        read only when accessed through nfs

        Args:
            image_directory:
                The directory where all the necessary files are stored

        Returns:
            None
        """

        # Note: need to remove the first '/' from file paths when building
        # absolute paths on the testing harness, as these paths are
        # absolute path intended for the support image operations (e.g. /usr/foo
        # rather than usr/foo, when we want to build
        # /path/to/nfs/path/to/rootfs/usr/foo)
        #
        # The need to remove the '/' is due to os.path.join behaviour, where it
        # will discard the current path string when encourtering an absolute
        # path

        logging.info("Creating directories and copying image files")

        common.make_directory(
            os.path.join(self.nfs_path, self.working_directory[1:]))

        common.make_directory(os.path.join(self.nfs_path, self.mount_dir[1:]))

        shutil.copy(os.path.join(image_directory, self.parameters["mlo_file"]),
                    os.path.join(self.nfs_path, self.mlo_file[1:]))

        shutil.copy(
            os.path.join(image_directory, self.parameters["u-boot_file"]),
            os.path.join(self.nfs_path, self.u_boot_file[1:]))

        shutil.copy(
            os.path.join(image_directory, self.parameters["root_tarball"]),
            os.path.join(self.nfs_path, self.root_tarball[1:]))

        shutil.copy(os.path.join(image_directory, self.parameters["dtb_file"]),
                    os.path.join(self.nfs_path, self.dtb_file[1:]))

        ssh_file = os.path.join(os.path.dirname(__file__), 'data',
                                "authorized_keys")

        shutil.copy(ssh_file, os.path.join(self.nfs_path, self.ssh_file[1:]))
Beispiel #6
0
    def _mount_virtual_drive(self):
        """
        Mount the VirtualBox virtual hard drive
        """
        # create mount folder
        common.make_directory(self._MOUNT_DIRECTORY)

        path = os.path.join(
            self._VM_DIRECTORY, self._vm_name,
            self._vhdd);
        logger.info("Mounting '" + path + "' with device '" + self._ROOTFS_DEVICE +
            "' into '" + self._MOUNT_DIRECTORY + "' for ssh key injection")

        misc.local_execute(
            ("guestmount -a " + path +" -m " + self._ROOTFS_DEVICE + " " +
             self._MOUNT_DIRECTORY + " -o allow_other").split())
Beispiel #7
0
    def _add_ssh_key(self):
        """
        Inject the ssh-key to DUT's authorized_keys

        Returns:
            None
        """
        logger.info("Injecting ssh-key.")
        source_file = os.path.join(self._MODULE_DATA_PATH,
                                   self._HARNESS_AUTHORIZED_KEYS_FILE)
        ssh_directory = os.path.join(os.curdir, self._LOCAL_MOUNT_DIR, "home",
                                     "root", ".ssh")
        authorized_keys_file = os.path.join(os.curdir, ssh_directory,
                                            "authorized_keys")
        common.make_directory(ssh_directory)
        shutil.copy(source_file, authorized_keys_file)
        os.chown(ssh_directory, 0, 0)
        os.chown(authorized_keys_file, 0, 0)
        os.chmod(ssh_directory, 0o700)
        os.chmod(authorized_keys_file, 0o600)
Beispiel #8
0
    def _add_ssh_key(self):
        """
        Inject the ssh-key to DUT's authorized_keys

        Returns:
            None
        """
        logger.info("Injecting ssh-key.")
        source_file = os.path.join(self._MODULE_DATA_PATH,
                                   self._HARNESS_AUTHORIZED_KEYS_FILE)
        ssh_directory = os.path.join(os.curdir,
                                     self._LOCAL_MOUNT_DIR,
                                     "home", "root", ".ssh")
        authorized_keys_file = os.path.join(os.curdir,
                                            ssh_directory,
                                            "authorized_keys")
        common.make_directory(ssh_directory)
        shutil.copy(source_file, authorized_keys_file)
        os.chown(ssh_directory, 0, 0)
        os.chown(authorized_keys_file, 0, 0)
        # Note: incompatibility with Python 3 in chmod octal numbers
        os.chmod(ssh_directory, 0700)
        os.chmod(authorized_keys_file, 0600)
Beispiel #9
0
    def _prepare_support_fs(self, image_directory):
        """
        Create directories and copy all the necessary files to the support fs
        working directory.

        This is done before booting the support image, as the rootfs might be
        read only when accessed through nfs

        Args:
            image_directory:
                The directory where all the necessary files are stored

        Returns:
            None
        """



        # Note: need to remove the first '/' from file paths when building
        # absolute paths on the testing harness, as these paths are
        # absolute path intended for the support image operations (e.g. /usr/foo
        # rather than usr/foo, when we want to build
        # /path/to/nfs/path/to/rootfs/usr/foo)
        #
        # The need to remove the '/' is due to os.path.join behaviour, where it
        # will discard the current path string when encourtering an absolute
        # path

        logging.info("Creating directories and copying image files")

        common.make_directory(os.path.join(
            self.nfs_path,
            self.working_directory[1:]))

        common.make_directory(
            os.path.join(
                self.nfs_path, self.mount_dir[1:]))

        shutil.copy(
            os.path.join(image_directory, self.parameters["mlo_file"]),
            os.path.join(self.nfs_path, self.mlo_file[1:]))

        shutil.copy(
            os.path.join(image_directory, self.parameters["u-boot_file"]),
            os.path.join(self.nfs_path, self.u_boot_file[1:]))

        shutil.copy(
            os.path.join(image_directory, self.parameters["root_tarball"]),
            os.path.join(self.nfs_path, self.root_tarball[1:]))

        shutil.copy(
            os.path.join(image_directory, self.parameters["dtb_file"]),
            os.path.join(self.nfs_path, self.dtb_file[1:]))

        ssh_file = os.path.join(
            os.path.dirname(__file__),
            'data',
            "authorized_keys")

        shutil.copy(
            ssh_file,
            os.path.join(self.nfs_path, self.ssh_file[1:]))
Beispiel #10
0
    def _add_usb_networking(self):
        """
        Inject USB-networking service files

        Returns:
            None
        """
        logger.info("Injecting USB-networking service.")
        source_file = os.path.join(self._MODULE_DATA_PATH,
                                   self._DUT_USB_SERVICE_FILE)
        target_file = os.path.join(os.curdir,
                                   self._LOCAL_MOUNT_DIR,
                                   self._DUT_USB_SERVICE_LOCATION,
                                   self._DUT_USB_SERVICE_FILE)
        shutil.copy(source_file, target_file)

        # Copy UID and GID
        source_stat = os.stat(source_file)
        os.chown(target_file, source_stat.st_uid, source_stat.st_gid)

        # Set symlink to start the service at the end of boot
        try:
            os.symlink(os.path.join(os.sep,
                                    self._DUT_USB_SERVICE_LOCATION,
                                    self._DUT_USB_SERVICE_FILE),
                       os.path.join(os.curdir,
                                    self._LOCAL_MOUNT_DIR,
                                    self._DUT_USB_SERVICE_LOCATION,
                                    "multi-user.target.wants",
                                    self._DUT_USB_SERVICE_FILE))
        except OSError as err:
            if err.errno == 17:
                logger.critical(
                    "The image file was not replaced. USB-networking service " +
                     "already exists.")
                print("The image file was not replaced! The symlink for "
                    "usb-networking service already exists.")

                # print "Aborting."
                # sys.exit(1)
            else:
                raise err

        # Create the service configuration file
        config_directory = os.path.join(os.curdir,
                                        self._LOCAL_MOUNT_DIR,
                                        self._DUT_USB_SERVICE_CONFIG_DIR)
        common.make_directory(config_directory)
        config_file = os.path.join(config_directory,
                                   self._DUT_USB_SERVICE_CONFIG_FILE)

        # Service configuration options
        config_stream = open(config_file, 'w')
        config_options = ["Interface=usb0",
                          "Address=" + self._dut_ip,
                          "MaskSize=30",
                          "Broadcast=" + self._broadcast_ip,
                          "Gateway=" + self._gateway_ip]
        for line in config_options:
            config_stream.write(line + "\n")
        config_stream.close()

        # Ignore usb0 in connman
        original_connman = os.path.join(os.curdir,
                                        self._LOCAL_MOUNT_DIR,
                                        self._DUT_CONNMAN_SERVICE_FILE)
        output_file = os.path.join(os.curdir,
                                   self._LOCAL_MOUNT_DIR,
                                   self._DUT_CONNMAN_SERVICE_FILE + "_temp")
        connman_in = open(original_connman, "r")
        connman_out = open(output_file, "w")
        for line in connman_in:
            if "ExecStart=/usr/sbin/connmand" in line:
                line = line[0:-1] + " -I usb0 \n"
            connman_out.write(line)
        connman_in.close()
        connman_out.close()
        shutil.copy(output_file, original_connman)
        os.remove(output_file)
Beispiel #11
0
    def _add_usb_networking(self):
        """
        Inject USB-networking service files

        Returns:
            None
        """
        logger.info("Injecting USB-networking service.")
        source_file = os.path.join(self._MODULE_DATA_PATH,
                                   self._DUT_USB_SERVICE_FILE)
        target_file = os.path.join(os.curdir, self._LOCAL_MOUNT_DIR,
                                   self._DUT_USB_SERVICE_LOCATION,
                                   self._DUT_USB_SERVICE_FILE)
        shutil.copy(source_file, target_file)

        # Copy UID and GID
        source_stat = os.stat(source_file)
        os.chown(target_file, source_stat.st_uid, source_stat.st_gid)

        # Set symlink to start the service at the end of boot
        try:
            os.symlink(
                os.path.join(os.sep, self._DUT_USB_SERVICE_LOCATION,
                             self._DUT_USB_SERVICE_FILE),
                os.path.join(os.curdir, self._LOCAL_MOUNT_DIR,
                             self._DUT_USB_SERVICE_LOCATION,
                             "multi-user.target.wants",
                             self._DUT_USB_SERVICE_FILE))
        except OSError as err:
            if err.errno == 17:
                logger.critical(
                    "The image file was not replaced. USB-networking service "
                    + "already exists.")
                print("The image file was not replaced! The symlink for "
                      "usb-networking service already exists.")

                # print "Aborting."
                # sys.exit(1)
            else:
                raise err

        # Create the service configuration file
        config_directory = os.path.join(os.curdir, self._LOCAL_MOUNT_DIR,
                                        self._DUT_USB_SERVICE_CONFIG_DIR)
        common.make_directory(config_directory)
        config_file = os.path.join(config_directory,
                                   self._DUT_USB_SERVICE_CONFIG_FILE)

        # Service configuration options
        config_stream = open(config_file, 'w')
        config_options = [
            "Interface=usb0", "Address=" + self._dut_ip, "MaskSize=30",
            "Broadcast=" + self._broadcast_ip, "Gateway=" + self._gateway_ip
        ]
        for line in config_options:
            config_stream.write(line + "\n")
        config_stream.close()

        # Ignore usb0 in connman
        original_connman = os.path.join(os.curdir, self._LOCAL_MOUNT_DIR,
                                        self._DUT_CONNMAN_SERVICE_FILE)
        output_file = os.path.join(os.curdir, self._LOCAL_MOUNT_DIR,
                                   self._DUT_CONNMAN_SERVICE_FILE + "_temp")
        connman_in = open(original_connman, "r")
        connman_out = open(output_file, "w")
        for line in connman_in:
            if "ExecStart=/usr/sbin/connmand" in line:
                line = line[0:-1] + " -I usb0 \n"
            connman_out.write(line)
        connman_in.close()
        connman_out.close()
        shutil.copy(output_file, original_connman)
        os.remove(output_file)
Beispiel #12
0
    def _prepare_support_fs(self, root_tarball):
        """
        Create directories and copy all the necessary files to the support fs
        working directory.

        This is done before booting the support image, as the rootfs might be
        read only when accessed through nfs

        Args:
            root_tarball:
                The name of the root fs tarball

        Returns:
            None
        """



        # Note: need to remove the first '/' from file paths when building
        # absolute paths on the testing harness, as these paths are
        # absolute path intended for the support image operations (e.g. /usr/foo
        # rather than usr/foo, when we want to build
        # /path/to/nfs/path/to/rootfs/usr/foo)
        #
        # The need to remove the '/' is due to os.path.join behaviour, where it
        # will discard the current path string when encourtering an absolute
        # path

        logger.info("Creating directories and copying image files")

        common.make_directory(os.path.join(
            self.nfs_path,
            self.working_directory[1:]))

        common.make_directory(
            os.path.join(
                self.nfs_path, self.mount_dir[1:]))

        shutil.copy(
            os.path.join(self.parameters["mlo_file"]),
            os.path.join(self.nfs_path, self.mlo_file[1:]))

        shutil.copy(
            os.path.join(self.parameters["u-boot_file"]),
            os.path.join(self.nfs_path, self.u_boot_file[1:]))

        # temporary hack - remove once CI scripts are updated

        if "tar.bz2" in root_tarball:
            logger.info("Using command line arg for root tarball")
            shutil.copy(
                os.path.join(root_tarball),
                os.path.join(self.nfs_path, self.root_tarball[1:]))
        else:
            logger.info("No tarball name passed - using default value")
            shutil.copy(
                self.parameters["root_tarball"],
                os.path.join(self.nfs_path, self.root_tarball[1:]))

        shutil.copy(
            os.path.join(self.parameters["dtb_file"]),
            os.path.join(self.nfs_path, self.dtb_file[1:]))

        ssh_file = os.path.join(
            os.path.dirname(__file__),
            'data',
            "authorized_keys")

        shutil.copy(
            ssh_file,
            os.path.join(self.nfs_path, self.ssh_file[1:]))