2015-11-08 00:11:48 +00:00
""" Read CVE in your IM client """
# PYTHON STUFFS #######################################################
2014-11-17 13:24:18 +00:00
from bs4 import BeautifulSoup
2015-07-07 10:34:00 +00:00
from urllib . parse import quote
2017-08-03 19:28:56 +00:00
from nemubot . exception import IMException
2015-01-03 19:34:44 +00:00
from nemubot . hooks import hook
2015-11-08 00:11:48 +00:00
from nemubot . tools . web import getURLContent , striphtml
2014-11-17 13:24:18 +00:00
2017-08-27 16:22:53 +00:00
from nemubot . module . more import Response
2014-11-17 13:24:18 +00:00
2017-07-21 05:26:00 +00:00
BASEURL_NIST = ' https://nvd.nist.gov/vuln/detail/ '
2014-11-17 13:24:18 +00:00
2015-11-08 00:11:48 +00:00
# MODULE CORE #########################################################
2014-11-17 13:24:18 +00:00
2017-08-03 19:28:56 +00:00
VULN_DATAS = {
" alert-title " : " vuln-warning-status-name " ,
" alert-content " : " vuln-warning-banner-content " ,
" description " : " vuln-description " ,
" published " : " vuln-published-on " ,
" last_modified " : " vuln-last-modified-on " ,
" source " : " vuln-source " ,
" base_score " : " vuln-cvssv3-base-score-link " ,
" severity " : " vuln-cvssv3-base-score-severity " ,
" impact_score " : " vuln-cvssv3-impact-score " ,
" exploitability_score " : " vuln-cvssv3-exploitability-score " ,
" av " : " vuln-cvssv3-av " ,
" ac " : " vuln-cvssv3-ac " ,
" pr " : " vuln-cvssv3-pr " ,
" ui " : " vuln-cvssv3-ui " ,
" s " : " vuln-cvssv3-s " ,
" c " : " vuln-cvssv3-c " ,
" i " : " vuln-cvssv3-i " ,
" a " : " vuln-cvssv3-a " ,
}
2015-07-07 10:34:00 +00:00
def get_cve ( cve_id ) :
2015-11-08 00:11:48 +00:00
search_url = BASEURL_NIST + quote ( cve_id . upper ( ) )
2014-11-17 13:24:18 +00:00
2015-07-07 10:34:00 +00:00
soup = BeautifulSoup ( getURLContent ( search_url ) )
2015-11-08 00:11:48 +00:00
2017-08-03 19:28:56 +00:00
vuln = { }
2017-07-21 05:26:00 +00:00
2017-08-03 19:28:56 +00:00
for vd in VULN_DATAS :
r = soup . body . find ( attrs = { " data-testid " : VULN_DATAS [ vd ] } )
if r :
vuln [ vd ] = r . text . strip ( )
2017-07-21 05:26:00 +00:00
2017-08-03 19:28:56 +00:00
return vuln
2017-07-21 05:26:00 +00:00
def display_metrics ( av , ac , pr , ui , s , c , i , a , * * kwargs ) :
ret = [ ]
if av != " None " : ret . append ( " Attack Vector: \x02 %s \x0F " % av )
if ac != " None " : ret . append ( " Attack Complexity: \x02 %s \x0F " % ac )
if pr != " None " : ret . append ( " Privileges Required: \x02 %s \x0F " % pr )
if ui != " None " : ret . append ( " User Interaction: \x02 %s \x0F " % ui )
if s != " Unchanged " : ret . append ( " Scope: \x02 %s \x0F " % s )
if c != " None " : ret . append ( " Confidentiality: \x02 %s \x0F " % c )
if i != " None " : ret . append ( " Integrity: \x02 %s \x0F " % i )
if a != " None " : ret . append ( " Availability: \x02 %s \x0F " % a )
return ' , ' . join ( ret )
2015-11-08 00:11:48 +00:00
2014-11-17 13:24:18 +00:00
2015-11-08 00:11:48 +00:00
# MODULE INTERFACE ####################################################
2014-11-17 13:24:18 +00:00
2015-11-08 00:11:48 +00:00
@hook.command ( " cve " ,
help = " Display given CVE " ,
help_usage = { " CVE_ID " : " Display the description of the given CVE " } )
2015-07-07 10:34:00 +00:00
def get_cve_desc ( msg ) :
res = Response ( channel = msg . channel )
2014-11-17 13:24:18 +00:00
2015-07-07 10:34:00 +00:00
for cve_id in msg . args :
if cve_id [ : 3 ] . lower ( ) != ' cve ' :
cve_id = ' cve- ' + cve_id
2014-11-17 13:24:18 +00:00
2017-07-21 05:26:00 +00:00
cve = get_cve ( cve_id )
2017-08-03 19:28:56 +00:00
if not cve :
raise IMException ( " CVE %s doesn ' t exists. " % cve_id )
if " alert-title " in cve or " alert-content " in cve :
alert = " \x02 %s : \x0F %s " % ( cve [ " alert-title " ] if " alert-title " in cve else " " ,
cve [ " alert-content " ] if " alert-content " in cve else " " )
else :
alert = " "
if " base_score " not in cve and " description " in cve :
res . append_message ( " {alert} From \x02 {source} \x0F , last modified on \x02 {last_modified} \x0F . {description} " . format ( alert = alert , * * cve ) , title = cve_id )
else :
metrics = display_metrics ( * * cve )
res . append_message ( " {alert} Base score: \x02 {base_score} {severity} \x0F (impact: \x02 {impact_score} \x0F , exploitability: \x02 {exploitability_score} \x0F ; {metrics} ), from \x02 {source} \x0F , last modified on \x02 {last_modified} \x0F . {description} " . format ( alert = alert , metrics = metrics , * * cve ) , title = cve_id )
2014-11-17 13:24:18 +00:00
2015-07-07 10:34:00 +00:00
return res