예제 #1
0
파일: utils.py 프로젝트: mitre/stixmarx
    def _get_class_instances(self, module_str, module):
        """Returns a tuple with objects that could be instantiated
        without arguments.

        Args:
            module: A ModuleType object. It can be either in the lowest or
            highest level module.

        Returns:
            A tuple with `mixbox.Entity` objects from the given module.
        """
        result = ()

        for klass_ in itervalues(vars(module)):
            try:
                if inspect.isclass(klass_) and issubclass(
                        klass_, entities.Entity):
                    result += (klass_(), )
                elif inspect.ismodule(klass_) and (
                        module_str in module_name(klass_)
                        and module_str != module_name(klass_)):
                    result += self._get_class_instances(module_str, klass_)
            except:
                msg = "{0} could not be instantiated without args."
                LOG.debug(msg.format(klass_))
                continue

        return result
예제 #2
0
파일: base.py 프로젝트: shinsec/python-stix
    def _set_vocab(self, klass=None, **kwargs):
        """Sets a controlled vocabulary property value.

        * If the input value is ``None``, the property is set to ``None``.
        * If the input value is an instance of ``VocabString``, the property
          is set to the input value.
        * If the input value is not an instance of ``VocabString``, an attempt
          will be made to cast the input to an instance of `klass`. If `klass`
          is ``None``, ``VocabString`` will be used.

        Args:
            klass: The VocabString impl to cast the input value to. If ``None``
                ``VocabString`` will be assumed.
            **kwargs: The field name, value pair. The field name is the key
                and the field value is the value.

        """
        from stix.common import VocabString

        klass = klass or VocabString
        item  = next(itervalues(kwargs))

        if isinstance(item, VocabString):
            self._set_var(VocabString, **kwargs)
        else:
            self._set_var(klass, **kwargs)
예제 #3
0
def status_code(results):
    """Determines the exit status code to be returned from this script
    by inspecting the results returned from validating file(s).

    Status codes are binary OR'd together, so exit codes can communicate
    multiple error conditions.

    """
    status = codes.EXIT_SUCCESS

    for result in itervalues(results):
        schema = result.schema_results
        best_practice = result.best_practice_results
        profile = result.profile_results
        fatal = result.fatal

        if schema and not schema.is_valid:
            status |= codes.EXIT_SCHEMA_INVALID
        if best_practice and not best_practice.is_valid:
            status |= codes.EXIT_BEST_PRACTICE_INVALID
        if profile and not profile.is_valid:
            status |= codes.EXIT_PROFILE_INVALID
        if fatal:
            status |= codes.EXIT_VALIDATION_ERROR

    return status
예제 #4
0
def status_code(results):
    """Determines the exit status code to be returned from this script
    by inspecting the results returned from validating file(s).

    Status codes are binary OR'd together, so exit codes can communicate
    multiple error conditions.

    """
    status = codes.EXIT_SUCCESS

    for result in itervalues(results):
        schema = result.schema_results
        best_practice = result.best_practice_results
        profile = result.profile_results
        fatal = result.fatal

        if schema and not schema.is_valid:
            status |= codes.EXIT_SCHEMA_INVALID
        if best_practice and not best_practice.is_valid:
            status |= codes.EXIT_BEST_PRACTICE_INVALID
        if profile and not profile.is_valid:
            status |= codes.EXIT_PROFILE_INVALID
        if fatal:
            status |= codes.EXIT_VALIDATION_ERROR

    return status
예제 #5
0
    def _check_1_2_duplicate_ids(self, root, namespaces, version):  # noqa
        """STIX 1.2 dropped the schematic enforcement of id uniqueness to
        support versioning of components.

        This checks for duplicate (id, timestamp) pairs.

        """
        results = BestPracticeWarningCollection('Duplicate IDs')
        nlist = namespaces.values()

        # Find all nodes with IDs in the STIX/CybOX namespace
        nodes = root.xpath("//*[@id]")
        filtered = [x for x in nodes if utils.namespace(x) in nlist]

        # Build a mapping of IDs to nodes
        idnodes = collections.defaultdict(list)
        for node in filtered:
            idnodes[node.attrib.get('id')].append(node)

        # Find all nodes that have duplicate IDs
        dups = [x for x in itervalues(idnodes) if len(x) > 1]

        # Build warnings for all nodes that have conflicting id/timestamp pairs.
        for nodeset in dups:
            warns = self._get_id_timestamp_conflicts(nodeset)
            results.extend(warns)

        return results
예제 #6
0
파일: base.py 프로젝트: sgml/python-stix
    def _set_vocab(self, klass=None, **kwargs):
        """Sets a controlled vocabulary property value.

        * If the input value is ``None``, the property is set to ``None``.
        * If the input value is an instance of ``VocabString``, the property
          is set to the input value.
        * If the input value is not an instance of ``VocabString``, an attempt
          will be made to cast the input to an instance of `klass`. If `klass`
          is ``None``, ``VocabString`` will be used.

        Args:
            klass: The VocabString impl to cast the input value to. If ``None``
                ``VocabString`` will be assumed.
            **kwargs: The field name, value pair. The field name is the key
                and the field value is the value.

        """
        from stix.common import VocabString

        klass = klass or VocabString
        item = next(itervalues(kwargs))

        if isinstance(item, VocabString):
            self._set_var(VocabString, **kwargs)
        else:
            self._set_var(klass, **kwargs)
예제 #7
0
파일: cache.py 프로젝트: kralca/mixbox
def instanceof(cls):
    """Return all cached objects that are instances of the input `cls`."""
    instances = []

    for cached in six.itervalues(_CACHE):
        objects = list(cached)  # Temporarily create strong refs
        instances.extend(x for x in objects if isinstance(x, cls))

    return instances
예제 #8
0
        def _get_schemalocs(node):
            schemalocs = {}

            for ns in itervalues(node.nsmap):
                if ns not in self._schemalocs:
                    continue

                schemalocs[ns] = self._schemalocs[ns]
            return schemalocs
예제 #9
0
    def get_uri_schemaloc_map(self):
        """Constructs and returns a map from namespace URI to schema location
        URI.  Namespaces without schema locations are excluded."""
        mapping = {}

        for ni in six.itervalues(self.__ns_uri_map):
            if ni.schema_location:
                mapping[ni.uri] = ni.schema_location

        return mapping
예제 #10
0
    def _check_1_0_duplicate_ids(self, root, namespaces, version):  # noqa
        """Checks for duplicate ids in the document.

        """
        id_nodes = collections.defaultdict(list)

        for node in root.xpath("//*[@id]"):
            id_nodes[node.attrib['id']].append(node)

        results = BestPracticeWarningCollection('Duplicate IDs')
        for nodes in itervalues(id_nodes):
            if len(nodes) > 1:
                results.extend(BestPracticeWarning(node=x) for x in nodes)

        return results
예제 #11
0
    def __new__(metacls, name, bases, dict_):
        obj = type.__new__(metacls, name, bases, dict_)

        # Initialize a mapping of STIX versions to applicable rule funcs.
        ruledict = collections.defaultdict(list)

        # Find all @rule marked functions in the class dict_
        rulefuncs = (x for x in itervalues(dict_) if hasattr(x, 'is_rule'))

        # Build the rule function dict.
        for rule in rulefuncs:
            ruledict[(rule.min_version, rule.max_version)].append(rule)  # noqa

        # Attach the rule dictionary to the object instance.
        obj._rules = ruledict  # noqa

        return obj
예제 #12
0
    def get_prefix_uri_map(self):
        """Constructs and returns a map from to prefix to namespace URI,
        representing all namespaces in this set.  The prefix chosen for each
        namespace is its preferred prefix if it's not None.  If the preferred
        prefix is None, one is chosen from the set of registered
        prefixes.  In the latter situation, if no prefixes are registered,
        an exception is raised.
        """
        mapping = {}

        for ni in six.itervalues(self.__ns_uri_map):
            if ni.preferred_prefix:
                mapping[ni.preferred_prefix] = ni.uri
            elif len(ni.prefixes) > 0:
                prefix = next(iter(ni.prefixes))
                mapping[prefix] = ni.uri
            else:
                raise NoPrefixesError(ni.uri)

        return mapping
예제 #13
0
    def _finalize_schemalocs(self, schemaloc_dict=None):
        # If schemaloc_dict was passed in, make a copy so we don't mistakenly
        # modify the original.
        if schemaloc_dict:
            schemaloc_dict = dict(iteritems(schemaloc_dict))
        else:
            schemaloc_dict = {}

        # Get our id namespace
        id_ns = idgen.get_id_namespace()

        # Build our schemalocation dictionary!
        #
        # Initialize it from values found in the parsed, input schemalocations
        # (if there are any) and the schemaloc_dict parameter values (if there
        # are any).
        #
        # If there is a schemalocation found in both the parsed schemalocs and
        # the schema_loc dict, use the schemaloc_dict value.
        for ns, loc in iteritems(self._input_schemalocs):
            if ns in schemaloc_dict:
                continue
            schemaloc_dict[ns] = loc

        # Iterate over the finalized namespaces for a document and attempt
        # to map them to schemalocations. Warn if the namespace should have a
        # schemalocation and we can't find it anywhere.
        nsset = set(itervalues(self.finalized_namespaces))
        for ns in nsset:
            if ns in DEFAULT_STIX_SCHEMALOCATIONS:
                schemaloc_dict[ns] = DEFAULT_STIX_SCHEMALOCATIONS[ns]
            elif ns in schemaloc_dict:
                continue
            elif (ns == id_ns) or (ns in XML_NAMESPACES):
                continue
            else:
                error = "Unable to map namespace '{0}' to schemaLocation"
                warnings.warn(error.format(ns))

        return schemaloc_dict
예제 #14
0
    def get_uri_prefix_map(self):
        """Constructs and returns a map from namespace URI to prefix,
        representing all namespaces in this set.  The prefix chosen for each
        namespace is its preferred prefix if it's not None.  If the preferred
        prefix is None, one is chosen from the set of registered
        prefixes.  In the latter situation, if no prefixes are registered,
        an exception is raised.
        """
        mapping = {}

        for ni in six.itervalues(self.__ns_uri_map):
            if ni.preferred_prefix:
                mapping[ni.uri] = ni.preferred_prefix
            elif len(ni.prefixes) > 0:
                mapping[ni.uri] = next(iter(ni.prefixes))
            else:
                # The reason I don't let any namespace map to None here is that
                # I don't think generateDS supports it.  It requires prefixes
                # for all namespaces.
                raise NoPrefixesError(ni.uri)

        return mapping
예제 #15
0
    def _get_include_root(self, ns, list_schemas):
        """Attempts to determine the "root" schema for a targetNamespace.

        This builds a graph of ``xs:include`` directive sources and targets
        and attempts to find a common base for all includes.

        Note:
            If no schemas in `list_schemas` ``xs:include`` another schema,
            then ``list_schemas[0]`` is returned. This occurs when duplicate
            schemas (or different versions of the same schema that define the
            same namespace) were encountered in the initialization schema
            directory.

        Args:
            ns: The target namespace
            list_schemas: A list of schemas which exist or define the
                target namespace.

        Returns:
            A path to the root schema for the input `ns`.

        """
        graph = self._build_include_graph(list_schemas)

        if all(not(x) for x in itervalues(graph)):
            return list_schemas[0]

        for fp in graph:
            has_ancestors = self._is_included(graph, fp)
            has_children  = len(graph[fp]) > 0

            if has_children and not has_ancestors:
                return fp

        msg = "Unable to determine base schema for %s" % ns
        raise errors.XMLSchemaIncludeError(msg)
예제 #16
0
 def __str__(self):
     """for debugging"""
     return "\n\n".join(str(v) for v in six.itervalues(self.__ns_uri_map))
예제 #17
0
파일: cache.py 프로젝트: kralca/mixbox
def count():
    """Return the number of objects currently in the mixbox cache."""
    return sum(len(items) for items in six.itervalues(_CACHE))
예제 #18
0
    def _is_included(self, graph, fp):
        """Returns ``True`` if the schema at `fp` was included by any other
        schemas in `graph`.

        """
        return any(fp in includes for includes in itervalues(graph))
예제 #19
0
파일: cache.py 프로젝트: bworrell/mixbox
def count():
    """Returns the number of objects currently in the mixbox cache.

    """
    return sum(len(items) for items in six.itervalues(_CACHE))