{"id":30950745,"url":"https://github.com/rog3rsm1th/frelatage","last_synced_at":"2025-09-11T05:18:38.131Z","repository":{"id":39578763,"uuid":"465913676","full_name":"Rog3rSm1th/frelatage","owner":"Rog3rSm1th","description":"Coverage-based fuzzer for python applications","archived":false,"fork":false,"pushed_at":"2022-11-04T14:11:05.000Z","size":106049,"stargazers_count":237,"open_issues_count":6,"forks_count":17,"subscribers_count":4,"default_branch":"main","last_synced_at":"2025-09-09T03:15:01.360Z","etag":null,"topics":["fuzz-testing","fuzzer","fuzzing","python","python3","security","testing"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Rog3rSm1th.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2022-03-03T23:10:15.000Z","updated_at":"2025-08-13T05:58:27.000Z","dependencies_parsed_at":"2022-07-13T07:51:53.853Z","dependency_job_id":null,"html_url":"https://github.com/Rog3rSm1th/frelatage","commit_stats":null,"previous_names":[],"tags_count":6,"template":false,"template_full_name":null,"purl":"pkg:github/Rog3rSm1th/frelatage","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Rog3rSm1th%2Ffrelatage","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Rog3rSm1th%2Ffrelatage/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Rog3rSm1th%2Ffrelatage/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Rog3rSm1th%2Ffrelatage/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Rog3rSm1th","download_url":"https://codeload.github.com/Rog3rSm1th/frelatage/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Rog3rSm1th%2Ffrelatage/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":274580783,"owners_count":25311238,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-09-11T02:00:13.660Z","response_time":74,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["fuzz-testing","fuzzer","fuzzing","python","python3","security","testing"],"created_at":"2025-09-11T05:18:36.419Z","updated_at":"2025-09-11T05:18:38.115Z","avatar_url":"https://github.com/Rog3rSm1th.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003cp align=center\u003e\n  \u003cimg src=\"https://github.com/Rog3rSm1th/Frelatage/blob/main/doc/frelatage_logo.gif?raw=true\" width=\"200\" height=\"200\" style=\"border-radius:4px\"/\u003e\n  \u003cbr\u003e\n  \u003ccode\u003epip3 install frelatage\u003c/code\u003e\u003c/br\u003e\n  \u003c/br\u003e\n  \u003ca target=\"_blank\" title=\"Downloads\"\u003e\u003cimg src=\"https://static.pepy.tech/badge/frelatage\"\u003e\u003c/a\u003e\n  \u003ca target=\"_blank\" href=\"https://www.python.org/downloads/\" title=\"Python version\"\u003e\u003cimg src=\"https://img.shields.io/badge/python-%3E=_3.6-green.svg\"\u003e\u003c/a\u003e\n  \u003ca target=\"_blank\" href=\"LICENSE\" title=\"License: MIT\"\u003e\u003cimg src=\"https://img.shields.io/badge/License-MIT-blue.svg\"\u003e\u003c/a\u003e\n  \u003ca target=\"_blank\" href=\"https://pypi.org/project/kharma/\" title=\"License: MIT\"\u003e\u003cimg src=\"https://img.shields.io/pypi/v/frelatage?label=release\"\u003e\u003c/a\u003e\n  \u003ca href=\"https://twitter.com/intent/follow?screen_name=Rog3rSm1th\" title=\"Follow\"\u003e\u003cimg src=\"https://img.shields.io/twitter/follow/Rog3rSm1th?label=Rog3rSm1th\u0026style=social\"\u003e\u003c/a\u003e\n  \u003cbr\u003e\n  \u003cspan\u003e\u003ci\u003eThe Python Fuzzer that the world deserves\u003c/i\u003e\u003c/span\u003e\n\u003c/p\u003e\n\n\u003cp align=\"center\"\u003e\n  \u003ca href=\"#installation\"\u003eInstallation\u003c/a\u003e\n  \u0026nbsp;\u0026nbsp;\u0026nbsp;|\u0026nbsp;\u0026nbsp;\u0026nbsp;\n  \u003ca href=\"#how-it-works\"\u003eHow it works\u003c/a\u003e\n  \u0026nbsp;\u0026nbsp;\u0026nbsp;|\u0026nbsp;\u0026nbsp;\u0026nbsp;\n  \u003ca href=\"#features\"\u003eFeatures\u003c/a\u003e\n  \u0026nbsp;\u0026nbsp;\u0026nbsp;|\u0026nbsp;\u0026nbsp;\u0026nbsp;\n  \u003ca href=\"#use-frelatage\"\u003eUse Frelatage\u003c/a\u003e\n  \u0026nbsp;\u0026nbsp;\u0026nbsp;|\u0026nbsp;\u0026nbsp;\u0026nbsp;\n  \u003ca href=\"#configuration\"\u003eConfiguration\u003c/a\u003e\n\u003c/p\u003e\n\n\u003cp align=\"center\"\u003e\n  \u003cimg src=\"https://github.com/Rog3rSm1th/Frelatage/blob/main/doc/frelatage_demo.gif?raw=true\" alt=\"Frelatage demonstration\"/\u003e\n\u003c/p\u003e\n\nFrelatage is a coverage-based Python fuzzing library which can be used to fuzz python code. The development of Frelatage was inspired by various other fuzzers, including [AFL](https://github.com/google/AFL)/[AFL++](https://github.com/AFLplusplus/AFLplusplus), [Atheris](https://github.com/google/atheris) and [PythonFuzz](https://github.com/fuzzitdev/pythonfuzz). The main purpose of the project is to take advantage of the best features of these fuzzers and gather them together into a new tool in order to efficiently fuzz python applications.\n\n**DISCLAIMER** : This project is at the alpha stage and can still cause many unexpected behaviors. Frelatage should not be used in a production environment at this time.\n\n## Requirements\n[Python 3](https://www.python.org/)\n\n## Installation\n\n#### Install with pip (recommended)\n\n```bash\npip3 install frelatage\n```\n\n#### Or build from source\n\nRecommended for developers. It automatically clones the main branch from the frelatage repo, and installs from source.\n\n```bash\n# Automatically clone the Frelatage repository and install Frelatage from source\nbash \u003c(wget -q https://raw.githubusercontent.com/Rog3rSm1th/Frelatage/main/scripts/autoinstall.sh -O -)\n```\n\n## How it works\n\nThe idea behind the design of Frelatage is the usage of a genetic algorithm to generate mutations that will cover as much code as possible. The functioning of a fuzzing cycle can be roughly summarized with this diagram : \n\n```mermaid\ngraph TB\n\n    m1(Mutation 1) --\u003e |input| function(Fuzzed function)\n    m2(Mutation 2) --\u003e |input| function(Fuzzed function)\n    mplus(Mutation ...) --\u003e |input| function(Fuzzed function)\n    mn(Mutation n) --\u003e |input| function(Fuzzed function)\n    \n    function --\u003e generate_reports(Generate reports)\n    generate_reports --\u003e rank_reports(Rank reports)  \n    rank_reports --\u003e select(Select n best reports)\n    \n    select --\u003e |mutate| nm1(Mutation 1) \u0026 nm2(Mutation 2) \u0026 nmplus(Mutation ...) \u0026 nmn(Mutation n)\n    \n    subgraph Cycle mutations\n    direction LR\n    m1\n    m2\n    mplus\n    mn\n    end\n    \n    subgraph Next cycle mutations\n    direction LR\n    nm1\n    nm2\n    nmplus\n    nmn\n    end\n     \n    style function fill:#5388e8,stroke:white,stroke-width:4px\n```\n## Features\n\n#### Fuzzing different argument types: \n  - String\n  - Int\n  - Float\n  - List\n  - Tuple\n  - Dictionary\n  \n#### File fuzzing\nFrelatage allows to fuzz a function by passing a file as input. \n\n#### Fuzzer efficiency\n- Corpus\n- Dictionnary\n\n## Use Frelatage\n\n#### Fuzz a classical parameter\n\n```python\nimport frelatage\nimport my_vulnerable_library\n\ndef MyFunctionFuzz(data):\n  my_vulnerable_library.parse(data)\n\ninput = frelatage.Input(value=\"initial_value\")\nf = frelatage.Fuzzer(MyFunctionFuzz, [[input]])\nf.fuzz()\n```\n\n#### Fuzz a file parameter\n\nFrelatage gives you the possibility to fuzz file type input parameters. To initialize the value of these files, you must create files in the input folder (```./in``` by default).\n\nIf we want to initialize the value of a file used to fuzz, we can do it like this:\n```bash\necho \"initial value\" \u003e ./in/input.txt\n```\n\nAnd then run the fuzzer: \n\n```python\nimport frelatage\nimport my_vulnerable_library\n\ndef MyFunctionFuzz(data):\n  my_vulnerable_library.load_file(data)\n\ninput = frelatage.Input(file=True, value=\"input.txt\")\nf = frelatage.Fuzzer(MyFunctionFuzz, [[input]])\nf.fuzz()\n```\n\n#### Fuzz several methods using decorators (experimental)\n\n```python\nimport frelatage\nimport my_vulnerable_library\n\ninput = frelatage.Input(file=True, value=\"input.txt\")\n\n@frelatage.instrument([[input]])\ndef MyFunctionFuzz_1(data):\n  my_vulnerable_library.load_file(data)\n\n@frelatage.instrument([[input]])\ndef MyFunctionFuzz_1(data):\n  my_vulnerable_library.load_file_but_different(data)\n# And so on\n\n# It will fuzz the instrumented methods one after the other\nfrelatage.Fuzzer.fuzz_all()\n```\n\n#### Load several files to a corpus at once\n\nIf you need to load several files into a corpus at once (useful if you use a large corpus) You can use the built-in function of Frelatage `load_corpus`. This function returns a list of inputs.\n\n```load_corpus(directory: str, file_extensions: list) -\u003e list[Input]```\n- directory: Subdirectory of the input directory (relative path), e.g `./`, `./images`\n- file_extensions: List of file extensions to include in the corpus entries, e.g. `[\"jpeg\", \"gif\"]`, `[\"pdf\"]`\n\n```python\nimport frelatage\nimport my_vulnerable_library\n\ndef MyFunctionFuzz(data):\n  my_vulnerable_library.load_file(data)\n  my_vulnerable_library.load_file(data2)\n\n# Load every every file in the ./in directory\ncorpus_1 = frelatage.load_corpus(directory=\"./\")\n# Load every .gif/.jpeg file in the ./in/images subdirectory\ncorpus_2 = frelatage.load_corpus(directory=\"./images\", file_extension=[\"gif\", \"jpeg\"])\n\nf = frelatage.Fuzzer(MyFunctionFuzz, [corpus_1, corpus_2])\nf.fuzz()\n```\n\n#### Fuzz with a dictionary\n\nYou can copy one or more dictionaries located [here](https://github.com/Rog3rSm1th/Frelatage/tree/main/dictionaries) in the directory dedicated to dictionaries (`./dict` by default).\n\n#### Differential fuzzing\n\n[Differental fuzzing](https://en.wikipedia.org/wiki/Differential_testing) is a popular software testing technique that attempts to detect bugs by providing the same input to multiple libraries/programs and observing differences in their behaviors. You will find an example [here](https://github.com/Rog3rSm1th/Frelatage/blob/main/examples/json_fuzzer/json_differential_fuzzer.py) of a use of differential fuzzing with Frelatage with the `json` and `ujson` libraries. \n\n#### Examples\n\nYou can find more examples of fuzzers and corpus in the [examples directory](https://github.com/Rog3rSm1th/Frelatage/tree/main/examples).\n\n- [Fuzzing Pillow with Frelatage to find bugs and vulnerabilities](https://rog3rsm1th.github.io/posts/fuzzing-python-libraries-frelatage/)\n\n## Crash reports\n\nEach crash report is saved in the output folder (```./out``` by default), in a folder named : ```id:\u003ccrash ID\u003e,err:\u003cerror type\u003e,err_pos:\u003cerror\u003e,err_file:\u003cerror file\u003e```.\n\nThe report directory is in the following form: \n```\n    ├── out\n    │   ├── id:\u003ccrash ID\u003e,err:\u003cerror type\u003e,err_file:\u003cerror file\u003e,err_pos:\u003cerr_pos\u003e\n    │       ├── message\n    │       ├── input\n    │       ├── 0\n    │            ├── \u003cinputfile1\u003e\n    │       ├── ...\n    │   ├── ...\n```\n\nEach crash report contains a ```message``` file which contains the error message.\n\n## Coverage increase reports\n\nEach coverage increase report is saved in the coverage folder (```./cov``` by default), in a folder named : ```coverage_\u003cID\u003e```, and the report directory is in the same form as the crash reports directories.\n\n#### Read a report\n\nInputs passed to a function are serialized using the [pickle](https://docs.python.org/3/library/pickle.html) module before being saved in the ```\u003creport_folder\u003e/input file```. It is therefore necessary to deserialize it to be able to read the contents of the file. This action can be performed with the ```frelatage-report``` commmand.\n\n```bash\n$ frelatage-report input\n```\n  \n## Configuration\n\nThere are two ways to set up Frelatage:\n\n#### Using the environment variables\n\n| ENV Variable                   | Description | Possible Values | Default Value |\n| -------------------------------| ----------- |--------|-------|\n| **FRELATAGE_DICTIONARY_ENABLE**   | Enable the use of mutations based on dictionary elements| ```1``` to enable, ```0``` otherwise | ```1``` |\n| **FRELATAGE_SAVE_NEW_COVERAGE**   | Save new coverage inputs to reuse them later| ```1``` to enable, ```0``` otherwise | ```1``` |\n| **FRELATAGE_TIMEOUT_DELAY**        | Delay in seconds after which a function will return a TimeoutError | ```1``` - ```infinity``` | ```2``` |\n| **FRELATAGE_INPUT_FILE_TMP_DIR**   | Temporary folder where input files are stored | absolute path to a folder, e.g. ```/tmp/custom_dir```| ```/tmp/frelatage```|\n| **FRELATAGE_INPUT_MAX_LEN**        | Maximum size of an input variable in bytes | ```4``` - ```infinity``` |  ```4094``` |\n| **FRELATAGE_MAX_THREADS**          | Maximum number of simultaneous threads | ```8``` - ```infinity``` | ```8``` |\n| **FRELATAGE_MAX_STAGES**           | Maximum number of stages for a fuzzed function | ```1``` - ```infinity``` | ```1000000``` |\n| **FRELATAGE_MAX_CYCLES_WITHOUT_NEW_PATHS**      | Number of cycles without new paths found after which we go to the next stage | ```10``` - ```infinity``` | ```5000``` | \n| **FRELATAGE_INPUT_DIR**           | Directory containing the initial input files. It needs to be a relative path (to the path of the fuzzing file) |relative path to a folder, e.g. ```./in```  | ```./in``` |\n| **FRELATAGE_DICTIONARY_DIR**      | Default directory for dictionaries. It needs to be a relative path (to the path of the fuzzing file) | relative path to a folder, e.g. ```./dict```  | ```./dict``` |  \n| **FRELATAGE_DEBUG_MODE**      | Enable the debug mode (show the error when Frelatage crash) | ```1``` to enable, ```0``` otherwise | ```1``` | \n\nA configuration example :\n\n```bash\nexport FRELATAGE_DICTIONARY_ENABLE=1 \u0026\u0026\nexport FRELATAGE_SAVE_NEW_COVERAGE=1 \u0026\u0026\nexport FRELATAGE_TIMEOUT_DELAY=2 \u0026\u0026\nexport FRELATAGE_INPUT_FILE_TMP_DIR=\"/tmp/frelatage\" \u0026\u0026\nexport FRELATAGE_INPUT_MAX_LEN=4096 \u0026\u0026\nexport FRELATAGE_MAX_THREADS=8 \u0026\u0026\nexport FRELATAGE_MAX_STAGES=1000000 \u0026\u0026\nexport FRELATAGE_MAX_CYCLES_WITHOUT_NEW_PATHS=5000 \u0026\u0026\nexport FRELATAGE_INPUT_DIR=\"./in\" \u0026\u0026\nexport FRELATAGE_DICTIONARY_DIR=\"./dict\" \u0026\u0026\npython3 fuzzer.py\n```\n\n#### Passing arguments to the fuzzer \n\n```python\nimport frelatage \n\ndef myfunction(input1_string, input2_int):\n    pass\n\ninput1 = frelatage.Input(value=\"initial_value\")\ninput2 = frelatage.Input(value=2)\n\nf = frelatage.Fuzzer(\n    # The method you want to fuzz\n    method=myfunction,\n    # Corpus\n    corpus=[[input1], [input2]],\n    # Number of threads\n    threads_count=8,\n    # Exceptions that will be taken into account\n    exceptions_whitelist=(OSError),\n    # Exceptions that will not be taken into account\n    exceptions_blacklist=(),\n    # Directory where the error reports will be stored\n    output_directory=\"./out\",\n    # Directory where the coverage increase reports will be stored\n    coverage_directory=\"./cov\",\n    # Enable or disable silent mode\n    silent=False,\n    # Enable or disable infinite fuzzing\n    infinite_fuzz=False\n)\nf.fuzz()\n```\n\n## Risks \n\nPlease keep in mind that, similarly to many other computationally-intensive\ntasks, fuzzing may put strain on your hardware and on the OS. In particular:\n\n  - Your CPU will run hot and will need adequate cooling. In most cases, if\n    cooling is insufficient or stops working properly, CPU speeds will be\n    automatically throttled. That said, especially when fuzzing on less\n    suitable hardware (laptops, smartphones, etc), it's not entirely impossible\n    for something to blow up.\n\n  - Targeted programs may end up erratically grabbing gigabytes of memory or\n    filling up disk space with junk files. Frelatage tries to enforce basic memory\n    limits, but can't prevent each and every possible mishap. The bottom line\n    is that you shouldn't be fuzzing on systems where the prospect of data loss\n    is not an acceptable risk.\n\n  - Fuzzing involves billions of reads and writes to the filesystem. On modern\n    systems, this will be usually heavily cached, resulting in fairly modest\n    \"physical\" I/O - but there are many factors that may alter this equation.\n    It is your responsibility to monitor for potential trouble; with very heavy\n    I/O, the lifespan of many HDDs and SSDs may be reduced.\n\n    A good way to monitor disk I/O on Linux is the 'iostat' command:\n\n```shell\n    $ iostat -d 3 -x -k [...optional disk ID...]\n```\n\n## 🔴 About Me/Hire me 🖥️\n\nI am Rog3rSm1th, I am 21 years old and I'm a French computer and cybersecurity enthusiast. I like developing tools (OSINT, Fuzzing...) and playing CTFs/Wargames. To learn more about me and my projects, juste click [here](https://github.com/Rog3rSm1th/Rog3rSm1th).\n\n➜ If you want to hire me for one of your projects (Programming, cybersecurity...), just contact me at [r0g3r5@protonmail.com](mailto:r0g3r5@protonmail.com) and we will assess your needs together.\n\n## Contact \n\nfor any remark, suggestion, bug report, or if you found a bug using Frelatage, you can contact me at r0g3r5@protonmail.com or on twitter [@Rog3rSm1th](https://twitter.com/Rog3rSm1th)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frog3rsm1th%2Ffrelatage","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Frog3rsm1th%2Ffrelatage","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frog3rsm1th%2Ffrelatage/lists"}