Skip to content

abelstuker/aran-taint-analysis

Repository files navigation

Portable Aran Taint Analysis for JavaScript

This repository contains the JavaScript implementation of the taint analysis component for JASMaint, a portable multi-language dynamic taint analysis tool designed for modern web applications that integrate JavaScript and WebAssembly (Wasm). The JASMaint architecture enables precise tracking of data flows across language boundaries to detect confidentiality and integrity vulnerabilities, such as information leaks or injection attacks.

JASMaint is based on source code instrumentation for both JavaScript (using Aran) and WebAssembly (via a separate Wasm instrumentation platform, e.g., Wastrumentation). This JavaScript part focuses on taint propagation in JS, while complying with the JASMaint architecture by handling taint propagation interoperation with Wasm modules (e.g., shared memory, globals, and function calls). The Wasm modules that interoperate with JS must be instrumented separately to support JASMaint compliant taint propagation. This instrumentation can be done using the JASMaint Wasm Taint Analysis instrumentation.

Key Features

  • Dynamic Taint Analysis for JavaScript: Tracks taint propagation through primitives, objects, intrinsics, and control flows using Aran instrumentation.
  • Multi-Language Support: Handles taint exchange between JS and Wasm during interoperation, including:
    • Function calls (JS → Wasm and Wasm → JS).
    • Shared linear memory (e.g., via TypedArrays and ArrayBuffers).
    • Shared global variables.

Note that this JavaScript taint analysis acts as the orchestrator for taint communication with the Wasm analysis, which must be implemented separately (e.g., using JASMaint's Wasm instrumentation). The Wasm analysis must support taint propagation within Wasm code and comply with the JASMaint taint communication protocol.

JASMaint Architecture

  • Portable Deployment: Works in any runtime supporting JS and Wasm (e.g., browsers, Node.js).
  • Configurable Analysis Modes: Supports no-analysis, forward analysis, Linvail-only, or full taint tracking.
  • Taint APIs: Provides Taint.source(), Taint.sink(), Taint.sanitize(), and assertion methods for marking and checking taint in code.
  • Precision Improvements: Reduces overtainting (0.003%–56.20% in benchmarks) with respect to state-of-the-art techniques that conservatively taint all information crossing interlanguage boundaries. Refer to the research paper for detailed evaluation.

This implementation is part of a bachelor's thesis and a research paper (see Publication below).

Installation

With Node.js and npm/yarn installed, clone the repository and install dependencies.

git clone https://github.com/abelstuker/aran-taint-analysis.git
cd aran-taint-analysis
npm install

Usage

As a Library

Use the TaintTracker class to instrument and analyze JavaScript files.

import { TaintTracker, ANALYSIS_TYPES } from "./index.js";

const tracker = new TaintTracker(
    ANALYSIS_TYPES.TAINT_ANALYSIS /* analysisType */,
    true /* logTaints */,
    true /* enableTaintCommunication */
);

await tracker.analyze("path/to/input.js", "path/to/output.js");
  • analysisType: One of NO_ANALYSIS, FORWARD_ANALYSIS, LINVAIL_ANALYSIS, or TAINT_ANALYSIS (default).
  • logTaints: Boolean to enable taint logging (outputs to a file).
  • enableTaintCommunication: Boolean to enable taint exchange with Wasm (disable for pure JS analysis).

After instrumentation, execute the output file:

await tracker.runInstrumentedAnalysis("path/to/output.js", /* args */ []);

CLI Usage

Run analysis directly from the command line:

node index.js path/to/input.js

This instruments input.js to tests/instrumented.js and executes it if CONFIG.EXECUTE_INSTRUMENTED is true.

Configuration

Edit utils/config.js for global settings:

  • ANALYSIS_TYPES: Enum for analysis modes.
  • CONFIG.EXECUTE_INSTRUMENTED: Auto-execute instrumented code.
  • CONFIG.ENABLE_TAINT_COMMUNICATION: Toggle JS-Wasm taint propagation.
  • CONFIG.TAINT_LOGGING: Log taint values during execution.

Integrating with Wasm

For multi-language analysis:

  1. Compile your Wasm module with JASMaint taint instrumentation.
  2. In JS, instantiate the JASMaint instrumented Wasm module.
  3. The analysis will automatically handle taint propagation during calls, memory access, and globals.

Examples

Basic Taint Tracking in JS

Input (test.js):

import Taint from "./src/taint.js";

function process() {
    const user_input_source = Taint.source("malicious<script>"); // Tainted source
    const safe_input = "safe data";
    Taint.assertIsTainted(user_input_source);
    Taint.assertIsNotTainted(safe_input);

    // Test arithmetic operators
    const concat_safe = safe_input + safe_input;
    const concat_unsafe = user_input_source + safe_input;
    Taint.assertIsNotTainted(concat_safe);
    Taint.assertIsTainted(concat_unsafe);

    // Test with other operators
    const modified = user_input_source.toUpperCase();
    const repeated = user_input_source.repeat(2);
    const extracted = user_input_source.substring(2, 5);
    Taint.assertIsTainted(modified);
    Taint.assertIsTainted(repeated);
    Taint.assertIsTainted(extracted);

    // Test assignment operators
    let accumulator = "start: ";
    accumulator += user_input_source;
    Taint.assertIsTainted(accumulator);

    // Test control flow
    const msg = "";
    if (user_input_source.length > 5) {
        msg = "Long input";
    } else {
        msg = "Short input";
    }
    Taint.assertIsTainted(msg);

    // Test objects and arrays
    const obj = { key1: safe_input, key2: user_input_source };
    const arr = [safe_input, user_input_source];
    Taint.assertIsNotTainted(obj.key1);
    Taint.assertIsTainted(obj.key2);
    Taint.assertIsNotTainted(arr[0]);
    Taint.assertIsTainted(arr[1]);

    // Test function calls
    function echo(input) {
        Taint.assertIsTainted(input);
        return input;
    }
    const echoed = echo(user_input_source);
    Taint.assertIsTainted(echoed);
}

export default process;

Analyze:

node index.js tests/test.js

The instrumented code will track taint during execution.

JS-Wasm Interoperation

Assume a Wasm module (module.wasm) with exported functions and shared memory. In JS:

const checkIsTainted = (value) => {
    console.log(Taint.isTainted(value) ? "Value tainted" : "Value not tainted");
};

const wasmBuffer = /* load wasm */;
const instance = await WebAssembly.instantiate(wasmBuffer, {
    js: {
        checkIsTainted, // called from Wasm with correct taint information
    },
});
const buffer = new Uint8Array(instance.exports.memory.buffer);
buffer[0] = Taint.source(42); // taint propagates to Wasm memory
instance.exports.process(Taint.source(7)); // taint propagates to Wasm in function calls

For more examples, see the tests/ directory.

Publication

  • Paper: "JASMaint: Portable Multi-language Taint Analysis for the Web" by Abel Stuker, Aäron Munsters, Angel Luis Scull Pupo, Laurent Christophe, and Elisa Gonzalez Boix. In Proceedings of MPLR '25. DOI: 10.1145/3759426.3760982
  • Thesis: "Multi-Language Taint Analysis for Emerging Web Applications" by Abel Stuker (Bachelor's Thesis, Vrije Universiteit Brussel). Supervised by Prof. Dr. Elisa Gonzalez Boix, Aäron Munsters, and Dr. Angel Luis Scull Pupo.

Citation

@inproceedings{10.1145/3759426.3760982,
    author = {Stuker, Abel and Munsters, A\"{a}ron and Scull Pupo, Angel Luis and Christophe, Laurent and Gonzalez Boix, Elisa},
    title = {JASMaint: Portable Multi-language Taint Analysis for the Web},
    year = {2025},
    isbn = {9798400721496},
    publisher = {Association for Computing Machinery},
    address = {New York, NY, USA},
    url = {https://doi.org/10.1145/3759426.3760982},
    doi = {10.1145/3759426.3760982},
    abstract = {Modern web applications integrate JavaScript code with more efficient languages compiling to WebAssembly, such as C, C++ or Rust. However, such multi-language applications challenge program understanding and increase the risk of security attacks. Dynamic taint analysis is a powerful technique used to uncover confidentiality and integrity vulnerabilities. The state of the art has mainly considered taint analysis targeting a single programming language, extended with a limited set of native extensions. To deal with data flows between the language and native extensions, typically taint signatures or models of those extensions have been derived from the extensions’ high-level source code. However, this does not scale for multi-language web applications as the WebAssembly modules evolve continuously and generally do not include their high-level source code. This paper proposes JASMaint, the first taint analysis approach for multi-language web applications. A novel analysis orchestrator component manages the exchange of taint information during interoperation between our language-specific taint analyses. JASMaint is based on source code instrumentation for both the JavaScript and WebAssembly codebases. This choice enables deployment to all runtimes that support JavaScript and WebAssembly. We evaluate our approach on a benchmark suite of multi-language programs. Our evaluation shows that JASMaint reduces overtainting by 0.003\%–56.20\% compared to an over-approximating taint analysis based on function models. However, this comes at the cost of an increase in performance overhead by a factor of 1.14x–1.61x relative to the state of the art.},
    booktitle = {Proceedings of the 22nd ACM SIGPLAN International Conference on Managed Programming Languages and Runtimes},
    pages = {79–92},
    numpages = {14},
    keywords = {JavaScript, Wasm, dynamic taint analysis, multi-language, source code instrumentation},
    location = {Singapore, Singapore},
    series = {MPLR '25}
}

Contributing

Contributions are welcome! Open an issue or PR for bug fixes, features, or documentation improvements.

Acknowledgments

  • Built on Aran and Linvail.
  • Part of research at the Software Languages Lab, Vrije Universiteit Brussel.

About

A JASMaint compliant source-code instrumented taint analysis for JavaScript programs.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Contributors 2

  •  
  •