Ejemplo n.º 1
0
def submit(ctx, target, url, options, package, custom, owner, timeout,
           priority, machine, platform, memory, enforce_timeout, clock, tags,
           baseline, remote, shuffle, pattern, max, unique):
    """Submit one or more files or URLs to Cuckoo."""
    init_console_logging(level=ctx.parent.level)
    Database().connect()

    try:
        l = submit_tasks(
            target, options, package, custom, owner, timeout, priority,
            machine, platform, memory, enforce_timeout, clock, tags, remote,
            pattern, max, unique, url, baseline, shuffle
        )

        for category, target, task_id in l:
            if task_id:
                print "%s: %s \"%s\" added as task with ID #%s" % (
                    bold(green("Success")), category, target, task_id
                )
            else:
                print "%s: %s \"%s\" as it has already been analyzed" % (
                    bold(yellow("Skipped")), category, target
                )
    except KeyboardInterrupt:
        print(red("Aborting submission of samples.."))
Ejemplo n.º 2
0
def submit(ctx, target, url, options, package, custom, owner, timeout,
           priority, machine, platform, memory, enforce_timeout, clock, tags,
           baseline, remote, shuffle, pattern, max, unique):
    """Submit one or more files or URLs to Cuckoo."""
    init_console_logging(level=ctx.parent.level)
    Database().connect()

    try:
        l = submit_tasks(
            target, options, package, custom, owner, timeout, priority,
            machine, platform, memory, enforce_timeout, clock, tags, remote,
            pattern, max, unique, url, baseline, shuffle
        )

        for category, target, task_id in l:
            if task_id:
                print "%s: %s \"%s\" added as task with ID #%s" % (
                    bold(green("Success")), category, target, task_id
                )
            else:
                print "%s: %s \"%s\" as it has already been analyzed" % (
                    bold(yellow("Skipped")), category, target
                )
    except KeyboardInterrupt:
        print(red("Aborting submission of samples.."))
Ejemplo n.º 3
0
def submit_tasks(target, options, package, custom, owner, timeout, priority,
                 machine, platform, memory, enforce_timeout, clock, tags,
                 remote, pattern, maxcount, is_unique, is_url, is_baseline,
                 is_shuffle):
    db = Database()

    data = dict(
        package=package or "",
        timeout=timeout,
        options=options,
        priority=priority,
        machine=machine,
        platform=platform,
        custom=custom,
        owner=owner,
        tags=tags,
        memory="1" if memory else "0",
        enforce_timeout="1" if enforce_timeout else "0",
        clock=clock,
        unique="1" if is_unique else "0",
    )

    if is_baseline:
        if remote:
            print "Remote baseline support has not yet been implemented."
            return

        task_id = db.add_baseline(timeout, owner, machine, memory)
        yield "Baseline", machine, task_id
        return

    if is_url and is_unique:
        print "URL doesn't have --unique support yet."
        return

    if is_url:
        for url in target:
            if not remote:
                data.pop("unique", None)
                task_id = db.add_url(to_unicode(url), **data)
                yield "URL", url, task_id
                continue

            data["url"] = to_unicode(url)
            try:
                r = requests.post("http://%s/tasks/create/url" % remote,
                                  data=data)
                yield "URL", url, r.json()["task_id"]
            except Exception as e:
                print "%s: unable to submit URL: %s" % (bold(red("Error")), e)
    else:
        files = []
        for path in target:
            files.extend(enumerate_files(os.path.abspath(path), pattern))

        if is_shuffle:
            random.shuffle(files)

        for filepath in files:
            if not os.path.getsize(filepath):
                print "%s: sample %s (skipping file)" % (bold(
                    yellow("Empty")), filepath)
                continue

            if maxcount is not None:
                if not maxcount:
                    break
                maxcount -= 1

            if not remote:
                if is_unique:
                    sha256 = File(filepath).get_sha256()
                    if db.find_sample(sha256=sha256):
                        yield "File", filepath, None
                        continue

                data.pop("unique", None)
                task_id = db.add_path(file_path=filepath, **data)
                yield "File", filepath, task_id
                continue

            files = {
                "file": (os.path.basename(filepath), open(filepath, "rb")),
            }

            try:
                r = requests.post("http://%s/tasks/create/file" % remote,
                                  data=data,
                                  files=files)
                yield "File", filepath, r.json()["task_id"]
            except Exception as e:
                print "%s: unable to submit file: %s" % (bold(red("Error")), e)
                continue
Ejemplo n.º 4
0
def check_version(ignore_vuln=False):
    """Check version of Cuckoo."""
    if not config("cuckoo:cuckoo:version_check"):
        return

    ignore_vuln = ignore_vuln or config("cuckoo:cuckoo:ignore_vulnerabilities")

    import pkg_resources

    print(" Checking for updates...")

    try:
        r = requests.get("https://cuckoosandbox.org/updates.json",
                         params={"version": version},
                         timeout=6)
        r.raise_for_status()
        r = r.json()
    except (requests.RequestException, ValueError) as e:
        print(red(" Error checking for the latest Cuckoo version: %s!" % e))
        return

    try:
        old = StrictVersion(version) < StrictVersion(r["version"])
    except ValueError:
        old = True

    warnings = []
    for deptype, vulns in r.get("vulnerable", {}).iteritems():
        for dep in vulns:
            compare = dep.get("highest") or dep.get("lowest")

            # Check if any of the mentioned Python dependencies are installed
            if deptype == "pydep":
                try:
                    v = pkg_resources.get_distribution(
                        dep["name"]).parsed_version
                except (pkg_resources.DistributionNotFound, ValueError):
                    continue

            # See if the mentioned virtualization software is used
            elif deptype == "machinery":
                if config("cuckoo:cuckoo:machinery") != dep["name"]:
                    continue

                # If the version number cannot be determined, raise a warning
                # to be sure. Virtualization vulnerabilities can potentially
                # cause a lot of damage
                v = cuckoo.machinery.plugins[dep["name"]].version()
                if not v:
                    warnings.append(
                        bold(
                            red("Potentially vulnerable %s version installed. "
                                "Failed to retrieve its version. Update if version"
                                " is: %s" % (dep["name"], compare))))
                    continue

            else:
                continue

            warn = False
            # If a range is specified, check if the current version falls
            # within the range.
            if dep.get("highest") and dep.get("lowest"):
                lv = LooseVersion(str(v))
                if (lv >= LooseVersion(dep["lowest"])
                        and lv <= LooseVersion(dep["highest"])):
                    warn = True

            # If no range is specified, use the specified operator to see if
            # the installed version is
            # 'if <operator> highest/lowest specified'
            elif cmp_version(str(v), compare, dep["op"]):
                warn = True

            # Warn the user the dependency must be updated/
            if warn:
                info = dep.get("info")
                message = "Vulnerable version of %s installed (%s). It is " \
                          "highly recommended to update. Please update and " \
                          "restart Cuckoo." % (dep["name"], v)

                if deptype == "pydep":
                    message += " 'pip install %s%s'" % (dep["name"],
                                                        dep["recommended"])

                else:
                    message += " Recommended version: %s" % dep["recommended"]

                message = bold(red(message))

                if info:
                    message += yellow("\nAdditional information: %s" % info)

                warnings.append(message)

    if warnings:
        print(color(bold(red("Vulnerable dependencies found\n")), 5))
    for warning in warnings:
        print("--> %s\n" % color(warning, 4))

    if warnings and not ignore_vuln:
        print(
            "This check can be disabled by enabling "
            "'ignore_vulnerabilities' in cuckoo.conf under the "
            "[cuckoo] section")
        sys.exit(1)

    if old:
        msg = "Cuckoo Sandbox version %s is available now." % r["version"]
        print(red(" Outdated! ") + msg)
    else:
        print(green(" You're good to go!"))

    print("\n Our latest blogposts:")
    for blogpost in r["blogposts"]:
        print(" * %s, %s." % (yellow(blogpost["title"]), blogpost["date"]))
        print("   %s" % red(blogpost["oneline"]))
        print("   More at %s" % blogpost["url"])
        print("")
    return r
Ejemplo n.º 5
0
def submit_tasks(target, options, package, custom, owner, timeout, priority,
                 machine, platform, memory, enforce_timeout, clock, tags,
                 remote, pattern, maxcount, is_unique, is_url, is_baseline,
                 is_shuffle):
    db = Database()

    data = dict(
        package=package or "",
        timeout=timeout,
        options=options,
        priority=priority,
        machine=machine,
        platform=platform,
        custom=custom,
        owner=owner,
        tags=tags,
        memory="1" if memory else "0",
        enforce_timeout="1" if enforce_timeout else "0",
        clock=clock,
        unique="1" if is_unique else "0",
    )

    if is_baseline:
        if remote:
            print "Remote baseline support has not yet been implemented."
            return

        task_id = db.add_baseline(timeout, owner, machine, memory)
        yield "Baseline", machine, task_id
        return

    if is_url and is_unique:
        print "URL doesn't have --unique support yet."
        return

    if is_url:
        for url in target:
            if not remote:
                data.pop("unique", None)
                task_id = db.add_url(to_unicode(url), **data)
                yield "URL", url, task_id
                continue

            data["url"] = to_unicode(url)
            try:
                r = requests.post(
                    "http://%s/tasks/create/url" % remote, data=data
                )
                yield "URL", url, r.json()["task_id"]
            except Exception as e:
                print "%s: unable to submit URL: %s" % (
                    bold(red("Error")), e
                )
    else:
        files = []
        for path in target:
            files.extend(enumerate_files(os.path.abspath(path), pattern))

        if is_shuffle:
            random.shuffle(files)

        for filepath in files:
            if not os.path.getsize(filepath):
                print "%s: sample %s (skipping file)" % (
                    bold(yellow("Empty")), filepath
                )
                continue

            if maxcount is not None:
                if not maxcount:
                    break
                maxcount -= 1

            if not remote:
                if is_unique:
                    sha256 = File(filepath).get_sha256()
                    if db.find_sample(sha256=sha256):
                        yield "File", filepath, None
                        continue

                data.pop("unique", None)
                task_id = db.add_path(file_path=filepath, **data)
                yield "File", filepath, task_id
                continue

            files = {
                "file": (os.path.basename(filepath), open(filepath, "rb")),
            }

            try:
                r = requests.post(
                    "http://%s/tasks/create/file" % remote,
                    data=data, files=files
                )
                yield "File", filepath, r.json()["task_id"]
            except Exception as e:
                print "%s: unable to submit file: %s" % (
                    bold(red("Error")), e
                )
                continue