private int CalculateSize(BsonToken t) { switch (t.Type) { case BsonType.Object: { BsonObject value = (BsonObject)t; int bases = 4; foreach (BsonProperty p in value) { int size = 1; size += CalculateSize(p.Name); size += CalculateSize(p.Value); bases += size; } bases += 1; value.CalculatedSize = bases; return(bases); } case BsonType.Array: { BsonArray value = (BsonArray)t; int size = 4; ulong index = 0; foreach (BsonToken c in value) { size += 1; size += CalculateSize(MathUtils.IntLength(index)); size += CalculateSize(c); index++; } size += 1; value.CalculatedSize = size; return(value.CalculatedSize); } case BsonType.Integer: return(4); case BsonType.Long: return(8); case BsonType.Number: return(8); case BsonType.String: { BsonString value = (BsonString)t; string s = (string)value.Value; value.ByteCount = (s != null) ? Encoding.GetByteCount(s) : 0; value.CalculatedSize = CalculateSizeWithLength(value.ByteCount, value.IncludeLength); return(value.CalculatedSize); } case BsonType.Boolean: return(1); case BsonType.Null: case BsonType.Undefined: return(0); case BsonType.Date: return(8); case BsonType.Binary: { BsonBinary value = (BsonBinary)t; byte[] data = (byte[])value.Value; value.CalculatedSize = 4 + 1 + data.Length; return(value.CalculatedSize); } case BsonType.Oid: return(12); case BsonType.Regex: { BsonRegex value = (BsonRegex)t; int size = 0; size += CalculateSize(value.Pattern); size += CalculateSize(value.Options); value.CalculatedSize = size; return(value.CalculatedSize); } default: throw new ArgumentOutOfRangeException(nameof(t), "Unexpected token when writing BSON: {0}".FormatWith(CultureInfo.InvariantCulture, t.Type)); } }