Exemplo n.º 1
0
    def scan_for_process(self):
        """Scan the image for the idle process."""
        maxlen = self.session.GetParameter("autodetect_scan_length",
                                           10 * 1024 * 1024 * 1024)

        self.image_name_offset = self.profile.get_obj_offset(
            "_EPROCESS", "ImageFileName")

        for offset, hit in scan.MultiStringScanner(
                session=self.session,
                needles=self.plugin_args.process_name,
                profile=self.profile,
                address_space=self.physical_address_space).scan(0,
                                                                maxlen=maxlen):
            eprocess = self.profile.Object(
                "_EPROCESS",
                offset=offset - self.image_name_offset,
                vm=self.session.physical_address_space)

            self.session.report_progress(
                u"Found possible _EPROCESS @ 0x%X (In process %s) (DTB: 0x%X)",
                eprocess.obj_offset, utils.SmartUnicode(hit),
                eprocess.Pcb.DirectoryTableBase.v())

            yield eprocess
Exemplo n.º 2
0
    def render(self, renderer):
        scanner = scan.MultiStringScanner(
            needles=self.keyword, address_space=self.address_space,
            session=self.session)

        for hit, _ in scanner.scan(offset=self.offset, maxlen=self.limit):
            hexdumper = self.session.plugins.dump(
                offset=hit - 16, length=self.context + 16,
                address_space=self.address_space)

            hexdumper.render(renderer)
Exemplo n.º 3
0
 def find_in_module(self, module_name, pattern):
     if module_name.lower() not in self.modules:
         raise Exception('Module is not in lsass emmory space! %s' %
                         module_name)
     module = self.modules[module_name.lower()]
     res = []
     scanner = scan.MultiStringScanner(
         needles=[pattern],
         address_space=self.lsass_task.get_process_address_space())
     for hit, _ in scanner.scan(offset=int(module.start_addr),
                                maxlen=int(module.size)):
         res.append(int(hit))
     return res
Exemplo n.º 4
0
    def render(self, renderer):
        scanner = scan.MultiStringScanner(
            needles=[utils.SmartStr(x) for x in self.plugin_args.keyword],
            address_space=self.plugin_args.address_space,
            session=self.session)

        for hit, _ in scanner.scan(offset=self.plugin_args.offset,
                                   maxlen=self.plugin_args.limit):
            hexdumper = self.session.plugins.dump(
                offset=hit - 16,
                length=self.plugin_args.context + 16,
                address_space=self.plugin_args.address_space)

            hexdumper.render(renderer)
Exemplo n.º 5
0
    def DetectFromHit(self, hit, filename_offset, address_space):
        # Make use of already known dtb and kernel_base parameters - this speeds
        # up live analysis significantly since we do not need to search for
        # anything then.
        if filename_offset == 0:
            if (self.session.HasParameter("dtb") and
                    self.session.HasParameter("kernel_base")):
                test_as = amd64.AMD64PagedMemory(
                    session=self.session, base=address_space,
                    dtb=self.session.GetParameter("dtb"))

                if self.VerifyAMD64DTB(test_as):
                    return self._match_profile_for_kernel_base(
                        self.session.GetParameter("kernel_base"),
                        test_as)

            return

        # Get potential kernel address spaces.
        for test_as in self.DetectWindowsDTB(filename_offset, address_space):
            # Try to find the kernel base. This can be improved in future by
            # taking more than a single search point.
            scanner = scan.MultiStringScanner(
                address_space=test_as, needles=[
                    b"This program cannot be run in DOS mode",
                ])

            if self.session.HasParameter("kernel_base"):
                kernel_base = self.session.GetParameter("kernel_base")
                return self._match_profile_for_kernel_base(
                    kernel_base, test_as)

            for offset, _ in scanner.scan(
                    offset=0xF80000000000, maxlen=0x10000000000):
                kernel_base = offset & 0xFFFFFFFFFFFFFF000
                profile_obj = self._match_profile_for_kernel_base(
                    kernel_base, test_as)

                if profile_obj:
                    self.session.logging.debug(
                        "Verifying profile %s by scanning processes for a valid DTB",
                        profile_obj)
                    if self.VerifyProfile(profile_obj):
                        return profile_obj
Exemplo n.º 6
0
    def DetectFromHit(self, hit, filename_offset, address_space):
        # Get potential kernel address spaces.
        for test_as in self.DetectWindowsDTB(filename_offset, address_space):
            # Try to find the kernel base. This can be improved in future by
            # taking more than a single search point.
            scanner = scan.MultiStringScanner(
                address_space=test_as, needles=[
                    "This program cannot be run in DOS mode",
                    ])

            kernel_base = self.session.GetParameter("kernel_base")
            if kernel_base:
                return self._match_profile_for_kernel_base(
                    kernel_base, test_as)

            for offset, _ in scanner.scan(
                    offset=0xF80000000000, maxlen=0x10000000000):
                kernel_base = offset & 0xFFFFFFFFFFFFFF000
                profile_obj = self._match_profile_for_kernel_base(
                    kernel_base, test_as)

                if profile_obj:
                    return profile_obj
Exemplo n.º 7
0
    def _ScanProfiles(self):
        address_space = self.session.physical_address_space
        best_profile = None
        best_match = 0

        methods = []
        needles = []
        needle_lookup = {}

        method_names = self.session.GetParameter("autodetect")

        self.session.logging.debug(
            "Will detect profile using these Detectors: %s" % ",".join(
                method_names))

        if not method_names:
            raise RuntimeError("No autodetection methods specified. "
                               "Use the --autodetect parameter.")

        for method_name in method_names:
            for method in DetectionMethod.classes_by_name[method_name]:
                methods.append(method(session=self.session))

        methods.sort(key=lambda x: x.order)
        for method in methods:
            for keyword in method.Keywords():
                needles.append(keyword)
                needle_lookup.setdefault(keyword, []).append(method)

            for offset in method.Offsets():
                self.session.logging.debug("Trying method %s, offset %d",
                                           method.name, offset)
                profile = method.DetectFromHit(None, offset, address_space)
                if profile:
                    self.session.logging.info(
                        "Detection method %s yielded profile %s",
                        method.name, profile)
                    return profile

        # 10 GB by default.
        autodetect_scan_length = self.session.GetParameter(
            "autodetect_scan_length", 10*1024*1024*1024)

        # Build and configure the scanner.
        scanner = scan.MultiStringScanner(
            profile=obj.NoneObject(),
            address_space=address_space, needles=needles,
            session=self.session)
        scanner.progress_message = "Autodetecting profile: %(offset)#08x"
        for offset, hit in scanner.scan(maxlen=autodetect_scan_length):
            self.session.render_progress(
                "guess_profile: autodetection hit @ %x - %s", offset, hit)

            for method in needle_lookup[hit]:
                profile = method.DetectFromHit(hit, offset, address_space)
                if profile:
                    self.session.logging.debug(
                        "Detection method %s worked at offset %#x",
                        method.name, offset)
                    return profile

            if best_match == 1.0:
                # If we have an exact match we can stop scanning.
                break

        threshold = self.session.GetParameter("autodetect_threshold")
        if best_match == 0:
            self.session.logging.error(
                "No profiles match this image. Try specifying manually.")

            return obj.NoneObject("No profile detected")

        elif best_match < threshold:
            self.session.logging.error(
                "Best match for profile is %s with %.0f%%, which is too low " +
                "for given threshold of %.0f%%. Try lowering " +
                "--autodetect-threshold.",
                best_profile.name,
                best_match * 100,
                threshold * 100)

            return obj.NoneObject("No profile detected")

        else:
            self.session.logging.info(
                "Profile %s matched with %.0f%% confidence.",
                best_profile.name,
                best_match * 100)

            return best_profile