misp-modules 2.4.196__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- misp_modules/__init__.py +379 -0
- misp_modules/helpers/__init__.py +1 -0
- misp_modules/helpers/cache.py +84 -0
- misp_modules/lib/__init__.py +4 -0
- misp_modules/lib/_vmray/__init__.py +0 -0
- misp_modules/lib/_vmray/parser.py +1417 -0
- misp_modules/lib/_vmray/rest_api.py +148 -0
- misp_modules/lib/cof2misp/LICENSE-2.0.txt +202 -0
- misp_modules/lib/cof2misp/__init__.py +0 -0
- misp_modules/lib/cof2misp/cof.py +165 -0
- misp_modules/lib/joe_mapping.py +114 -0
- misp_modules/lib/joe_parser.py +573 -0
- misp_modules/lib/lastline_api.py +841 -0
- misp_modules/lib/qintel_helper.py +263 -0
- misp_modules/lib/stix2misp.py +2080 -0
- misp_modules/lib/stix2misp_mapping.py +460 -0
- misp_modules/lib/synonymsToTagNames.json +1 -0
- misp_modules/lib/vt_graph_parser/__init__.py +8 -0
- misp_modules/lib/vt_graph_parser/errors.py +20 -0
- misp_modules/lib/vt_graph_parser/helpers/__init__.py +7 -0
- misp_modules/lib/vt_graph_parser/helpers/parsers.py +88 -0
- misp_modules/lib/vt_graph_parser/helpers/rules.py +304 -0
- misp_modules/lib/vt_graph_parser/helpers/wrappers.py +58 -0
- misp_modules/lib/vt_graph_parser/importers/__init__.py +7 -0
- misp_modules/lib/vt_graph_parser/importers/base.py +98 -0
- misp_modules/lib/vt_graph_parser/importers/pymisp_response.py +73 -0
- misp_modules/modules/__init__.py +4 -0
- misp_modules/modules/action_mod/__init__.py +1 -0
- misp_modules/modules/action_mod/_utils/__init__.py +1 -0
- misp_modules/modules/action_mod/_utils/utils.py +70 -0
- misp_modules/modules/action_mod/mattermost.py +113 -0
- misp_modules/modules/action_mod/slack.py +96 -0
- misp_modules/modules/action_mod/testaction.py +68 -0
- misp_modules/modules/expansion/__init__.py +36 -0
- misp_modules/modules/expansion/_dnsdb_query/COPYRIGHT +27 -0
- misp_modules/modules/expansion/_dnsdb_query/LICENSE +202 -0
- misp_modules/modules/expansion/_dnsdb_query/README.md +162 -0
- misp_modules/modules/expansion/_dnsdb_query/__init__.py +0 -0
- misp_modules/modules/expansion/_dnsdb_query/dnsdb_query.py +327 -0
- misp_modules/modules/expansion/_ransomcoindb/__init__.py +0 -0
- misp_modules/modules/expansion/_ransomcoindb/ransomcoindb.py +96 -0
- misp_modules/modules/expansion/_vulnerability_parser/__init__.py +0 -0
- misp_modules/modules/expansion/_vulnerability_parser/vulnerability_parser.py +118 -0
- misp_modules/modules/expansion/abuseipdb.py +146 -0
- misp_modules/modules/expansion/apiosintds.py +365 -0
- misp_modules/modules/expansion/apivoid.py +133 -0
- misp_modules/modules/expansion/assemblyline_query.py +179 -0
- misp_modules/modules/expansion/assemblyline_submit.py +100 -0
- misp_modules/modules/expansion/backscatter_io.py +84 -0
- misp_modules/modules/expansion/btc_scam_check.py +54 -0
- misp_modules/modules/expansion/btc_steroids.py +238 -0
- misp_modules/modules/expansion/censys_enrich.py +287 -0
- misp_modules/modules/expansion/circl_passivedns.py +85 -0
- misp_modules/modules/expansion/circl_passivessl.py +113 -0
- misp_modules/modules/expansion/clamav.py +129 -0
- misp_modules/modules/expansion/cluster25_expand.py +239 -0
- misp_modules/modules/expansion/countrycode.py +69 -0
- misp_modules/modules/expansion/cpe.py +140 -0
- misp_modules/modules/expansion/crowdsec.py +235 -0
- misp_modules/modules/expansion/crowdstrike_falcon.py +148 -0
- misp_modules/modules/expansion/cuckoo_submit.py +161 -0
- misp_modules/modules/expansion/cve.py +57 -0
- misp_modules/modules/expansion/cve_advanced.py +185 -0
- misp_modules/modules/expansion/cytomic_orion.py +196 -0
- misp_modules/modules/expansion/dbl_spamhaus.py +78 -0
- misp_modules/modules/expansion/dns.py +71 -0
- misp_modules/modules/expansion/docx_enrich.py +71 -0
- misp_modules/modules/expansion/domaintools.py +290 -0
- misp_modules/modules/expansion/eql.py +91 -0
- misp_modules/modules/expansion/eupi.py +86 -0
- misp_modules/modules/expansion/extract_url_components.py +83 -0
- misp_modules/modules/expansion/farsight_passivedns.py +243 -0
- misp_modules/modules/expansion/geoip_asn.py +75 -0
- misp_modules/modules/expansion/geoip_city.py +75 -0
- misp_modules/modules/expansion/geoip_country.py +73 -0
- misp_modules/modules/expansion/google_safe_browsing.py +86 -0
- misp_modules/modules/expansion/google_search.py +57 -0
- misp_modules/modules/expansion/google_threat_intelligence.py +453 -0
- misp_modules/modules/expansion/greynoise.py +346 -0
- misp_modules/modules/expansion/hashdd.py +53 -0
- misp_modules/modules/expansion/hashlookup.py +118 -0
- misp_modules/modules/expansion/hibp.py +62 -0
- misp_modules/modules/expansion/html_to_markdown.py +63 -0
- misp_modules/modules/expansion/hyasinsight.py +881 -0
- misp_modules/modules/expansion/intel471.py +73 -0
- misp_modules/modules/expansion/intelmq_eventdb.py.experimental +67 -0
- misp_modules/modules/expansion/ip2locationio.py +90 -0
- misp_modules/modules/expansion/ipasn.py +70 -0
- misp_modules/modules/expansion/ipinfo.py +112 -0
- misp_modules/modules/expansion/ipqs_fraud_and_risk_scoring.py +633 -0
- misp_modules/modules/expansion/iprep.py +98 -0
- misp_modules/modules/expansion/jinja_template_rendering.py +54 -0
- misp_modules/modules/expansion/joesandbox_query.py +91 -0
- misp_modules/modules/expansion/joesandbox_submit.py +147 -0
- misp_modules/modules/expansion/lastline_query.py +148 -0
- misp_modules/modules/expansion/lastline_submit.py +180 -0
- misp_modules/modules/expansion/macaddress_io.py +130 -0
- misp_modules/modules/expansion/macvendors.py +55 -0
- misp_modules/modules/expansion/malshare_upload.py +107 -0
- misp_modules/modules/expansion/malwarebazaar.py +67 -0
- misp_modules/modules/expansion/mcafee_insights_enrich.py +249 -0
- misp_modules/modules/expansion/mmdb_lookup.py +138 -0
- misp_modules/modules/expansion/module.py.skeleton +44 -0
- misp_modules/modules/expansion/mwdb.py +152 -0
- misp_modules/modules/expansion/ocr_enrich.py +74 -0
- misp_modules/modules/expansion/ods_enrich.py +71 -0
- misp_modules/modules/expansion/odt_enrich.py +61 -0
- misp_modules/modules/expansion/onyphe.py +243 -0
- misp_modules/modules/expansion/onyphe_full.py +387 -0
- misp_modules/modules/expansion/otx.py +167 -0
- misp_modules/modules/expansion/passive_ssh.py +150 -0
- misp_modules/modules/expansion/passivetotal.py +358 -0
- misp_modules/modules/expansion/pdf_enrich.py +58 -0
- misp_modules/modules/expansion/pptx_enrich.py +65 -0
- misp_modules/modules/expansion/qintel_qsentry.py +229 -0
- misp_modules/modules/expansion/qrcode.py +99 -0
- misp_modules/modules/expansion/ransomcoindb.py +82 -0
- misp_modules/modules/expansion/rbl.py +126 -0
- misp_modules/modules/expansion/recordedfuture.py +544 -0
- misp_modules/modules/expansion/reversedns.py +77 -0
- misp_modules/modules/expansion/securitytrails.py +571 -0
- misp_modules/modules/expansion/shodan.py +244 -0
- misp_modules/modules/expansion/sigma_queries.py +61 -0
- misp_modules/modules/expansion/sigma_syntax_validator.py +49 -0
- misp_modules/modules/expansion/sigmf_expand.py +303 -0
- misp_modules/modules/expansion/socialscan.py +108 -0
- misp_modules/modules/expansion/sophoslabs_intelix.py +146 -0
- misp_modules/modules/expansion/sourcecache.py +57 -0
- misp_modules/modules/expansion/stairwell.py +156 -0
- misp_modules/modules/expansion/stix2_pattern_syntax_validator.py +56 -0
- misp_modules/modules/expansion/threatcrowd.py +170 -0
- misp_modules/modules/expansion/threatfox.py +75 -0
- misp_modules/modules/expansion/threatminer.py +152 -0
- misp_modules/modules/expansion/triage_submit.py +119 -0
- misp_modules/modules/expansion/trustar_enrich.py +235 -0
- misp_modules/modules/expansion/urlhaus.py +164 -0
- misp_modules/modules/expansion/urlscan.py +269 -0
- misp_modules/modules/expansion/variotdbs.py +133 -0
- misp_modules/modules/expansion/virustotal.py +311 -0
- misp_modules/modules/expansion/virustotal_public.py +272 -0
- misp_modules/modules/expansion/virustotal_upload.py +91 -0
- misp_modules/modules/expansion/vmray_submit.py +161 -0
- misp_modules/modules/expansion/vmware_nsx.py +628 -0
- misp_modules/modules/expansion/vulndb.py +292 -0
- misp_modules/modules/expansion/vulnerability_lookup.py +324 -0
- misp_modules/modules/expansion/vulners.py +81 -0
- misp_modules/modules/expansion/vysion.py +221 -0
- misp_modules/modules/expansion/whois.py +72 -0
- misp_modules/modules/expansion/whoisfreaks.py +232 -0
- misp_modules/modules/expansion/wiki.py +58 -0
- misp_modules/modules/expansion/xforceexchange.py +189 -0
- misp_modules/modules/expansion/xlsx_enrich.py +63 -0
- misp_modules/modules/expansion/yara_query.py +70 -0
- misp_modules/modules/expansion/yara_syntax_validator.py +49 -0
- misp_modules/modules/expansion/yeti.py +196 -0
- misp_modules/modules/export_mod/__init__.py +3 -0
- misp_modules/modules/export_mod/cef_export.py +93 -0
- misp_modules/modules/export_mod/cisco_firesight_manager_ACL_rule_export.py +150 -0
- misp_modules/modules/export_mod/defender_endpoint_export.py +141 -0
- misp_modules/modules/export_mod/goamlexport.py +255 -0
- misp_modules/modules/export_mod/liteexport.py +97 -0
- misp_modules/modules/export_mod/mass_eql_export.py +106 -0
- misp_modules/modules/export_mod/nexthinkexport.py +131 -0
- misp_modules/modules/export_mod/osqueryexport.py +125 -0
- misp_modules/modules/export_mod/pdfexport.py +107 -0
- misp_modules/modules/export_mod/testexport.py +73 -0
- misp_modules/modules/export_mod/threatStream_misp_export.py +114 -0
- misp_modules/modules/export_mod/threat_connect_export.py +125 -0
- misp_modules/modules/export_mod/virustotal_collections.py +141 -0
- misp_modules/modules/export_mod/vt_graph.py +120 -0
- misp_modules/modules/export_mod/yara_export.py +290 -0
- misp_modules/modules/import_mod/__init__.py +22 -0
- misp_modules/modules/import_mod/cof2misp.py +264 -0
- misp_modules/modules/import_mod/csvimport.py +319 -0
- misp_modules/modules/import_mod/cuckooimport.py +749 -0
- misp_modules/modules/import_mod/email_import.py +294 -0
- misp_modules/modules/import_mod/goamlimport.py +188 -0
- misp_modules/modules/import_mod/import_blueprint.py +93 -0
- misp_modules/modules/import_mod/joe_import.py +74 -0
- misp_modules/modules/import_mod/lastline_import.py +160 -0
- misp_modules/modules/import_mod/mispjson.py +73 -0
- misp_modules/modules/import_mod/ocr.py +122 -0
- misp_modules/modules/import_mod/openiocimport.py +99 -0
- misp_modules/modules/import_mod/taxii21.py +383 -0
- misp_modules/modules/import_mod/testimport.py +73 -0
- misp_modules/modules/import_mod/threatanalyzer_import.py +552 -0
- misp_modules/modules/import_mod/url_import.py +97 -0
- misp_modules/modules/import_mod/vmray_import.py +96 -0
- misp_modules/modules/import_mod/vmray_summary_json_import.py +87 -0
- misp_modules-2.4.196.dist-info/LICENSE +661 -0
- misp_modules-2.4.196.dist-info/METADATA +281 -0
- misp_modules-2.4.196.dist-info/RECORD +194 -0
- misp_modules-2.4.196.dist-info/WHEEL +4 -0
- misp_modules-2.4.196.dist-info/entry_points.txt +3 -0
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Export module for converting MISP events into Endgame EQL queries
|
|
3
|
+
"""
|
|
4
|
+
import base64
|
|
5
|
+
import io
|
|
6
|
+
import json
|
|
7
|
+
import logging
|
|
8
|
+
|
|
9
|
+
misperrors = {"error": "Error"}
|
|
10
|
+
|
|
11
|
+
moduleinfo = {
|
|
12
|
+
'version': '0.1',
|
|
13
|
+
'author': '92 COS DOM',
|
|
14
|
+
'description': 'Export MISP event in Event Query Language',
|
|
15
|
+
'module-type': ['export'],
|
|
16
|
+
'name': 'EQL Query Export',
|
|
17
|
+
'logo': 'eql.png',
|
|
18
|
+
'requirements': [],
|
|
19
|
+
'features': 'This module produces EQL queries for all relevant attributes in a MISP event.',
|
|
20
|
+
'references': ['https://eql.readthedocs.io/en/latest/'],
|
|
21
|
+
'input': 'MISP Event attributes',
|
|
22
|
+
'output': 'Text file containing one or more EQL queries',
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
# Map of MISP fields => Endgame fields
|
|
26
|
+
fieldmap = {
|
|
27
|
+
"ip-src": "source_address",
|
|
28
|
+
"ip-dst": "destination_address",
|
|
29
|
+
"filename": "file_name"
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
# Describe what events have what fields
|
|
33
|
+
event_types = {
|
|
34
|
+
"source_address": "network",
|
|
35
|
+
"destination_address": "network",
|
|
36
|
+
"file_name": "file"
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
# combine all the MISP fields from fieldmap into one big list
|
|
40
|
+
mispattributes = {
|
|
41
|
+
"input": list(fieldmap.keys())
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
def handler(q=False):
|
|
46
|
+
"""
|
|
47
|
+
Convert a MISP query into a CSV file matching the ThreatConnect Structured Import file format.
|
|
48
|
+
Input
|
|
49
|
+
q: Query dictionary
|
|
50
|
+
"""
|
|
51
|
+
if q is False or not q:
|
|
52
|
+
return False
|
|
53
|
+
|
|
54
|
+
# Check if we were given a configuration
|
|
55
|
+
request = json.loads(q)
|
|
56
|
+
config = request.get("config", {"Default_Source": ""})
|
|
57
|
+
logging.info("Setting config to: %s", config)
|
|
58
|
+
|
|
59
|
+
response = io.StringIO()
|
|
60
|
+
|
|
61
|
+
# start parsing MISP data
|
|
62
|
+
queryDict = {}
|
|
63
|
+
for event in request["data"]:
|
|
64
|
+
for attribute in event["Attribute"]:
|
|
65
|
+
if attribute["type"] in mispattributes["input"]:
|
|
66
|
+
logging.debug("Adding %s to EQL query", attribute["value"])
|
|
67
|
+
event_type = event_types[fieldmap[attribute["type"]]]
|
|
68
|
+
if event_type not in queryDict.keys():
|
|
69
|
+
queryDict[event_type] = {}
|
|
70
|
+
queryDict[event_type][attribute["value"]] = fieldmap[attribute["type"]]
|
|
71
|
+
i = 0
|
|
72
|
+
for query in queryDict.keys():
|
|
73
|
+
response.write("{} where\n".format(query))
|
|
74
|
+
for value in queryDict[query].keys():
|
|
75
|
+
if i != 0:
|
|
76
|
+
response.write(" or\n")
|
|
77
|
+
response.write("\t{} == \"{}\"".format(queryDict[query][value], value))
|
|
78
|
+
i += 1
|
|
79
|
+
|
|
80
|
+
return {"response": [], "data": str(base64.b64encode(bytes(response.getvalue(), 'utf-8')), 'utf-8')}
|
|
81
|
+
|
|
82
|
+
|
|
83
|
+
def introspection():
|
|
84
|
+
"""
|
|
85
|
+
Relay the supported attributes to MISP.
|
|
86
|
+
No Input
|
|
87
|
+
Output
|
|
88
|
+
Dictionary of supported MISP attributes
|
|
89
|
+
"""
|
|
90
|
+
modulesetup = {
|
|
91
|
+
"responseType": "application/txt",
|
|
92
|
+
"outputFileExtension": "txt",
|
|
93
|
+
"userConfig": {},
|
|
94
|
+
"inputSource": []
|
|
95
|
+
}
|
|
96
|
+
return modulesetup
|
|
97
|
+
|
|
98
|
+
|
|
99
|
+
def version():
|
|
100
|
+
"""
|
|
101
|
+
Relay module version and associated metadata to MISP.
|
|
102
|
+
No Input
|
|
103
|
+
Output
|
|
104
|
+
moduleinfo: metadata output containing all potential configuration values
|
|
105
|
+
"""
|
|
106
|
+
return moduleinfo
|
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Export module for coverting MISP events into Nexthink NXQL queries.
|
|
3
|
+
Source: https://github.com/HacknowledgeCH/misp-modules/blob/master/misp_modules/modules/export_mod/nexthinkexport.py
|
|
4
|
+
Config['Period'] : allows to define period over witch to look for IOC from now (15m, 1d, 2w, 30d, ...), see Nexthink data model documentation
|
|
5
|
+
"""
|
|
6
|
+
|
|
7
|
+
import base64
|
|
8
|
+
import json
|
|
9
|
+
|
|
10
|
+
misperrors = {"error": "Error"}
|
|
11
|
+
|
|
12
|
+
types_to_use = ['sha1', 'sha256', 'md5', 'domain']
|
|
13
|
+
|
|
14
|
+
userConfig = {
|
|
15
|
+
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
moduleconfig = ["Period"]
|
|
19
|
+
inputSource = ['event']
|
|
20
|
+
|
|
21
|
+
outputFileExtension = 'nxql'
|
|
22
|
+
responseType = 'application/txt'
|
|
23
|
+
|
|
24
|
+
moduleinfo = {
|
|
25
|
+
'version': '1.0',
|
|
26
|
+
'author': 'Julien Bachmann, Hacknowledge',
|
|
27
|
+
'description': 'Nexthink NXQL query export module',
|
|
28
|
+
'module-type': ['export'],
|
|
29
|
+
'name': 'Nexthink NXQL Export',
|
|
30
|
+
'logo': 'nexthink.svg',
|
|
31
|
+
'requirements': [],
|
|
32
|
+
'features': 'This module export an event as Nexthink NXQL queries that can then be used in your own python3 tool or from wget/powershell',
|
|
33
|
+
'references': ['https://doc.nexthink.com/Documentation/Nexthink/latest/APIAndIntegrations/IntroducingtheWebAPIV2'],
|
|
34
|
+
'input': 'MISP Event attributes',
|
|
35
|
+
'output': 'Nexthink NXQL queries',
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
def handle_sha1(value, period):
|
|
40
|
+
query = '''select ((binary (executable_name version)) (user (name)) (device (name last_ip_address)) (execution (binary_path start_time)))
|
|
41
|
+
(from (binary user device execution)
|
|
42
|
+
(where binary (eq sha1 (sha1 %s)))
|
|
43
|
+
(between now-%s now))
|
|
44
|
+
(limit 1000)
|
|
45
|
+
''' % (value, period)
|
|
46
|
+
return query.replace('\n', ' ')
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
def handle_sha256(value, period):
|
|
50
|
+
query = '''select ((binary (executable_name version)) (user (name)) (device (name last_ip_address)) (execution (binary_path start_time)))
|
|
51
|
+
(from (binary user device execution)
|
|
52
|
+
(where binary (eq sha256 (sha256 %s)))
|
|
53
|
+
(between now-%s now))
|
|
54
|
+
(limit 1000)
|
|
55
|
+
''' % (value, period)
|
|
56
|
+
return query.replace('\n', ' ')
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
def handle_md5(value, period):
|
|
60
|
+
query = '''select ((binary (executable_name version)) (user (name)) (device (name last_ip_address)) (execution (binary_path start_time)))
|
|
61
|
+
(from (binary user device execution)
|
|
62
|
+
(where binary (eq hash (md5 %s)))
|
|
63
|
+
(between now-%s now))
|
|
64
|
+
(limit 1000)
|
|
65
|
+
''' % (value, period)
|
|
66
|
+
return query.replace('\n', ' ')
|
|
67
|
+
|
|
68
|
+
|
|
69
|
+
def handle_domain(value, period):
|
|
70
|
+
query = '''select ((device name) (device (name last_ip_address)) (user name)(user department) (binary executable_name)(binary application_name)(binary description)(binary application_category)(binary (executable_name version)) (binary #"Suspicious binary")(binary first_seen)(binary last_seen)(binary threat_level)(binary hash) (binary paths)
|
|
71
|
+
(destination name)(domain name) (domain domain_category)(domain hosting_country)(domain protocol)(domain threat_level) (port port_number)(web_request incoming_traffic)(web_request outgoing_traffic))
|
|
72
|
+
(from (web_request device user binary executable destination domain port)
|
|
73
|
+
(where domain (eq name(string %s)))
|
|
74
|
+
(between now-%s now))
|
|
75
|
+
(limit 1000)
|
|
76
|
+
''' % (value, period)
|
|
77
|
+
return query.replace('\n', ' ')
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
handlers = {
|
|
81
|
+
'sha1': handle_sha1,
|
|
82
|
+
'sha256': handle_sha256,
|
|
83
|
+
'md5': handle_md5,
|
|
84
|
+
'domain': handle_domain
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
|
|
88
|
+
def handler(q=False):
|
|
89
|
+
if q is False:
|
|
90
|
+
return False
|
|
91
|
+
r = {'results': []}
|
|
92
|
+
request = json.loads(q)
|
|
93
|
+
config = request.get("config", {"Period": ""})
|
|
94
|
+
output = ''
|
|
95
|
+
|
|
96
|
+
for event in request["data"]:
|
|
97
|
+
for attribute in event["Attribute"]:
|
|
98
|
+
if attribute['type'] in types_to_use:
|
|
99
|
+
output = output + handlers[attribute['type']](attribute['value'], config['Period']) + '\n'
|
|
100
|
+
r = {"response": [], "data": str(base64.b64encode(bytes(output, 'utf-8')), 'utf-8')}
|
|
101
|
+
return r
|
|
102
|
+
|
|
103
|
+
|
|
104
|
+
def introspection():
|
|
105
|
+
modulesetup = {}
|
|
106
|
+
try:
|
|
107
|
+
responseType
|
|
108
|
+
modulesetup['responseType'] = responseType
|
|
109
|
+
except NameError:
|
|
110
|
+
pass
|
|
111
|
+
try:
|
|
112
|
+
userConfig
|
|
113
|
+
modulesetup['userConfig'] = userConfig
|
|
114
|
+
except NameError:
|
|
115
|
+
pass
|
|
116
|
+
try:
|
|
117
|
+
outputFileExtension
|
|
118
|
+
modulesetup['outputFileExtension'] = outputFileExtension
|
|
119
|
+
except NameError:
|
|
120
|
+
pass
|
|
121
|
+
try:
|
|
122
|
+
inputSource
|
|
123
|
+
modulesetup['inputSource'] = inputSource
|
|
124
|
+
except NameError:
|
|
125
|
+
pass
|
|
126
|
+
return modulesetup
|
|
127
|
+
|
|
128
|
+
|
|
129
|
+
def version():
|
|
130
|
+
moduleinfo['config'] = moduleconfig
|
|
131
|
+
return moduleinfo
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Export module for coverting MISP events into OSQuery queries.
|
|
3
|
+
Source: https://github.com/0xmilkmix/misp-modules/blob/master/misp_modules/modules/export_mod/osqueryexport.py
|
|
4
|
+
"""
|
|
5
|
+
|
|
6
|
+
import base64
|
|
7
|
+
import json
|
|
8
|
+
import re
|
|
9
|
+
|
|
10
|
+
misperrors = {"error": "Error"}
|
|
11
|
+
|
|
12
|
+
types_to_use = ['regkey', 'regkey|value', 'mutex', 'windows-service-displayname', 'windows-scheduled-task', 'yara']
|
|
13
|
+
|
|
14
|
+
userConfig = {
|
|
15
|
+
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
moduleconfig = []
|
|
19
|
+
inputSource = ['event']
|
|
20
|
+
|
|
21
|
+
outputFileExtension = 'conf'
|
|
22
|
+
responseType = 'application/txt'
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
moduleinfo = {
|
|
26
|
+
'version': '1.0',
|
|
27
|
+
'author': 'Julien Bachmann, Hacknowledge',
|
|
28
|
+
'description': 'OSQuery export of a MISP event.',
|
|
29
|
+
'module-type': ['export'],
|
|
30
|
+
'name': 'OSQuery Export',
|
|
31
|
+
'logo': 'osquery.png',
|
|
32
|
+
'requirements': [],
|
|
33
|
+
'features': 'This module export an event as osquery queries that can be used in packs or in fleet management solution like Kolide.',
|
|
34
|
+
'references': [],
|
|
35
|
+
'input': 'MISP Event attributes',
|
|
36
|
+
'output': 'osquery SQL queries',
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
|
|
40
|
+
def handle_regkey(value):
|
|
41
|
+
rep = {'HKCU': 'HKEY_USERS\\%', 'HKLM': 'HKEY_LOCAL_MACHINE'}
|
|
42
|
+
rep = dict((re.escape(k), v) for k, v in rep.items())
|
|
43
|
+
pattern = re.compile("|".join(rep.keys()))
|
|
44
|
+
value = pattern.sub(lambda m: rep[re.escape(m.group(0))], value)
|
|
45
|
+
return 'SELECT * FROM registry WHERE path LIKE \'%s\';' % value
|
|
46
|
+
|
|
47
|
+
|
|
48
|
+
def handle_regkeyvalue(value):
|
|
49
|
+
key, value = value.split('|')
|
|
50
|
+
rep = {'HKCU': 'HKEY_USERS\\%', 'HKLM': 'HKEY_LOCAL_MACHINE'}
|
|
51
|
+
rep = dict((re.escape(k), v) for k, v in rep.items())
|
|
52
|
+
pattern = re.compile("|".join(rep.keys()))
|
|
53
|
+
key = pattern.sub(lambda m: rep[re.escape(m.group(0))], key)
|
|
54
|
+
return 'SELECT * FROM registry WHERE path LIKE \'%s\' AND data LIKE \'%s\';' % (key, value)
|
|
55
|
+
|
|
56
|
+
|
|
57
|
+
def handle_mutex(value):
|
|
58
|
+
return 'SELECT * FROM winbaseobj WHERE object_name LIKE \'%s\';' % value
|
|
59
|
+
|
|
60
|
+
|
|
61
|
+
def handle_service(value):
|
|
62
|
+
return 'SELECT * FROM services WHERE display_name LIKE \'%s\' OR name like \'%s\';' % (value, value)
|
|
63
|
+
|
|
64
|
+
|
|
65
|
+
def handle_yara(value):
|
|
66
|
+
return 'not implemented yet, not sure it\'s easily feasible w/o dropping the sig on the hosts first'
|
|
67
|
+
|
|
68
|
+
|
|
69
|
+
def handle_scheduledtask(value):
|
|
70
|
+
return 'SELECT * FROM scheduled_tasks WHERE name LIKE \'%s\';' % value
|
|
71
|
+
|
|
72
|
+
|
|
73
|
+
handlers = {
|
|
74
|
+
'regkey': handle_regkey,
|
|
75
|
+
'regkey|value': handle_regkeyvalue,
|
|
76
|
+
'mutex': handle_mutex,
|
|
77
|
+
'windows-service-displayname': handle_service,
|
|
78
|
+
'windows-scheduled-task': handle_scheduledtask,
|
|
79
|
+
'yara': handle_yara
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
|
|
83
|
+
def handler(q=False):
|
|
84
|
+
if q is False:
|
|
85
|
+
return False
|
|
86
|
+
r = {'results': []}
|
|
87
|
+
request = json.loads(q)
|
|
88
|
+
output = ''
|
|
89
|
+
|
|
90
|
+
for event in request["data"]:
|
|
91
|
+
for attribute in event["Attribute"]:
|
|
92
|
+
if attribute['type'] in types_to_use:
|
|
93
|
+
output = output + handlers[attribute['type']](attribute['value']) + '\n'
|
|
94
|
+
r = {"response": [], "data": str(base64.b64encode(bytes(output, 'utf-8')), 'utf-8')}
|
|
95
|
+
return r
|
|
96
|
+
|
|
97
|
+
|
|
98
|
+
def introspection():
|
|
99
|
+
modulesetup = {}
|
|
100
|
+
try:
|
|
101
|
+
responseType
|
|
102
|
+
modulesetup['responseType'] = responseType
|
|
103
|
+
except NameError:
|
|
104
|
+
pass
|
|
105
|
+
try:
|
|
106
|
+
userConfig
|
|
107
|
+
modulesetup['userConfig'] = userConfig
|
|
108
|
+
except NameError:
|
|
109
|
+
pass
|
|
110
|
+
try:
|
|
111
|
+
outputFileExtension
|
|
112
|
+
modulesetup['outputFileExtension'] = outputFileExtension
|
|
113
|
+
except NameError:
|
|
114
|
+
pass
|
|
115
|
+
try:
|
|
116
|
+
inputSource
|
|
117
|
+
modulesetup['inputSource'] = inputSource
|
|
118
|
+
except NameError:
|
|
119
|
+
pass
|
|
120
|
+
return modulesetup
|
|
121
|
+
|
|
122
|
+
|
|
123
|
+
def version():
|
|
124
|
+
moduleinfo['config'] = moduleconfig
|
|
125
|
+
return moduleinfo
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
#!/usr/bin/env python3
|
|
2
|
+
# -*- coding: utf-8 -*-
|
|
3
|
+
|
|
4
|
+
import json
|
|
5
|
+
|
|
6
|
+
from pymisp import MISPEvent
|
|
7
|
+
from pymisp.tools import reportlab_generator
|
|
8
|
+
|
|
9
|
+
misperrors = {'error': 'Error'}
|
|
10
|
+
|
|
11
|
+
moduleinfo = {
|
|
12
|
+
'version': '2',
|
|
13
|
+
'author': 'Vincent Falconieri (prev. Raphaël Vinot)',
|
|
14
|
+
'description': 'Simple export of a MISP event to PDF.',
|
|
15
|
+
'module-type': ['export'],
|
|
16
|
+
'name': 'Event to PDF Export',
|
|
17
|
+
'require_standard_format': True,
|
|
18
|
+
'logo': '',
|
|
19
|
+
'requirements': ['PyMISP', 'reportlab'],
|
|
20
|
+
'features': "The module takes care of the PDF file building, and work with any MISP Event. Except the requirement of reportlab, used to create the file, there is no special feature concerning the Event. Some parameters can be given through the config dict. 'MISP_base_url_for_dynamic_link' is your MISP URL, to attach an hyperlink to your event on your MISP instance from the PDF. Keep it clear to avoid hyperlinks in the generated pdf.\n 'MISP_name_for_metadata' is your CERT or MISP instance name. Used as text in the PDF' metadata\n 'Activate_textual_description' is a boolean (True or void) to activate the textual description/header abstract of an event\n 'Activate_galaxy_description' is a boolean (True or void) to activate the description of event related galaxies.\n 'Activate_related_events' is a boolean (True or void) to activate the description of related event. Be aware this might leak information on confidential events linked to the current event !\n 'Activate_internationalization_fonts' is a boolean (True or void) to activate Noto fonts instead of default fonts (Helvetica). This allows the support of CJK alphabet. Be sure to have followed the procedure to download Noto fonts (~70Mo) in the right place (/tools/pdf_fonts/Noto_TTF), to allow PyMisp to find and use them during PDF generation.\n 'Custom_fonts_path' is a text (path or void) to the TTF file of your choice, to create the PDF with it. Be aware the PDF won't support bold/italic/special style anymore with this option ",
|
|
21
|
+
'references': ['https://acrobat.adobe.com/us/en/acrobat/about-adobe-pdf.html'],
|
|
22
|
+
'input': 'MISP Event',
|
|
23
|
+
'output': 'MISP Event in a PDF file.',
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
# config fields that your code expects from the site admin
|
|
27
|
+
moduleconfig = ["MISP_base_url_for_dynamic_link", "MISP_name_for_metadata", "Activate_textual_description", "Activate_galaxy_description", "Activate_related_events", "Activate_internationalization_fonts", "Custom_fonts_path"]
|
|
28
|
+
mispattributes = {}
|
|
29
|
+
|
|
30
|
+
outputFileExtension = "pdf"
|
|
31
|
+
responseType = "application/pdf"
|
|
32
|
+
|
|
33
|
+
types_to_attach = ['ip-dst', 'url', 'domain']
|
|
34
|
+
objects_to_attach = ['domain-ip']
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
class ReportGenerator():
|
|
38
|
+
def __init__(self):
|
|
39
|
+
self.report = ''
|
|
40
|
+
|
|
41
|
+
def from_remote(self, event_id):
|
|
42
|
+
from pymisp import PyMISP
|
|
43
|
+
from keys import misp_url, misp_key, misp_verifycert
|
|
44
|
+
misp = PyMISP(misp_url, misp_key, misp_verifycert)
|
|
45
|
+
result = misp.get(event_id)
|
|
46
|
+
self.misp_event = MISPEvent()
|
|
47
|
+
self.misp_event.load(result)
|
|
48
|
+
|
|
49
|
+
def from_event(self, event):
|
|
50
|
+
self.misp_event = MISPEvent()
|
|
51
|
+
self.misp_event.load(event)
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
def handler(q=False):
|
|
55
|
+
if q is False:
|
|
56
|
+
return False
|
|
57
|
+
|
|
58
|
+
request = json.loads(q)
|
|
59
|
+
|
|
60
|
+
if 'data' not in request:
|
|
61
|
+
return False
|
|
62
|
+
|
|
63
|
+
config = {}
|
|
64
|
+
|
|
65
|
+
# Construct config object for reportlab_generator
|
|
66
|
+
for config_item in moduleconfig:
|
|
67
|
+
if (request.get('config')) and (request['config'].get(config_item) is not None):
|
|
68
|
+
config[config_item] = request['config'].get(config_item)
|
|
69
|
+
|
|
70
|
+
for evt in request['data']:
|
|
71
|
+
misp_event = MISPEvent()
|
|
72
|
+
misp_event.load(evt)
|
|
73
|
+
|
|
74
|
+
pdf = reportlab_generator.get_base64_from_value(reportlab_generator.convert_event_in_pdf_buffer(misp_event, config))
|
|
75
|
+
|
|
76
|
+
return {'response': [], 'data': str(pdf, 'utf-8')}
|
|
77
|
+
|
|
78
|
+
|
|
79
|
+
def introspection():
|
|
80
|
+
modulesetup = {}
|
|
81
|
+
try:
|
|
82
|
+
responseType
|
|
83
|
+
modulesetup['responseType'] = responseType
|
|
84
|
+
except NameError:
|
|
85
|
+
pass
|
|
86
|
+
|
|
87
|
+
try:
|
|
88
|
+
userConfig
|
|
89
|
+
modulesetup['userConfig'] = userConfig
|
|
90
|
+
except NameError:
|
|
91
|
+
pass
|
|
92
|
+
try:
|
|
93
|
+
outputFileExtension
|
|
94
|
+
modulesetup['outputFileExtension'] = outputFileExtension
|
|
95
|
+
except NameError:
|
|
96
|
+
pass
|
|
97
|
+
try:
|
|
98
|
+
inputSource
|
|
99
|
+
modulesetup['inputSource'] = inputSource
|
|
100
|
+
except NameError:
|
|
101
|
+
pass
|
|
102
|
+
return modulesetup
|
|
103
|
+
|
|
104
|
+
|
|
105
|
+
def version():
|
|
106
|
+
moduleinfo['config'] = moduleconfig
|
|
107
|
+
return moduleinfo
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
import json
|
|
2
|
+
import base64
|
|
3
|
+
|
|
4
|
+
misperrors = {'error': 'Error'}
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
userConfig = {
|
|
8
|
+
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
moduleconfig = []
|
|
12
|
+
|
|
13
|
+
# fixed for now, options in the future:
|
|
14
|
+
# event, attribute, event-collection, attribute-collection
|
|
15
|
+
inputSource = ['event']
|
|
16
|
+
|
|
17
|
+
outputFileExtension = 'txt'
|
|
18
|
+
responseType = 'application/txt'
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
moduleinfo = {
|
|
22
|
+
'version': '0.1',
|
|
23
|
+
'author': 'Andras Iklody',
|
|
24
|
+
'description': 'Skeleton export module.',
|
|
25
|
+
'name': 'Test Export',
|
|
26
|
+
'module-type': ['export'],
|
|
27
|
+
'logo': '',
|
|
28
|
+
'requirements': [],
|
|
29
|
+
'features': '',
|
|
30
|
+
'references': [],
|
|
31
|
+
'input': '',
|
|
32
|
+
'output': '',
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
def handler(q=False):
|
|
37
|
+
if q is False:
|
|
38
|
+
return False
|
|
39
|
+
r = {'results': []}
|
|
40
|
+
result = json.loads(q) # noqa
|
|
41
|
+
output = '' # Insert your magic here!
|
|
42
|
+
r = {"data": base64.b64encode(output.encode('utf-8')).decode('utf-8')}
|
|
43
|
+
return r
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
def introspection():
|
|
47
|
+
modulesetup = {}
|
|
48
|
+
try:
|
|
49
|
+
responseType
|
|
50
|
+
modulesetup['responseType'] = responseType
|
|
51
|
+
except NameError:
|
|
52
|
+
pass
|
|
53
|
+
try:
|
|
54
|
+
userConfig
|
|
55
|
+
modulesetup['userConfig'] = userConfig
|
|
56
|
+
except NameError:
|
|
57
|
+
pass
|
|
58
|
+
try:
|
|
59
|
+
outputFileExtension
|
|
60
|
+
modulesetup['outputFileExtension'] = outputFileExtension
|
|
61
|
+
except NameError:
|
|
62
|
+
pass
|
|
63
|
+
try:
|
|
64
|
+
inputSource
|
|
65
|
+
modulesetup['inputSource'] = inputSource
|
|
66
|
+
except NameError:
|
|
67
|
+
pass
|
|
68
|
+
return modulesetup
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
def version():
|
|
72
|
+
moduleinfo['config'] = moduleconfig
|
|
73
|
+
return moduleinfo
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Export module for coverting MISP events into ThreatStream Structured Import files. Based of work by the CenturyLink CIRT.
|
|
3
|
+
Source: https://github.com/MISP/misp-modules/blob/master/misp_modules/modules/export_mod/threat_connect_export.py
|
|
4
|
+
"""
|
|
5
|
+
|
|
6
|
+
import base64
|
|
7
|
+
import csv
|
|
8
|
+
import io
|
|
9
|
+
import json
|
|
10
|
+
import logging
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
misperrors = {"error": "Error"}
|
|
14
|
+
|
|
15
|
+
moduleinfo = {
|
|
16
|
+
'version': '1.0',
|
|
17
|
+
'author': 'Robert Nixon, based off of the ThreatConnect MISP Module written by the CenturyLink CIRT',
|
|
18
|
+
'description': 'Module to export a structured CSV file for uploading to threatStream.',
|
|
19
|
+
'module-type': ['export'],
|
|
20
|
+
'name': 'ThreatStream Export',
|
|
21
|
+
'logo': 'threatstream.png',
|
|
22
|
+
'requirements': ['csv'],
|
|
23
|
+
'features': 'The module takes a MISP event in input, to look every attribute. Each attribute matching with some predefined types is then exported in a CSV format recognized by ThreatStream.',
|
|
24
|
+
'references': ['https://www.anomali.com/platform/threatstream', 'https://github.com/threatstream'],
|
|
25
|
+
'input': 'MISP Event attributes',
|
|
26
|
+
'output': 'ThreatStream CSV format file',
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
moduleconfig = []
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
# Map of MISP fields => ThreatStream itypes, you can modify this to your liking
|
|
34
|
+
fieldmap = {
|
|
35
|
+
"domain": "mal_domain",
|
|
36
|
+
"hostname": "mal_domain",
|
|
37
|
+
"ip-src": "mal_ip",
|
|
38
|
+
"ip-dst": "mal_ip",
|
|
39
|
+
"email-src": "phish_email",
|
|
40
|
+
"url": "mal_url",
|
|
41
|
+
"md5": "mal_md5",
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
# combine all the MISP fields from fieldmap into one big list
|
|
45
|
+
mispattributes = {
|
|
46
|
+
"input": list(fieldmap.keys())
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
def handler(q=False):
|
|
51
|
+
"""
|
|
52
|
+
Convert a MISP query into a CSV file matching the ThreatStream Structured Import file format.
|
|
53
|
+
Input
|
|
54
|
+
q: Query dictionary
|
|
55
|
+
"""
|
|
56
|
+
if q is False or not q:
|
|
57
|
+
return False
|
|
58
|
+
|
|
59
|
+
request = json.loads(q)
|
|
60
|
+
|
|
61
|
+
response = io.StringIO()
|
|
62
|
+
writer = csv.DictWriter(response, fieldnames=["value", "itype", "tags"])
|
|
63
|
+
writer.writeheader()
|
|
64
|
+
|
|
65
|
+
# start parsing MISP data
|
|
66
|
+
for event in request["data"]:
|
|
67
|
+
for attribute in event["Attribute"]:
|
|
68
|
+
if attribute["type"] in mispattributes["input"]:
|
|
69
|
+
logging.debug("Adding %s to structured CSV export of ThreatStream Export", attribute["value"])
|
|
70
|
+
if "|" in attribute["type"]:
|
|
71
|
+
# if the attribute type has multiple values, line it up with the corresponding ThreatStream values in fieldmap
|
|
72
|
+
indicators = tuple(attribute["value"].split("|"))
|
|
73
|
+
ts_types = tuple(fieldmap[attribute["type"]].split("|"))
|
|
74
|
+
for i, indicator in enumerate(indicators):
|
|
75
|
+
writer.writerow({
|
|
76
|
+
"value": indicator,
|
|
77
|
+
"itype": ts_types[i],
|
|
78
|
+
"tags": attribute["comment"]
|
|
79
|
+
})
|
|
80
|
+
else:
|
|
81
|
+
writer.writerow({
|
|
82
|
+
"itype": fieldmap[attribute["type"]],
|
|
83
|
+
"value": attribute["value"],
|
|
84
|
+
"tags": attribute["comment"]
|
|
85
|
+
})
|
|
86
|
+
|
|
87
|
+
return {"response": [], "data": str(base64.b64encode(bytes(response.getvalue(), 'utf-8')), 'utf-8')}
|
|
88
|
+
|
|
89
|
+
|
|
90
|
+
def introspection():
|
|
91
|
+
"""
|
|
92
|
+
Relay the supported attributes to MISP.
|
|
93
|
+
No Input
|
|
94
|
+
Output
|
|
95
|
+
Dictionary of supported MISP attributes
|
|
96
|
+
"""
|
|
97
|
+
modulesetup = {
|
|
98
|
+
"responseType": "application/txt",
|
|
99
|
+
"outputFileExtension": "csv",
|
|
100
|
+
"userConfig": {},
|
|
101
|
+
"inputSource": []
|
|
102
|
+
}
|
|
103
|
+
return modulesetup
|
|
104
|
+
|
|
105
|
+
|
|
106
|
+
def version():
|
|
107
|
+
"""
|
|
108
|
+
Relay module version and associated metadata to MISP.
|
|
109
|
+
No Input
|
|
110
|
+
Output
|
|
111
|
+
moduleinfo: metadata output containing all potential configuration values
|
|
112
|
+
"""
|
|
113
|
+
moduleinfo["config"] = moduleconfig
|
|
114
|
+
return moduleinfo
|