Skip to content

Object prototype can be overwritten #762

@adelphes

Description

@adelphes

The JSZip loadAsync() function returns an object whose keys are set from the filenames contained within the zip file.

This is a potential security risk: zip files containing filenames which match properties on the Object prototype mean that the returned files instance can have its prototype corrupted.

Example:
Create a new zip file with two empty files inside named "file.txt" and "toString".
Load the file contents and pass the buffer to the loadAsync() method of jszip. The returned object instance has a "files" property and the toString function is now set to an object. Calling toString() (either explicitly or implicitly) on the files object throws.

const jszip = require('jszip');

async function loadZip() {
    // this is a raw buffer of a zip file containing 1 empty file:
    // - "file.txt"
    let zipdata = Buffer.from('UEsDBAoACAAAAMudoVIAAAAAAAAAAAAAAAAIABwAZmlsZS50eHRVVAkAA/6hjWD+oY1gdXgLAAEE9QEAAAQAAAAAUEsHCAAAAAAAAAAAAAAAAFBLAQIeAwoACAAAAMudoVIAAAAAAAAAAAAAAAAIABgAAAAAAAAAAACkgQAAAABmaWxlLnR4dFVUBQAD/qGNYHV4CwABBPUBAAAEAAAAAFBLBQYAAAAAAQABAE4AAABSAAAAAAA=', 'base64');
    const okZip = await jszip.loadAsync(zipdata);
    console.log(`${okZip.files}`);   // this should print [Object object]

    // this is a raw buffer of a zip file containing 2 empty files:
    // - "file.txt"
    // - "toString"
    zipdata = Buffer.from('UEsDBBQACAAIANS8kVIAAAAAAAAAAAAAAAAIACAAdG9TdHJpbmdVVA0AB3Bje2BmY3tgcGN7YHV4CwABBPUBAAAEFAAAAAMAUEsHCAAAAAACAAAAAAAAAFBLAwQUAAgACADDvJFSAAAAAAAAAAAAAAAACAAgAGZpbGUudHh0VVQNAAdPY3tg4FJ7YE9je2B1eAsAAQT1AQAABBQAAAADAFBLBwgAAAAAAgAAAAAAAABQSwECFAMUAAgACADUvJFSAAAAAAIAAAAAAAAACAAgAAAAAAAAAAAApIEAAAAAdG9TdHJpbmdVVA0AB3Bje2BmY3tgcGN7YHV4CwABBPUBAAAEFAAAAFBLAQIUAxQACAAIAMO8kVIAAAAAAgAAAAAAAAAIACAAAAAAAAAAAACkgVgAAABmaWxlLnR4dFVUDQAHT2N7YOBSe2BPY3tgdXgLAAEE9QEAAAQUAAAAUEsFBgAAAAACAAIArAAAALAAAAAAAA==', 'base64');

    const failZip = await jszip.loadAsync(zipdata);
    console.log(`${failZip.files}`);   // this should print [Object object] but will throw

    console.log('finished');
}

loadZip();

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions