Example #1
0
        internal static async Task WriteFinalFromBase64Urlsafe(
            this Stream stream, Memory <byte> base64Memory,
            CancellationToken cancelToken = default)
        {
            int base64Count = CommonBase64UrlSafe.RevertUrlSafeUtf8(base64Memory.Span,
                                                                    out int base64PadCount);
            int base64Length = base64Memory.Length + base64PadCount;

            using (var base64FinalBuffer = bytesPool.Rent(base64Length))
            {
                Memory <byte> base64FinalMemory = base64FinalBuffer.Memory;
                base64Memory.CopyTo(base64FinalMemory);
                Memory <byte> base64PadMemory = base64FinalMemory.Slice(base64Memory.Length, base64PadCount);
                base64PadMemory.Span.Fill(base64PadByte);

                int bytesRequired  = Base64.GetMaxDecodedFromUtf8Length(base64Count + base64PadCount);
                int base64Consumed = await stream.WritePartialFromBase64(
                    base64FinalMemory.Slice(0, base64Length), bytesRequired,
                    isFinalBlock : true, cancelToken).ConfigureAwait(false);

                if (base64Consumed < base64Length)
                {
                    throw new InvalidOperationException("Base64 decode of final block did not consume all bytes");
                }
            }
        }
Example #2
0
        internal static async Task <(int base64Remaining, int base64PadCount)> WritePartialFromBase64Urlsafe(
            this Stream stream, Memory <byte> base64Memory,
            CancellationToken cancelToken = default)
        {
            int base64Count = CommonBase64UrlSafe.RevertUrlSafeUtf8(base64Memory.Span,
                                                                    out int base64PaddingRequired);
            int bytesRequired  = Base64.GetMaxDecodedFromUtf8Length(base64Count);
            int base64Consumed = await stream.WritePartialFromBase64(base64Memory,
                                                                     bytesRequired, isFinalBlock : false, cancelToken)
                                 .ConfigureAwait(false);

            Memory <byte> base64Remaining = base64Memory.Slice(base64Consumed);

            base64Remaining.CopyTo(base64Memory);
            return(base64Remaining.Length, base64PaddingRequired);
        }