This page contains suggested practices for developing and consuming CybOX content. There's a similar page for STIX.
Note that these are simply suggested practices. In many cases, operational or technical concerns may prohibit you from implementing them or they may just not make sense in your situation. That's perfectly fine, these are just suggestions.
CybOX IDs are XML QNames. Each ID includes both a namespace portion (optional) and an ID portion (required) separated by a colon (:). The recommend approach to creating CybOX IDs is to define a producer namespace and namespace prefix, then use the form:
[ns prefix]:[construct type]-[GUID]
The "ns prefix" should be a namespace prefix bound to a namespace owned/controlled by the producer of the content.
Some examples:
acme:event-ce431003-ad07-4c96-bd7a-a50a3196e2a0
acme:action-bf8bc5d5-c7e6-46b0-8d22-7500fea77196
acme:observable-79090715-8d6a-46b7-943b-c0bb9e063788
acme:fileobj-965e1140-2c22-4408-a423-b7acc08290a7
In order to use this approach, you will need to define that namespace prefix in the head of your XML document:
<cybox:Observables xmlns:acme="http://acme.example.com" ...
This format provides high assurance that IDs will be both unique and meaningful, because the producer namespace denotes who's producing it, the construct name denotes what it is, and the GUID guarantees uniqueness.
When generating CybOX Observables and Objects from source data that contains identification information, CybOX authors should record the mapping of their source IDs to their newly generated CybOX IDs using some storage mechanism outside of CybOX (e.g., a database). This will allow authors to quickly refer to and/or alter source data when new information regarding a particular CybOX Observable or Object presents itself in the future. Newly generated IDs may contain a namespace prefix which refers to the source vendor or tool used to generate the source data.
In many cases, you'll have an option to either include a component (an object, for example) within the parent component or to reference the component by ID to a representation in a global location.
For example, an Object can include Related Objects. One way of doing this is to include the related object inline in the parent object:
<cybox:Object id="acme:fileobj-f7304dae-94c6-4592-b943-398e1e6916a7">
<cybox:Properties xsi:type="FileObj:FileObjectType">
<!-- SNIP -->
</cybox:Properties>
<cybox:Related_Objects>
<cybox:Related_Object id="acme:mutexobj-3c1221bd-2037-45ec-8129-4ba8d791e86b">
<cybox:Properties xsi:type="MutexObj:MutexObjectType">
<!-- SNIP -->
</cybox:Properties>
<cybox:Relationship xsi:type="cyboxVocabs:ObjectRelationshipVocab-1.0">Created</cybox:Relationship>
</cybox:Related_Object>
</cybox:Object>
The other alternative is to reference that TTP, which would be represented elsewhere:
<cybox:Object id="acme:fileobj-f7304dae-94c6-4592-b943-398e1e6916a7">
<cybox:Properties xsi:type="FileObj:FileObjectType">
<!-- SNIP -->
</cybox:Properties>
<cybox:Related_Objects>
<cybox:Related_Object idref="acme:mutexobj-3c1221bd-2037-45ec-8129-4ba8d791e86b" />
<cybox:Relationship xsi:type="cyboxVocabs:ObjectRelationshipVocab-1.0">Created</cybox:Relationship>
</cybox:Related_Object>
</cybox:Object>
These situations are a judgment call, but when making that judgment you should consider whether the related construct (object in this case) has value individually or only within the context of the parent? If it only has value in the parent, embedding it may be appropriate. Otherwise it's probably better to reference it. If you're unsure, it's generally safer to reference it.
When creating references, you'll use the idref attribute:
<cybox:Related_Object idref="acme:mutexobj-3c1221bd-2037-45ec-8129-4ba8d791e86b" />
When using this idref attribute, you should avoid putting any other attributes or elements in the reference element.
These suggestions only apply when you're creating documents you intend to be human-readable. They simply make the document more readable and easy to validate by XML editors but are not important for automated processing.
For best readability:
To ease validation in XML editors:
Many places in CybOX use controlled vocabularies to represent data. When possible, you should use the vocabularies included in the CybOX defaults. If necessary you can use your own vocabulary or even use strings outside of any vocabularies.
If you do this to add values that you think might be useful for other CybOX users, you should let us know so we can consider adding it to the default vocabulary.
To remove ambiguity regarding the timezone, all times should include an explicit timezone if possible.
CybOX observables are capable of representing both instance observables (specific events or properties that were observed) or pattern observables (patterns of events or properties that may potentially be observed). The conditional nature of patterns is expressed through the use of the @condition attribute on the fields within the observable. If the @condition attribute is set, that denotes that the field is part of a pattern.
Because it doesn't make sense to mix pattern fields with instance field, if @condition is set on any fields it should be set on all fields. You should not mix and match fields with @condition set and fields without @condition set.
Sometimes, a tool will capture properties about a CybOX object that aren't in the schema for that object type. In some cases this is because the schemas need to be expanded to cover that property, but in other cases this is because the tool is collecting derived information or other properties that are not generally represented for that object type.
In either case, those properties should be collected using the
Custom_Properties
element of the object properties. This is essentially a
simple list of key/value pairs:
<cybox:Properties xsi:type="FileObj:FileObjectType">
<cyboxCommon:Custom_Properties>
<cyboxCommon:Property name="Property Name">Property Value</cyboxCommon:Property>
</cyboxCommon:Custom_Properties>
<!-- Other properties from the FileObjectType schema -->
</cybox:Properties>
When capturing the output from a tool, the suggested practice is to set the
@name
attribute of the custom property to the exact field name used in the
tool. If possible, the @datatype
attribute should be set to the datatype that
will be output and the value formatted to fit that datatype's formatting. If
that's not possible, the exact value reported by the tool should be used and
the @datatype
attribute should be omitted.
The Bro tool captures the HTTP Transaction depth of an HTTP connection. In the
Bro output, this field is called trans_depth
and the value will be set to
some integer (whatever the depth is). So the @name
attribute should be set to
trans_depth
, the value should be set to the output from Bro, and the
@datatype
attribute should be set to int
(Integer). That would give you
something like:
<cyboxCommon:Custom_Properties>
<cyboxCommon:Property name="trans_depth" datatype="int">3</cyboxCommon:Property>
</cyboxCommon:Custom_Properties>
The FileObjectType
contains several fields for recording name and path
information about the file.
The following practices are recommended for the use of these fields. Consider a
file located at
C:\Users\ExampleUser\Documents\ProjectX\MeetingNotes_2014-08-01.txt
or
/home/exampleuser/ProjectX/MeetingNotes_2014-08-01.txt
The File_Name
field should specify the base name of the file, including extension
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Name>MeetingNotes_2014-08-01.txt</FileObj:File_Name>
</cybox:Properties>
The File_Path
field should contain the path to the file.
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Path>C:\Users\ExampleUser\Documents\ProjectX\MeetingNotes_2014-08-01.txt</FileObj:File_Path>
</cybox:Properties>
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Path>/home/exampleuser/ProjectX/MeetingNotes_2014-08-01.txt</FileObj:File_Path>
</cybox:Properties>
The File_Path
should contain the name of the file if the File_Name
field is not provided. If the File_Name
field is provided, the name in the
File_Path
field must not conflict with the File_Name
field. If the
File_Path
field does not contain the file name, it should end with a path
separator (slash /
or backslash \
, depending on the operating system).
OK
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Name>MeetingNotes_2014-08-01.txt</FileObj:File_Name>
<FileObj:File_Path>C:\Users\ExampleUser\Documents\ProjectX\MeetingNotes_2014-08-01.txt</FileObj:File_Path>
</cybox:Properties>
BETTER
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Name>MeetingNotes_2014-08-01.txt</FileObj:File_Name>
<FileObj:File_Path>C:\Users\ExampleUser\Documents\ProjectX\</FileObj:File_Path>
</cybox:Properties>
Although the path may be either relative or fully qualified, it should be
fully qualified unless the file which the File_Path
is relative to is
specified via a RelatedObject. If you specify a relative path (with
fully_qualified="false"
), you should include a related object, either
embedded or by reference.
<cybox:Object id="example:File-1">
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Path fully_qualified="false">ProjectX\MeetingNotes_2014-08-01.txt</FileObj:File_Path>
</cybox:Properties>
<cybox:Related_Objects>
<cybox:Related_Object id="example:File-2">
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Path>C:\Users\ExampleUser\Documents\</FileObj:File_Path>
</cybox:Properties>
</cybox:Related_Object>
</cybox:Related_Objects>
</cybox:Object>
The Device_Path
field specifies the path to the device on which the file resides. This is not the drive letter, which has its own property on The WindowsFileObject (though it could be \\.\C:
). On Windows, this could be a path such as \\.\PhysicalDrive1
or \Device\Harddisk0\Partition0
. On Unix-like systems, this could be a path like /dev/sda1
. In general, it is better to include a relationship to a DeviceObject which contains the file, rather than using this field.
The Full_Path
field is used to specify a combination of Device_Path
plus Full_Path
. In general, it is preferable to include this information separately under the component fields rather than the Full_Path
field, unless it is not possible or desired to separate the information apart. Furthermore, this should not be used for files on Unix-like systems, since addressing a file by combination of device path and file path is not typically valid (/dev/sda1/home/exampleuser/ProjectX/MeetingNotes_2014-08-01.txt
).
The File_Extension
field is best used in CybOX patterns, rather than using an EndsWith
condition on any of the other name or path fields.
OK
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Name condition="EndsWith">.txt</FileObj:File_Name>
</cybox:Properties>
BETTER
<cybox:Properties xsi:type="FileObj:FileObjectType">
<FileObj:File_Extension condition="Equals">.txt</FileObj:File_Extension>
</cybox:Properties>