Securing Your Application: Using Radamsa to Fuzz for Improper User Input Validation

Web applications are everywhere these days, from our banking to our social media accounts - and security is an ever-growing concern for both developers and users alike. Improper input validation is a major source of those security vulnerabilities, which can lead to potentially devastating results if left unchecked.

Syn Cubes Community - February 28, 2023
Securing Your App: Radamsa Fuzzing for User Input Validation Issues
Picture Credit - Canva

Introduction

Web applications are everywhere these days, from our banking to our social media accounts - and security is an ever-growing concern for both developers and users alike. Improper input validation is a major source of those security vulnerabilities, which can lead to potentially devastating results if left unchecked.

There are many techniques out there used to test for this issue, but "input fuzzing" is less explored and documented. One approach to elevating fuzzing into the AppSec testing realm is through the use of mutating fuzzing techniques.

Short Intro into Fuzzing

Fuzzing is a process of automated software testing, usually done in security testing, to detect unexpected input and edge-case errors. At its base, it involves feeding random data into a program or system to test its responses and uncover potential vulnerabilities. Fuzzing can be used to test both code-level and network-level components of a system, helping to identify security flaws that could be exploited by malicious actors.

There are a variety of different types of fuzzers, such as mutation-based, generation-based, protocol-aware, grammar-based, and model-based fuzzers.

  • Mutation-based fuzzers make slight random changes to valid data to try to create unexpected behavior from the system.
  • Generation-based fuzzers generate completely randomized data, which often contains more syntax errors than mutation based fuzzers.
  • Protocol aware fuzzers target protocols specifically and send messages with valid structure but invalid content. This could make programs crash and allow.
  • Grammar based fuzzers operate similar to generation-based ones, but they rely on pre-defined grammar rules instead of pure randomness for data generation.
  • Model-based fuzzers use existing models to capture real-world scenarios in order to increase test coverage.

Intro into Radamsa - a mutation-based fuzzer

And here is why a simple but powerful tool like Radamsa comes in handy when testing input validation, part of a penetration testing engagement - Radamsa acts as the most basic “fuzzer”, an input “mutator”, randomly generating “exotic” inputs in order to help detecting any potential weak spots at the application server level or backend framework.

Mutation-based fuzzing is a method of testing an application by providing it with a large number of inputs, many of which are invalid or unexpected. The goal of fuzz testing is to identify niche vulnerabilities in the application by causing it to crash or behave unexpectedly. This approach is particularly beneficial for testing an application's robustness to "exotic" input attack vectors, as it can help to identify edge cases that may not have been found during manual testing, but a skilled attacker could find and exploit them further.

One popular tool for mutating fuzzing is Radamsa. Radamsa can be used to test for a variety of vulnerabilities, including SQL injection, Cross-Site Scripting (XSS), and Remote Code Execution (RCE).

Additionally, one of the other benefits of using Radamsa is that it can be used to test a wide range of file formats, such as image files, audio files and even binary files. This can be particularly useful for identifying vulnerabilities in file-processing functionality, such as file uploads and downloads.

Another benefit of using Radamsa is that it can be integrated with other tools, such as Burp Suite, under the form of a plugin named Bradamsa.

How fuzzing can help

Fuzz testing can uncover various bugs depending on the programming language, but its main purpose is to challenge assumptions about your code. By identifying an expected property that must be true for any input (an "invariant"), a fuzzer searches for inputs that violate this invariant. Some invariances are universal for all applications, such as:

  • Crashes, timeouts, and hangs
  • Memory corruption (overflows and leaks)
  • Race conditions
  • Excessive resource usage
  • Unhandled exceptions
  • Undefined behavior

usage examples

By testing these malformed inputs against an application, developers can detect weaknesses at the source code level they may not have known about otherwise. And thanks to its off the shelf command line interface (CLI), it's easy even for less experienced users to get started with using Radamsa - here's a few usage examples based on its specifications:

  • To generate 10 files containing random mutations of valid inputs from the directory original_inputs/, you would use this command:
    radamsa -o outputfiles -n 10 original_inputs/*

    This is a command that is using the command line tool "radamsa" to randomly select 10 files from a folder called "original_inputs", and then it will output those selected files to a folder called "outputfiles". The "" at the end of the "original_inputs/" means to select all the files in that folder. So the command is telling radamsa to randomly select 10 files from the "original_inputs" folder and put those selected files in the "outputfiles" folder.

  • To produce 1000 different mutated variations based on existing valid inputs, without actually producing any output files, you would use this command:
    radamsa -n 1000 original_inputs/*

    This command uses the "radamsa" tool to generate 1000 new files based on the files in the "original_inputs" folder. It takes all files in the folder "original_inputs" indicated by "original_inputs/*" and radamsa will randomly mutate them to create 1000 new files. These new files will be saved in the same location as the original files. The -n flag is used to specify the number of generated files, in this case it's set to 1000.

  • To write mutated output files based on existing valid inputs with the filename prefix radamsarun followed by timestamp and mutation number (e.g., radamsarun_1567323006228_001), you can run this command:
    radamsa -o radamsarun_{TIMESTAMP}_{NUMBER} original_inputs/*

    This command uses the "radamsa" tool to generate new files based on the files in the "original_inputs" folder, and then output the generated files to a new folder. The new folder name is generated using the pattern "radamsarun_{TIMESTAMP}_{NUMBER}" where TIMESTAMP is the current timestamp and NUMBER is an incremental number.

    It takes all files in the folder "original_inputs" indicated by "original_inputs/*" and radamsa will randomly mutate them to create new files. The -o flag is used to specify the output folder, in this case it's set to the generated folder name.

    So the command is telling radamsa to randomly mutate the files in the "original_inputs" folder, and then save those new files in a new folder, with a name that includes the current timestamp and an incremental number.

  • If want to define exactly how your test cases should be generated (e.g., some kind of bit flips ratio), you could use this command instead:
    radamsa -M 0x10 -o outputfiles original_inputs/*

    This command uses the "radamsa" tool to generate new files based on the files in the "original_inputs" folder, and then output the generated files to a folder called "outputfiles".

    It takes all files in the folder "original_inputs" indicated by "original_inputs/*" and radamsa will randomly mutate them to create new files. The -M flag is used to specify the mutation mode, in this case it's set to 0x10. The mutation mode is a number that tells radamsa how to change the files. This specific value 0x10 is a specific mutation mode that Radamsa uses for certain type of mutations.

    The -o flag is used to specify the output folder, in this case it's set to "outputfiles". So the command is telling radamsa to randomly mutate the files in the "original_inputs" folder, and then save those new files in a folder called "outputfiles" with a specific mutation mode (0x10).

  • To combine two or more valid inputs into one mutation file instead of just one at a time, run this command:
    radamsa -m "originalA;originalB;originalC" *outputfile*

    This command uses the "radamsa" tool to generate new files based on the files "originalA", "originalB" and "originalC", and then output the generated files to a file called "outputfile".

    The -m flag is used to specify the original file(s) to mutate, in this case it's set to "originalA;originalB;originalC". The semi-colon(;) is used to separate the different file names.

    The outputfile is a placeholder for the output file name, it may have a different name in the actual usage. So the command is telling radamsa to randomly mutate the files "originalA", "originalB" and "originalC", and then save those new files in a file called "outputfile".

  • You can also set a size limit for your output files using the --maxbytes flag like so:
    radamsa --maxbytes 10240 /path/to/validA /path/to/validB /outputfile

    This command uses the "radamsa" tool to generate new files based on the files "/path/to/validA" and "/path/to/validB", and then output the generated files to a file called "/outputfile".

    The --maxbytes flag is used to specify the maximum number of bytes that the output files should have. In this case, it is set to 10240 bytes, meaning the output files will not be larger than 10240 bytes.

    The "/path/to/validA" and "/path/to/validB" are the file paths of the files that are used as the base to generate the new files.

    The "/outputfile" is the file name of the generated files. So the command is telling radamsa to randomly mutate the files "/path/to/validA" and "/path/to/validB" and to save the new files in a file called "/outputfile", and that the output files should not be larger than 10240 bytes, or 10kb.

  • To generate new input from stdin instead of an existing source file or directory, try the following syntax:
    cat source | radamsa > outputfile

    This command uses the "radamsa" tool to generate new files based on the contents of a file called "source". The "cat" command is used to read the contents of the file "source" and then it is piped to the "radamsa" command using the "|" symbol. The "|" symbol is known as a pipe, it is used to redirect the output of one command as the input to another command.

    The output of the radamsa command is then saved in a file called "outputfile". So the command is reading the contents of the file "source", passing it to radamsa, which then mutates the contents and saves the new contents in a file called "outputfile".

  • To make sure only data conforming to certain rulesets are generated, add the --filter flag with your desired criteria e.g.:
    cat source | radamsa --filter "(IP|EMAIL)" >outputfile.

    This is a command that is using the command line tool "radamsa" to filter the contents of a file called "source" and only output the lines that contain either the string "IP" or "EMAIL" to a new file called "outputfile".

  • If want to create multiple identical tests as part of large scale testing sessions simply add the count flag like so:
    radamsa --count 5 originalA > ufiles dir/{filename}{COUNT}.out

    The command "radamsa --count 5 originalA >ufiles dir/{filename}{COUNT}.out" will take the file originalA and generate five mutated versions of it, each with a different set of mutations applied to it. The mutated files will be saved to the directory "ufiles" with names such as "filename1.out", "filename2.out", etc. This command can be used to generate a set of test files from a single source file.

  • To control the way data is split up into questions (for example when doing quizzes) try out something like this:
    cat source | seeder --split=space --size 4 > quizset

    The command "cat source | seeder --split=space --size 4 > quizset" will take the contents of the file "source" and split it into four separate files, each containing a subset of the words from the original file. The files will be created in the same directory as the source file and will be named "quizset1", "quizset2", "quizset3", and "quizset4". This command can be used to create a set of quiz questions from a source text file.

Using Radamsa with Burp Suite

To use Radamsa with Burp Suite, you can install the Radamsa extension for Burp Suite, and configure it to use Radamsa as the default input generator for the fuzzer. This will enable Burp Suite to use Radamsa to generate random input data for each request sent by the fuzzer, increasing the chances of discovering new vulnerabilities.

Conclusions

These are just some of the many ways in which Radamsa can be used for effective testing and detection of potential security risks due to improper input validation - but the possibilities don't stop there!

Despite its age, Radamsa has been more popular among highly trained security experts as a reliable and robust application security testing solution. Input validation anomalies are a typical source of software vulnerabilities, but Radamsa's mutator fuzzer technology has shown to be quite successful at identifying them.

In fact, Radamsa's mutator fuzzer can be used for testing anything from web apps and embedded devices to network protocols. Because of its capacity to create unpredictable and varied test inputs, it has proven to be an invaluable tool for finding security flaws that could otherwise go undetected by more conventional testing procedures.

Radamsa's implementation as a tool for application security assessment exemplifies the value of originality and ingenuity in the cybersecurity industry. While time-honored techniques for evaluating software's reliability and security have their uses, novel ways are required to stay up with today's complex security threats. Security experts may anticipate new attacks and better safeguard software applications by using powerful tools like Radamsa.

Aknowledgements | References | Resources



Be the adversary - attack first