public void WriteFromDict <TKey, TValue> (IEnumerable <KeyValuePair <TKey, TValue> > val) { long origPos = stream.Position; // Pre-write array length field, we overwrite it at the end with the correct value WriteUInt32((uint)0); WritePad(8); long startPos = stream.Position; var keyWriter = WriteMethodFactory.CreateWriteMethodDelegate <TKey>(); var valueWriter = WriteMethodFactory.CreateWriteMethodDelegate <TValue>(); foreach (KeyValuePair <TKey, TValue> entry in val) { WritePad(8); keyWriter(this, entry.Key); valueWriter(this, entry.Value); } long endPos = stream.Position; uint ln = (uint)(endPos - startPos); stream.Position = origPos; if (ln > ProtocolInformation.MaxArrayLength) { throw new ProtocolException("Dict length " + ln + " exceeds maximum allowed " + ProtocolInformation.MaxArrayLength + " bytes"); } WriteUInt32(ln); stream.Position = endPos; }
public void LittleEndian( Type type, object writeValue, int alignment, byte[] bigEndianData, byte[] littleEndianData) { // via Delegate { MessageWriter writer = new MessageWriter(EndianFlag.Little); var method = s_createWriteDelegateMethod.MakeGenericMethod(type); var writeMethodDelegate = (Delegate)method.Invoke(null, null); writeMethodDelegate.DynamicInvoke(new object[] { writer, writeValue }); var bytes = writer.ToArray(); Assert.Equal(littleEndianData, bytes); } // via WriteMethod { MessageWriter writer = new MessageWriter(EndianFlag.Little); var writeMethodInfo = WriteMethodFactory.CreateWriteMethodForType(type, true); if (writeMethodInfo.IsStatic) { writeMethodInfo.Invoke(null, new object[] { writer, writeValue }); } else { writeMethodInfo.Invoke(writer, new object[] { writeValue }); } var bytes = writer.ToArray(); Assert.Equal(littleEndianData, bytes); } }
public void Invalid(Type type) { var method = s_createWriteDelegateMethod.MakeGenericMethod(type); Exception exception = null; try { method.Invoke(null, null); } catch (TargetInvocationException tie) { exception = tie.InnerException; } Assert.IsAssignableFrom <ArgumentException>(exception); Assert.Throws <ArgumentException>(() => WriteMethodFactory.CreateWriteMethodForType(type, true)); }
public void WriteArray <T> (IEnumerable <T> val) { Type elemType = typeof(T); var byteArray = val as byte[]; if (byteArray != null) { int valLength = val.Count(); if (byteArray.Length > ProtocolInformation.MaxArrayLength) { ThrowArrayLengthException((uint)byteArray.Length); } WriteUInt32((uint)byteArray.Length); stream.Write(byteArray, 0, byteArray.Length); return; } if (elemType.GetTypeInfo().IsEnum) { elemType = Enum.GetUnderlyingType(elemType); } Signature sigElem = Signature.GetSig(elemType, isCompileTimeType: true); int fixedSize = 0; if (endianness == Environment.NativeEndianness && elemType.GetTypeInfo().IsValueType&& !sigElem.IsStruct && elemType != typeof(bool) && sigElem.GetFixedSize(ref fixedSize) && val is Array) { var array = val as Array; int byteLength = fixedSize * array.Length; if (byteLength > ProtocolInformation.MaxArrayLength) { ThrowArrayLengthException((uint)byteLength); } WriteUInt32((uint)byteLength); WritePad(sigElem.Alignment); byte[] data = new byte[byteLength]; Buffer.BlockCopy(array, 0, data, 0, data.Length); stream.Write(data, 0, data.Length); return; } long origPos = stream.Position; WriteUInt32((uint)0); WritePad(sigElem.Alignment); long startPos = stream.Position; var tWriter = WriteMethodFactory.CreateWriteMethodDelegate <T>(); foreach (T elem in val) { tWriter(this, elem); } long endPos = stream.Position; uint ln = (uint)(endPos - startPos); stream.Position = origPos; if (ln > ProtocolInformation.MaxArrayLength) { ThrowArrayLengthException(ln); } WriteUInt32(ln); stream.Position = endPos; }
public void Write(Type type, object val, bool isCompileTimeType) { if (type.GetTypeInfo().IsEnum) { type = Enum.GetUnderlyingType(type); } if (type == typeof(bool)) { WriteBoolean((bool)val); return; } else if (type == typeof(byte)) { WriteByte((byte)val); return; } else if (type == typeof(double)) { WriteDouble((double)val); return; } else if (type == typeof(short)) { WriteInt16((short)val); return; } else if (type == typeof(int)) { WriteInt32((int)val); return; } else if (type == typeof(long)) { WriteInt64((long)val); return; } else if (type == typeof(ObjectPath)) { WriteObjectPath((ObjectPath)val); return; } else if (type == typeof(Signature)) { WriteSignature((Signature)val); return; } else if (type == typeof(string)) { WriteString((string)val); return; } else if (type == typeof(float)) { WriteSingle((float)val); return; } else if (type == typeof(ushort)) { WriteUInt16((ushort)val); return; } else if (type == typeof(uint)) { WriteUInt32((uint)val); return; } else if (type == typeof(ulong)) { WriteUInt64((ulong)val); return; } else if (type == typeof(object)) { WriteVariant(val); return; } else if (type == typeof(IDBusObject)) { WriteBusObject((IDBusObject)val); return; } if (ArgTypeInspector.IsDBusObjectType(type, isCompileTimeType)) { WriteBusObject((IDBusObject)val); return; } if (ArgTypeInspector.IsSafeHandleType(type)) { WriteSafeHandle((SafeHandle)val); return; } MethodInfo method = WriteMethodFactory.CreateWriteMethodForType(type, isCompileTimeType); if (method.IsStatic) { method.Invoke(null, new object[] { this, val }); } else { method.Invoke(this, new object[] { val }); } }