Bug 1266569 - Avoid including the `ChromeUtils` binding in `Base64.h`. r=froydnj

MozReview-Commit-ID: 8ZLdMhJMaUe

--HG--
extra : rebase_source : d5cb2b5bcc587bad95e6223d18ef38c6937f9270
extra : histedit_source : 208b28d87e223333c2995fd615e0602b11d5bb68
This commit is contained in:
Kit Cambridge 2016-04-22 07:41:58 -07:00
Родитель 341af4d90b
Коммит b3e4980239
7 изменённых файлов: 61 добавлений и 33 удалений

Просмотреть файл

@ -74,7 +74,9 @@ ThreadSafeChromeUtils::Base64URLEncode(GlobalObject& aGlobal,
MOZ_CRASH("Uninitialized union: expected buffer or view");
}
nsresult rv = mozilla::Base64URLEncode(length, data, aOptions, aResult);
auto paddingPolicy = aOptions.mPad ? Base64URLEncodePaddingPolicy::Include :
Base64URLEncodePaddingPolicy::Omit;
nsresult rv = mozilla::Base64URLEncode(length, data, paddingPolicy, aResult);
if (NS_WARN_IF(NS_FAILED(rv))) {
aResult.Truncate();
aRv.Throw(rv);
@ -88,8 +90,26 @@ ThreadSafeChromeUtils::Base64URLDecode(GlobalObject& aGlobal,
JS::MutableHandle<JSObject*> aRetval,
ErrorResult& aRv)
{
Base64URLDecodePaddingPolicy paddingPolicy;
switch (aOptions.mPadding) {
case Base64URLDecodePadding::Require:
paddingPolicy = Base64URLDecodePaddingPolicy::Require;
break;
case Base64URLDecodePadding::Ignore:
paddingPolicy = Base64URLDecodePaddingPolicy::Ignore;
break;
case Base64URLDecodePadding::Reject:
paddingPolicy = Base64URLDecodePaddingPolicy::Reject;
break;
default:
aRv.Throw(NS_ERROR_INVALID_ARG);
return;
}
FallibleTArray<uint8_t> data;
nsresult rv = mozilla::Base64URLDecode(aString, aOptions, data);
nsresult rv = mozilla::Base64URLDecode(aString, paddingPolicy, data);
if (NS_WARN_IF(NS_FAILED(rv))) {
aRv.Throw(rv);
return;

Просмотреть файл

@ -88,8 +88,10 @@ function testDecode(input, decoded) {
function test_base64URLDecode() {
throws(_ => ChromeUtils.base64URLDecode(""), /TypeError/,
"Should require decoding options");
throws(_ => ChromeUtils.base64URLEncode("", {}), /TypeError/,
throws(_ => ChromeUtils.base64URLDecode("", {}), /TypeError/,
"Decoding should require the padding option");
throws(_ => ChromeUtils.base64URLDecode("", { padding: "chocolate" }),
"Decoding should throw for invalid padding policy");
for (let {decoded, encoded} of binaryTests) {
testDecode(encoded, decoded);

Просмотреть файл

@ -115,10 +115,9 @@ CryptoBuffer::FromJwkBase64(const nsString& aBase64)
NS_ConvertUTF16toUTF8 temp(aBase64);
temp.StripWhitespace();
Base64URLDecodeOptions options;
// JWK prohibits padding per RFC 7515, section 2.
options.mPadding = Base64URLDecodePadding::Reject;
nsresult rv = Base64URLDecode(temp, options, *this);
nsresult rv = Base64URLDecode(temp, Base64URLDecodePaddingPolicy::Reject,
*this);
NS_ENSURE_SUCCESS(rv, rv);
return NS_OK;
@ -134,9 +133,8 @@ CryptoBuffer::ToJwkBase64(nsString& aBase64)
}
nsAutoCString base64;
Base64URLEncodeOptions options;
options.mPad = false;
nsresult rv = Base64URLEncode(Length(), Elements(), options, base64);
nsresult rv = Base64URLEncode(Length(), Elements(),
Base64URLEncodePaddingPolicy::Omit, base64);
NS_ENSURE_SUCCESS(rv, rv);
CopyASCIItoUTF16(base64, aBase64);

Просмотреть файл

@ -341,13 +341,10 @@ PushSubscription::ToJSON(PushSubscriptionJSON& aJSON, ErrorResult& aRv)
aJSON.mEndpoint.Construct();
aJSON.mEndpoint.Value() = mEndpoint;
Base64URLEncodeOptions encodeOptions;
encodeOptions.mPad = false;
aJSON.mKeys.mP256dh.Construct();
nsresult rv = Base64URLEncode(mRawP256dhKey.Length(),
mRawP256dhKey.Elements(),
encodeOptions,
Base64URLEncodePaddingPolicy::Omit,
aJSON.mKeys.mP256dh.Value());
if (NS_WARN_IF(NS_FAILED(rv))) {
aRv.Throw(rv);
@ -356,7 +353,8 @@ PushSubscription::ToJSON(PushSubscriptionJSON& aJSON, ErrorResult& aRv)
aJSON.mKeys.mAuth.Construct();
rv = Base64URLEncode(mAuthSecret.Length(), mAuthSecret.Elements(),
encodeOptions, aJSON.mKeys.mAuth.Value());
Base64URLEncodePaddingPolicy::Omit,
aJSON.mKeys.mAuth.Value());
if (NS_WARN_IF(NS_FAILED(rv))) {
aRv.Throw(rv);
return;

Просмотреть файл

@ -215,11 +215,9 @@ NS_IMETHODIMP
IdentityCryptoService::Base64UrlEncode(const nsACString & utf8Input,
nsACString & result)
{
dom::Base64URLEncodeOptions options;
options.mPad = true;
return Base64URLEncode(utf8Input.Length(),
reinterpret_cast<const uint8_t*>(utf8Input.BeginReading()), options,
result);
reinterpret_cast<const uint8_t*>(utf8Input.BeginReading()),
Base64URLEncodePaddingPolicy::Include, result);
}
KeyPair::KeyPair(SECKEYPrivateKey * privateKey, SECKEYPublicKey * publicKey)
@ -513,9 +511,9 @@ SignRunnable::Run()
mRv = MapSECStatus(PK11_Sign(mPrivateKey, &sig, &hashItem));
}
if (NS_SUCCEEDED(mRv)) {
dom::Base64URLEncodeOptions encodeOptions;
encodeOptions.mPad = true;
mRv = Base64URLEncode(sig.len, sig.data, encodeOptions, mSignature);
mRv = Base64URLEncode(sig.len, sig.data,
Base64URLEncodePaddingPolicy::Include,
mSignature);
}
SECITEM_FreeItem(&sig, false);
}

Просмотреть файл

@ -391,7 +391,7 @@ Base64Decode(const nsAString& aBinaryData, nsAString& aString)
nsresult
Base64URLDecode(const nsACString& aString,
const dom::Base64URLDecodeOptions& aOptions,
Base64URLDecodePaddingPolicy aPaddingPolicy,
FallibleTArray<uint8_t>& aOutput)
{
// Don't decode empty strings.
@ -412,8 +412,8 @@ Base64URLDecode(const nsACString& aString,
// Determine whether to check for and ignore trailing padding.
bool maybePadded = false;
switch (aOptions.mPadding) {
case dom::Base64URLDecodePadding::Require:
switch (aPaddingPolicy) {
case Base64URLDecodePaddingPolicy::Require:
if (sourceLength % 4) {
// Padded input length must be a multiple of 4.
return NS_ERROR_INVALID_ARG;
@ -421,7 +421,7 @@ Base64URLDecode(const nsACString& aString,
maybePadded = true;
break;
case dom::Base64URLDecodePadding::Ignore:
case Base64URLDecodePaddingPolicy::Ignore:
// Check for padding only if the length is a multiple of 4.
maybePadded = !(sourceLength % 4);
break;
@ -429,8 +429,8 @@ Base64URLDecode(const nsACString& aString,
// If we're expecting unpadded input, no need for additional checks.
// `=` isn't in the decode table, so padded strings will fail to decode.
default:
MOZ_FALLTHROUGH_ASSERT("Invalid decode padding option");
case dom::Base64URLDecodePadding::Reject:
MOZ_FALLTHROUGH_ASSERT("Invalid decode padding policy");
case Base64URLDecodePaddingPolicy::Reject:
break;
}
if (maybePadded && source[sourceLength - 1] == '=') {
@ -487,7 +487,7 @@ Base64URLDecode(const nsACString& aString,
nsresult
Base64URLEncode(uint32_t aLength, const uint8_t* aData,
const dom::Base64URLEncodeOptions& aOptions,
Base64URLEncodePaddingPolicy aPaddingPolicy,
nsACString& aString)
{
// Don't encode empty strings.
@ -533,7 +533,7 @@ Base64URLEncode(uint32_t aLength, const uint8_t* aData,
}
uint32_t length = rawBuffer - aString.BeginWriting();
if (aOptions.mPad) {
if (aPaddingPolicy == Base64URLEncodePaddingPolicy::Include) {
if (length % 4 == 2) {
*rawBuffer++ = '=';
*rawBuffer++ = '=';
@ -542,6 +542,9 @@ Base64URLEncode(uint32_t aLength, const uint8_t* aData,
*rawBuffer++ = '=';
length += 1;
}
} else {
MOZ_ASSERT(aPaddingPolicy == Base64URLEncodePaddingPolicy::Omit,
"Invalid encode padding policy");
}
// Null terminate and truncate to the actual number of characters.

Просмотреть файл

@ -9,8 +9,6 @@
#include "nsString.h"
#include "mozilla/dom/ThreadSafeChromeUtilsBinding.h"
class nsIInputStream;
namespace mozilla {
@ -36,6 +34,11 @@ Base64Decode(const nsACString& aBinaryData, nsACString& aString);
nsresult
Base64Decode(const nsAString& aBinaryData, nsAString& aString);
enum class Base64URLEncodePaddingPolicy {
Include,
Omit,
};
/**
* Converts |aData| to an unpadded, Base64 URL-encoded string per RFC 4648.
* Aims to encode the data in constant time. The caller retains ownership
@ -43,15 +46,21 @@ Base64Decode(const nsAString& aBinaryData, nsAString& aString);
*/
nsresult
Base64URLEncode(uint32_t aLength, const uint8_t* aData,
const dom::Base64URLEncodeOptions& aOptions,
Base64URLEncodePaddingPolicy aPaddingPolicy,
nsACString& aString);
enum class Base64URLDecodePaddingPolicy {
Require,
Ignore,
Reject,
};
/**
* Decodes a Base64 URL-encoded |aString| into |aOutput|.
*/
nsresult
Base64URLDecode(const nsACString& aString,
const dom::Base64URLDecodeOptions& aOptions,
Base64URLDecodePaddingPolicy aPaddingPolicy,
FallibleTArray<uint8_t>& aOutput);
} // namespace mozilla