Conversation
addTranslations assigned catalogs[locale][domain] without sanitizing keys, so a locale of __proto__ wrote onto Object.prototype (GHSA-g974-hxvm-x689).
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
addTranslations,setLocale, andsetTextDomainnow reject non-strings and keys that live onObject.prototype(key in {}).Fixes GHSA-g974-hxvm-x689 / CVE-2024-21528:
addTranslations('__proto__', 'polluted', 'pwned')wrote ontoObject.prototypebecausecatalogs['__proto__']is the prototype object. Reproduced on this tree at 3.0.1 (the advisory's "last affected" 3.0.0 is stale; 3.0.1 was docs/deps only). Issue #72 asked to backport postalsys/gettext@63e627c.Tests cover the Snyk PoC, a reserved domain key, the reserved-key error event, and the two setters.
Decision
Reserved-key rejection via
key in {}plus type checks, as in the cited backport. Alternative:Object.create(null)forcatalogsand per-locale maps, so__proto__would be an ordinary own property instead of the prototype setter. #72 asked for the reserved-key rejection, and this file already validates locale/domain types the same way. Can switch to null-prototype catalogs.The cited commit type-checked
localetwice (the second warning still saidsetLocale()). This PR type-checksdomaininstead, matchingsetTextDomainhere and postalsys/gettext@c2bf8dc.Fixes #72
Test plan
addTranslations('__proto__', 'polluted', 'pwned')does not set{}.pollutedaddTranslations('et-EE', '__proto__', translations)does not create/rewrite that catalogsetLocale('__proto__')/setTextDomain('__proto__')leave the previous locale/domainnpx mocha test/gettext-test.js(42 passing) andnpx grunt(jshint + mocha)