示例#1
0
文件: beaconing.py 项目: zhangrb/maas
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)
示例#2
0
文件: dhcp.py 项目: th3architect/maas
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)
示例#3
0
def _reader_from_avahi():
    """Read from a newly spawned `avahi-browse` subprocess.

    :raises SystemExit: If `avahi-browse` exits non-zero.
    """
    avahi_browse = subprocess.Popen(
        [
            get_path("/usr/bin/avahi-browse"),
            "--all",
            "--resolve",
            "--no-db-lookup",
            "--parsable",
            "--no-fail",
        ],
        stdin=subprocess.DEVNULL,
        stdout=subprocess.PIPE,
    )
    try:
        # Avahi says "All strings used in DNS-SD are UTF-8 strings".
        yield avahi_browse.stdout
    finally:
        # SIGINT or SIGTERM (see ActionScript.setup) has been received,
        # avahi-browse may have crashed or been terminated, or there may have
        # been an exception in this script. In any case we give the subprocess
        # a chance to exit cleanly if it has not done so already, and then we
        # report on that exit.
        if _terminate_process(avahi_browse) != 0:
            raise SystemExit(avahi_browse.returncode)
示例#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)
示例#5
0
def get_config_v4(
    template_name: str,
    global_dhcp_snippets: Sequence[dict],
    failover_peers: Sequence[dict],
    shared_networks: Sequence[dict],
    hosts: Sequence[dict],
    omapi_key: str,
) -> str:
    """Return a DHCP config file based on the supplied parameters.

    :param template_name: Template file name: `dhcpd.conf.template` for the
        IPv4 template.
    :return: A full configuration, as a string.
    """
    platform_codename = lsb_release()["codename"]
    template = load_template("dhcp", template_name)
    dhcp_socket = get_maas_data_path("dhcpd.sock")

    # Helper functions to stuff into the template namespace.
    helpers = {
        "oneline": normalise_whitespace,
        "commalist": normalise_any_iterable_to_comma_list,
        "quoted_commalist": normalise_any_iterable_to_quoted_comma_list,
        "running_in_snap": snappy.running_in_snap(),
    }

    for shared_network in shared_networks:
        interface = shared_network.get("interface", None)
        for subnet in shared_network["subnets"]:
            rack_ip = get_rack_ip_for_subnet(
                4, subnet["subnet_cidr"], interface
            )
            if rack_ip is not None:
                subnet["next_server"] = rack_ip
                subnet["bootloader"] = compose_conditional_bootloader(
                    False, rack_ip
                )
            ntp_servers = subnet["ntp_servers"]  # Is a list.
            ntp_servers_ipv4, ntp_servers_ipv6 = _get_addresses(*ntp_servers)
            subnet["ntp_servers_ipv4"] = ", ".join(ntp_servers_ipv4)
            subnet["ntp_servers_ipv6"] = ", ".join(ntp_servers_ipv6)

    try:
        return template.substitute(
            global_dhcp_snippets=global_dhcp_snippets,
            hosts=hosts,
            failover_peers=failover_peers,
            shared_networks=shared_networks,
            platform_codename=platform_codename,
            omapi_key=omapi_key,
            dhcp_helper=(get_path("/usr/sbin/maas-dhcp-helper")),
            dhcp_socket=dhcp_socket,
            **helpers
        )
    except (KeyError, NameError) as error:
        raise DHCPConfigError(
            "Failed to render DHCP configuration."
        ) from error
示例#6
0
文件: config.py 项目: pfxuan/maas
def get_config_v4(template_name: str, global_dhcp_snippets: Sequence[dict],
                  failover_peers: Sequence[dict],
                  shared_networks: Sequence[dict], hosts: Sequence[dict],
                  omapi_key: str) -> str:
    """Return a DHCP config file based on the supplied parameters.

    :param template_name: Template file name: `dhcpd.conf.template` for the
        IPv4 template.
    :return: A full configuration, as a string.
    """
    platform_codename = linux_distribution()[2]
    template = load_template('dhcp', template_name)
    dhcp_socket = get_data_path('/var/lib/maas/dhcpd.sock')

    # Helper functions to stuff into the template namespace.
    helpers = {
        "oneline": normalise_whitespace,
        "commalist": normalise_any_iterable_to_comma_list,
        "quoted_commalist": normalise_any_iterable_to_quoted_comma_list,
        "running_in_snap": snappy.running_in_snap(),
    }

    rack_addrs = [
        IPAddress(addr) for addr in net_utils.get_all_interface_addresses()
    ]

    for shared_network in shared_networks:
        for subnet in shared_network["subnets"]:
            cidr = IPNetwork(subnet['subnet_cidr'])
            rack_ips = [
                str(rack_addr) for rack_addr in rack_addrs if rack_addr in cidr
            ]
            if len(rack_ips) > 0:
                subnet["next_server"] = rack_ips[0]
                subnet["bootloader"] = compose_conditional_bootloader(
                    False, rack_ips[0])
            ntp_servers = subnet["ntp_servers"]  # Is a list.
            ntp_servers_ipv4, ntp_servers_ipv6 = _get_addresses(*ntp_servers)
            subnet["ntp_servers_ipv4"] = ", ".join(ntp_servers_ipv4)
            subnet["ntp_servers_ipv6"] = ", ".join(ntp_servers_ipv6)

    try:
        return template.substitute(
            global_dhcp_snippets=global_dhcp_snippets,
            hosts=hosts,
            failover_peers=failover_peers,
            shared_networks=shared_networks,
            platform_codename=platform_codename,
            omapi_key=omapi_key,
            dhcp_helper=(get_path('/usr/sbin/maas-dhcp-helper')),
            dhcp_socket=dhcp_socket,
            **helpers)
    except (KeyError, NameError) as error:
        raise DHCPConfigError(
            "Failed to render DHCP configuration.") from error
示例#7
0
def get_maas_common_command():
    """Return path to the maas-rack command.

    In production mode this will just return 'maas-rack', but in
    development mode it will return the path for the current development
    environment.
    """
    # Avoid circular imports.
    from provisioningserver.config import is_dev_environment
    if is_dev_environment():
        from maastesting import root
        return os.path.join(root, "bin", "maas-common")
    else:
        return os.path.join(get_path("/usr/lib/maas"), "maas-common")
示例#8
0
def get_maas_common_command():
    """Return path to the maas-rack command.

    In production mode this will just return 'maas-rack', but in
    development mode it will return the path for the current development
    environment.
    """
    # Avoid circular imports.
    from provisioningserver.config import is_dev_environment
    if is_dev_environment():
        from maastesting import root
        return os.path.join(root, 'bin/maas-common')
    elif snappy.running_in_snap():
        # there's no maas-common in the snap as maas-rack is always present
        return os.path.join(snappy.get_snap_path(), 'bin/maas-rack')
    else:
        return get_path('usr/lib/maas/maas-common')
示例#9
0
def get_library_script_path(name):
    """Return path to a "library script".

    By convention (here) scripts are always installed to ``/usr/lib/maas`` on
    the target machine.

    The FHS (Filesystem Hierarchy Standard) defines ``/usr/lib/`` as the
    location for libraries used by binaries in ``/usr/bin`` and ``/usr/sbin``,
    hence the term "library script".

    In production mode this will return ``/usr/lib/maas/$name``, but in
    development mode it will return ``$root/scripts/$name``.
    """
    # Avoid circular imports.
    from provisioningserver.config import is_dev_environment
    if is_dev_environment():
        from maastesting import root
        return os.path.join(root, "scripts", name)
    else:
        return os.path.join(get_path("/usr/lib/maas"), name)