Beispiel #1
0
def sudo_write_file(filename, contents, mode=0o644):
    """Write (or overwrite) file as root.  USE WITH EXTREME CARE.

    Runs an atomic update using non-interactive `sudo`.  This will fail if
    it needs to prompt for a password.

    When running in a snap or devel mode, this function calls
    `atomic_write` directly.

    :type contents: `bytes`.
    """
    from provisioningserver.config import is_dev_environment

    if not isinstance(contents, bytes):
        raise TypeError("Content must be bytes, got: %r" % (contents, ))
    if snappy.running_in_snap():
        atomic_write(contents, filename, mode=mode)
    else:
        maas_write_file = get_library_script_path("maas-write-file")
        command = _with_dev_python(maas_write_file, filename, "%.4o" % mode)
        if not is_dev_environment():
            command = sudo(command)
        proc = Popen(command, stdin=PIPE)
        stdout, stderr = proc.communicate(contents)
        if proc.returncode != 0:
            raise ExternalProcessError(proc.returncode, command, stderr)
Beispiel #2
0
def run(
    args, output=sys.stdout, stdin=sys.stdin, stdin_buffer=sys.stdin.buffer
):
    """Observe an Ethernet interface and print DHCP packets."""
    network_monitor = None
    if args.input_file is None:
        if args.interface is None:
            raise ActionScriptError("Required argument: interface")
        cmd = sudo([get_path("/usr/lib/maas/dhcp-monitor"), args.interface])
        network_monitor = subprocess.Popen(
            cmd,
            stdin=subprocess.DEVNULL,
            stdout=subprocess.PIPE,
            stderr=subprocess.DEVNULL,
        )
        infile = network_monitor.stdout
    else:
        if args.input_file == "-":
            mode = os.fstat(stdin.fileno()).st_mode
            if not stat.S_ISFIFO(mode):
                raise ActionScriptError("Expected stdin to be a pipe.")
            infile = stdin_buffer
        else:
            infile = open(args.input_file, "rb")
    return_code = observe_dhcp_packets(input=infile, out=output)
    if return_code is not None:
        raise SystemExit(return_code)
    if network_monitor is not None:
        return_code = network_monitor.poll()
        if return_code is not None:
            raise SystemExit(return_code)
Beispiel #3
0
def run(args,
        output=sys.stdout,
        stdin=sys.stdin,
        stdin_buffer=sys.stdin.buffer):
    """Observe an Ethernet interface and print beaconing packets."""

    # First, become a progress group leader, so that signals can be directed
    # to this process and its children; see p.u.twisted.terminateProcess.
    os.setpgrp()

    network_monitor = None
    if args.input_file is None:
        if args.interface is None:
            raise ActionScriptError("Required argument: interface")
        cmd = sudo([get_path("/usr/lib/maas/beacon-monitor"), args.interface])
        network_monitor = subprocess.Popen(cmd,
                                           stdin=subprocess.DEVNULL,
                                           stdout=subprocess.PIPE)
        infile = network_monitor.stdout
    else:
        if args.input_file == '-':
            mode = os.fstat(stdin.fileno()).st_mode
            if not stat.S_ISFIFO(mode):
                raise ActionScriptError("Expected stdin to be a pipe.")
            infile = stdin_buffer
        else:
            infile = open(args.input_file, "rb")
    return_code = observe_beaconing_packets(input=infile, out=output)
    if return_code is not None:
        raise SystemExit(return_code)
    if network_monitor is not None:
        return_code = network_monitor.poll()
        if return_code is not None:
            raise SystemExit(return_code)
Beispiel #4
0
def update_targets_conf(snapshot):
    """Runs tgt-admin to update the new targets from "maas.tgt"."""
    # Ensure that tgt is running before tgt-admin is used.
    service_monitor.ensureService("tgt").wait(30)

    # Update the tgt config.
    targets_conf = os.path.join(snapshot, 'maas.tgt')

    # The targets_conf may not exist in the event the BootSource is broken
    # and images havn't been imported yet. This fixes LP:1655721
    if not os.path.exists(targets_conf):
        return

    try:
        call_and_check(
            sudo([
                get_path('/usr/sbin/tgt-admin'),
                '--conf',
                targets_conf,
                '--update',
                'ALL',
            ]))
    except ExternalProcessError as e:
        msg = "Unable to update TGT config: %s" % e
        try_send_rack_event(EVENT_TYPES.RACK_IMPORT_WARNING, msg)
        maaslog.warning(msg)
Beispiel #5
0
def sudo_delete_file(filename):
    """Delete file as root.  USE WITH EXTREME CARE.

    Runs an atomic update using non-interactive `sudo`.  This will fail if
    it needs to prompt for a password.

    When running in a snap this function calls `atomic_write` directly.
    """
    from provisioningserver.config import is_dev_environment
    if snappy.running_in_snap():
        atomic_delete(filename)
    else:
        maas_delete_file = get_library_script_path("maas-delete-file")
        command = _with_dev_python(maas_delete_file, filename)
        if not is_dev_environment():
            command = sudo(command)
        proc = Popen(command)
        stdout, stderr = proc.communicate()
        if proc.returncode != 0:
            raise ExternalProcessError(proc.returncode, command, stderr)
Beispiel #6
0
 def test_returns_sudo_command_when_is_not_dev_environment(self):
     cmd = [factory.make_name("cmd") for _ in range(3)]
     self.set_is_dev_environment(False)
     self.set_is_in_snap(False)
     self.assertEqual(["sudo", "-n"] + cmd, sudo(cmd))
Beispiel #7
0
 def test_returns_same_command_when_in_snap(self):
     cmd = [factory.make_name("cmd") for _ in range(3)]
     self.set_is_dev_environment(False)
     self.set_is_in_snap(True)
     self.assertEqual(cmd, sudo(cmd))