1b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer#region Copyright notice and license 2b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// Protocol Buffers - Google's data interchange format 3b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// Copyright 2008 Google Inc. All rights reserved. 4b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// https://developers.google.com/protocol-buffers/ 5b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// 6b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// Redistribution and use in source and binary forms, with or without 7b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// modification, are permitted provided that the following conditions are 8b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// met: 9b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// 10b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// * Redistributions of source code must retain the above copyright 11b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// notice, this list of conditions and the following disclaimer. 12b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// * Redistributions in binary form must reproduce the above 13b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// copyright notice, this list of conditions and the following disclaimer 14b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// in the documentation and/or other materials provided with the 15b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// distribution. 16b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// * Neither the name of Google Inc. nor the names of its 17b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// contributors may be used to endorse or promote products derived from 18b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// this software without specific prior written permission. 19b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// 20b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 21b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 22b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 23b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 24b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 25b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 26b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 27b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 28b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 29b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 30b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 31b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer#endregion 32b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 33b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammerusing System; 34b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammerusing System.Collections; 35b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammerusing System.Collections.Generic; 36b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammerusing System.IO; 37b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammerusing System.Text; 38b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 39b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammernamespace Google.Protobuf 40b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer{ 41b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 42b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Immutable array of bytes. 43b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 44b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public sealed class ByteString : IEnumerable<byte>, IEquatable<ByteString> 45b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 46b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer private static readonly ByteString empty = new ByteString(new byte[0]); 47b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 48b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer private readonly byte[] bytes; 49b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 50b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 51b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Unsafe operations that can cause IO Failure and/or other catestrophic side-effects. 52b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 53b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer internal static class Unsafe 54b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 55b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 56b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Constructs a new ByteString from the given byte array. The array is 57b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// *not* copied, and must not be modified after this constructor is called. 58b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 59b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer internal static ByteString FromBytes(byte[] bytes) 60b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 61b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return new ByteString(bytes); 62b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 63b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 64b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 65b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Provides direct, unrestricted access to the bytes contained in this instance. 66b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// You must not modify or resize the byte array returned by this method. 67b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 68b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer internal static byte[] GetBuffer(ByteString bytes) 69b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 70b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return bytes.bytes; 71b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 72b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 73b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 74b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 75b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Internal use only. Ensure that the provided array is not mutated and belongs to this instance. 76b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 77b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer internal static ByteString AttachBytes(byte[] bytes) 78b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 79b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return new ByteString(bytes); 80b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 81b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 82b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 83b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Constructs a new ByteString from the given byte array. The array is 84b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// *not* copied, and must not be modified after this constructor is called. 85b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 86b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer private ByteString(byte[] bytes) 87b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 88b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer this.bytes = bytes; 89b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 90b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 91b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 92b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Returns an empty ByteString. 93b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 94b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static ByteString Empty 95b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 96b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer get { return empty; } 97b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 98b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 99b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 100b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Returns the length of this ByteString in bytes. 101b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 102b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public int Length 103b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 104b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer get { return bytes.Length; } 105b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 106b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 107b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 108b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Returns <c>true</c> if this byte string is empty, <c>false</c> otherwise. 109b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 110b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public bool IsEmpty 111b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 112b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer get { return Length == 0; } 113b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 114b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 115b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 116b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Converts this <see cref="ByteString"/> into a byte array. 117b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 118b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <remarks>The data is copied - changes to the returned array will not be reflected in this <c>ByteString</c>.</remarks> 119b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns>A byte array with the same data as this <c>ByteString</c>.</returns> 120b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public byte[] ToByteArray() 121b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 122b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return (byte[]) bytes.Clone(); 123b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 124b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 125b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 126b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Converts this <see cref="ByteString"/> into a standard base64 representation. 127b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 128b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns>A base64 representation of this <c>ByteString</c>.</returns> 129b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public string ToBase64() 130b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 131b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return Convert.ToBase64String(bytes); 132b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 133b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 134b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 135b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Constructs a <see cref="ByteString" /> from the Base64 Encoded String. 136b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 137b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static ByteString FromBase64(string bytes) 138b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 139b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer // By handling the empty string explicitly, we not only optimize but we fix a 140b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer // problem on CF 2.0. See issue 61 for details. 141b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return bytes == "" ? Empty : new ByteString(Convert.FromBase64String(bytes)); 142b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 143b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 144b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 145b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Constructs a <see cref="ByteString" /> from the given array. The contents 146b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// are copied, so further modifications to the array will not 147b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// be reflected in the returned ByteString. 148b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// This method can also be invoked in <c>ByteString.CopyFrom(0xaa, 0xbb, ...)</c> form 149b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// which is primarily useful for testing. 150b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 151b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static ByteString CopyFrom(params byte[] bytes) 152b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 153b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return new ByteString((byte[]) bytes.Clone()); 154b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 155b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 156b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 157b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Constructs a <see cref="ByteString" /> from a portion of a byte array. 158b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 159b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static ByteString CopyFrom(byte[] bytes, int offset, int count) 160b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 161b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer byte[] portion = new byte[count]; 162b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer ByteArray.Copy(bytes, offset, portion, 0, count); 163b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return new ByteString(portion); 164b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 165b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 166b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 167b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Creates a new <see cref="ByteString" /> by encoding the specified text with 168b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// the given encoding. 169b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 170b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static ByteString CopyFrom(string text, Encoding encoding) 171b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 172b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return new ByteString(encoding.GetBytes(text)); 173b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 174b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 175b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 176b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Creates a new <see cref="ByteString" /> by encoding the specified text in UTF-8. 177b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 178b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static ByteString CopyFromUtf8(string text) 179b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 180b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return CopyFrom(text, Encoding.UTF8); 181b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 182b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 183b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 184b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Retuns the byte at the given index. 185b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 186b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public byte this[int index] 187b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 188b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer get { return bytes[index]; } 189b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 190b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 191b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 192b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Converts this <see cref="ByteString"/> into a string by applying the given encoding. 193b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 194b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <remarks> 195b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// This method should only be used to convert binary data which was the result of encoding 196b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// text with the given encoding. 197b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </remarks> 198b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <param name="encoding">The encoding to use to decode the binary data into text.</param> 199b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns>The result of decoding the binary data with the given decoding.</returns> 200b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public string ToString(Encoding encoding) 201b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 202b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return encoding.GetString(bytes, 0, bytes.Length); 203b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 204b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 205b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 206b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Converts this <see cref="ByteString"/> into a string by applying the UTF-8 encoding. 207b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 208b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <remarks> 209b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// This method should only be used to convert binary data which was the result of encoding 210b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// text with UTF-8. 211b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </remarks> 212b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns>The result of decoding the binary data with the given decoding.</returns> 213b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public string ToStringUtf8() 214b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 215b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return ToString(Encoding.UTF8); 216b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 217b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 218b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 219b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Returns an iterator over the bytes in this <see cref="ByteString"/>. 220b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 221b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns>An iterator over the bytes in this object.</returns> 222b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public IEnumerator<byte> GetEnumerator() 223b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 224b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return ((IEnumerable<byte>) bytes).GetEnumerator(); 225b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 226b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 227b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 228b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Returns an iterator over the bytes in this <see cref="ByteString"/>. 229b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 230b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns>An iterator over the bytes in this object.</returns> 231b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer IEnumerator IEnumerable.GetEnumerator() 232b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 233b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return GetEnumerator(); 234b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 235b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 236b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 237b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Creates a CodedInputStream from this ByteString's data. 238b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 239b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public CodedInputStream CreateCodedInput() 240b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 241b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer // We trust CodedInputStream not to reveal the provided byte array or modify it 242b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return new CodedInputStream(bytes); 243b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 244b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 245b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 246b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Compares two byte strings for equality. 247b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 248b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <param name="lhs">The first byte string to compare.</param> 249b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <param name="rhs">The second byte string to compare.</param> 250b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns><c>true</c> if the byte strings are equal; false otherwise.</returns> 251b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static bool operator ==(ByteString lhs, ByteString rhs) 252b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 253b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer if (ReferenceEquals(lhs, rhs)) 254b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 255b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return true; 256b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 257b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer if (ReferenceEquals(lhs, null) || ReferenceEquals(rhs, null)) 258b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 259b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return false; 260b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 261b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer if (lhs.bytes.Length != rhs.bytes.Length) 262b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 263b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return false; 264b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 265b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer for (int i = 0; i < lhs.Length; i++) 266b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 267b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer if (rhs.bytes[i] != lhs.bytes[i]) 268b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 269b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return false; 270b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 271b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 272b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return true; 273b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 274b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 275b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 276b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Compares two byte strings for inequality. 277b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 278b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <param name="lhs">The first byte string to compare.</param> 279b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <param name="rhs">The second byte string to compare.</param> 280b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns><c>false</c> if the byte strings are equal; true otherwise.</returns> 281b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public static bool operator !=(ByteString lhs, ByteString rhs) 282b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 283b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return !(lhs == rhs); 284b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 285b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 286b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 287b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Compares this byte string with another object. 288b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 289b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <param name="obj">The object to compare this with.</param> 290b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns><c>true</c> if <paramref name="obj"/> refers to an equal <see cref="ByteString"/>; <c>false</c> otherwise.</returns> 291b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public override bool Equals(object obj) 292b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 293b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return this == (obj as ByteString); 294b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 295b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 296b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 297b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Returns a hash code for this object. Two equal byte strings 298b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// will return the same hash code. 299b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 300b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns>A hash code for this object.</returns> 301b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public override int GetHashCode() 302b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 303b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer int ret = 23; 304b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer foreach (byte b in bytes) 305b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 306b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer ret = (ret << 8) | b; 307b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 308b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return ret; 309b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 310b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 311b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 312b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Compares this byte string with another. 313b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 314b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <param name="other">The <see cref="ByteString"/> to compare this with.</param> 315b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <returns><c>true</c> if <paramref name="other"/> refers to an equal byte string; <c>false</c> otherwise.</returns> 316b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public bool Equals(ByteString other) 317b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 318b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer return this == other; 319b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 320b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 321b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 322b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Used internally by CodedOutputStream to avoid creating a copy for the write 323b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 324b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer internal void WriteRawBytesTo(CodedOutputStream outputStream) 325b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 326b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer outputStream.WriteRawBytes(bytes, 0, bytes.Length); 327b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 328b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 329b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 330b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Copies the entire byte array to the destination array provided at the offset specified. 331b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 332b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public void CopyTo(byte[] array, int position) 333b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 334b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer ByteArray.Copy(bytes, 0, array, position, bytes.Length); 335b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 336b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer 337b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// <summary> 338b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// Writes the entire byte array to the provided stream 339b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer /// </summary> 340b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer public void WriteTo(Stream outputStream) 341b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer { 342b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer outputStream.Write(bytes, 0, bytes.Length); 343b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 344b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer } 345b0575e93e4c39dec69365b850088a1eb7f82c5b3Tamas Berghammer}