Wpbullet - A Static Code Analysis For Wordpress (And Php)
H5N1 static code analysis for WordPress Plugins/Themes (and PHP)
Installation
Simply clone the repository, install requirements as well as run the script
$ git clone https://github.com/webarx-security/wpbullet wpbullet
$ cd wpbullet
$ pip install -r requirements.txt
$ python wpbullet.py
Usage
Available options:
--path (required) System path or download URL Examples: --path="/path/to/plugin" --path="https://wordpress.org/plugins/example-plugin" --path="https://downloads.wordpress.org/plugin/example-plugin.1.5.zip" --enabled (optional) Check exclusively for given modules, ex. --enabled="SQLInjection,CrossSiteScripting" --disabled (optional) Don't banking concern check for given modules, ex. --disabled="SQLInjection,CrossSiteScripting" --cleanup (optional) Automatically take content of .temp folder later scanning remotely downloaded plugin $ python wpbullet.py --path="/var/www/wp-content/plugins/plugin-name"
Creating modules
Creating a module is flexible as well as allows for override of the
BaseClass
methods for each module too every bit creating their ain methodsEach module inwards
Modules
directory is implementing properties as well as methods from core.modules.BaseClass
, thus each module's required parameter is BaseClass
Once created, module needs to hold upward imported inwards
modules/__init__.py
. Module as well as cast advert must hold upward consistent inwards lodge to module to hold upward loaded.If y'all are opening clit asking to add together novel module, delight render unit of measurement tests for your module every bit well.
Module template
Modules/ExampleVulnerability.py
from core.modules import BaseClass cast ExampleVulnerability(object): # Vulnerability advert advert = "Cross-site Scripting" # Vulnerability severity severity = "Low-Medium" # Functions causing vulnerability functions = [ "print" "echo" ] # Functions/regex that forestall exploitation blacklist = [ "htmlspecialchars", "esc_attr" ]
Overriding regex gibe pattern
Regex designing is beingness generated inwards
core.modules.BaseClass.build_pattern
as well as so tin dismiss hold upward overwritten inwards each module class.Modules/ExampleVulnerability.py
import re-create ... # Build dynamic regex designing to locate vulnerabilities inwards given content def build_pattern(self, content, file): user_input = copy.deepcopy(self.user_input) variables = self.get_input_variables(self, content) if variables: user_input.extend(variables) if self.blacklist: blacklist_pattern = r"(?!(\s?)+(.*(" + '|'.join(self.blacklist) + ")))" else: blacklist_pattern = "" self.functions = [self.functions_prefix + x for x inwards self.functions] designing = r"((" + '|'.join(self.functions) + ")\s{0,}\(?\s{0,1}" + blacklist_pattern + ".*(" + '|'.join(user_input) + ").*)" render pattern
Testing
Running unit of measurement tests:
$ python3 -m unittest