badmoodle logo

Introduction: why badmoodle?

Once upon a time, I found two Stored XSS vulnerabilities in moodle. I reported the issues to them but due to their vulnerability disclosure program policy they considered them as Informational severity issues.

I tried to explain the impact of such vulnerabilities, providing them an XSS Tunneling exploitation PoC performed through BeEF, but they wouldn’t listen to reason and insisted that the severity was still Informational.

Since I found them unreliable on assigning a severity to a vulnerability, I decided to write a tool that scans for all the vulnerabilities discovered by security researchers, including the ones that Moodle won’t fix: badmoodle

So, since Moodle is so strict about their vulnerability disclosure program, a lot of vulnerabilities that security researchers discover and share with Moodle end up rejected or put on hold forever.

All these vulnerabilities will never see the light, they will be left unfixed and forgotten by Moodle… but not by badmoodle ;)

What is badmoodle

badmoodle is an unofficial community-based vulnerability scanner for moodle that scans for canonical and non-canonical Moodle vulnerabilities.

Community-based means that it’s up to the security researchers community to define vulnerabilities, it is not exclusively up to Moodle anymore. This allows to find more vulnerabilities in moodle instances, not only the ones “approved” by Moodle.

badmoodle’s purpose is to help penetration testers, bug hunters and security researchers find more vulnerabilities on moodle instances.

Since badmoodle is community-based, it will scan for two different kind of vulnerabilities:

  • Official vulnerabilities: The canonical ones published in Moodle security advisory blog;
  • Community vulnerabilities: The non-canonical ones that are not present in Moodle security advisory blog.

The community vulnerability scan can run in two modes:

  • Check mode: Only checks if the host is vulnerable or not;
  • Exploit mode: If the host is vulnerable, exploit the vulnerabilities.

Community Vulnerability Modules

Community vulnerability scans are performed by community vulnerability modules, which are modules added by the community of security researchers to scan for the vulnerabilities they found.

In fact, badmoodle is modular: everyone can add a community vulnerability module by just creating a .py file inside the “vulns” directory and badmoodle will execute it alongside the other modules without interfering with the rest of the code.

badmoodle needs only 2 requirements to make a module work:

  • It must have a boolean variable enabled and a string variable name.
    The enabled boolean variable is used to determine wether badmoodle should run the module or not. This allows to enable or disable modules by simply editing this variable without removing it from the “vulns” folder.
    The name string variable is just the vulnerability name, that will be printed in the core.
  • It must have the functions check(args, sess, version) and exploit(args, sess, version)
    These are the main functions of the module, the ones badmoodle will call in the core. Through these functions badmoodle will pass to the module the script arguments, the request session object of the script (useful for authenticated sessions) and moodle version.
    The check function is a boolean function that only checks whether the host is vulnerable or not, the exploit function instead will exploit that vulnerability.
    If in check mode badmoodle will call only the check function to only determine whether the host is vulnerable or not, if in exploit mode badmoodle will also call the exploit function for exploiting the vulnerability.

Community vulnerability module authors are also free to include all the logging and output functions they need by using from utils.output import * for colored output functions and from utils.logging import * for logging functions.

There follows a template for a badmoodle community vulnerability module:





from utils.output import *
from utils.logging import *

enabled = True

def check(args, sess, version):
	#return True if the host is vulnerable, False otherwise

def exploit(args, sess, version):


Everyone is welcome to contribute to badmoodle!

If you wrote a community vulnerability module for badmoodle and want to share it with the community, you can contribute to the badmoodle project by performing a pull request to the GitHub repository.

Also, if you want to report a bug, feel free to open an issue or contact me via mail at

Installation, usage and more info

To install, use and for more info about badmoodle, please refer to the GitHub repository