//this requires a seekable stream for now
        public void Write(Type type, Array val)
        {
            Type elemType = type.GetElementType();

            //TODO: more fast paths for primitive arrays
            if (elemType == typeof(byte))
            {
                Write((uint)val.Length);
                stream.Write((byte[])val, 0, val.Length);
                return;
            }

            Write((uint)0);
            long lengthPos = stream.Position - 4;

            //advance to the alignment of the element
            WritePad(Protocol.GetAlignment(Signature.TypeToDType(elemType)));

            long startPos = stream.Position;

            foreach (object elem in val)
            {
                Write(elemType, elem);
            }

            long endPos = stream.Position;

            stream.Position = lengthPos;
            Write((uint)(endPos - startPos));

            stream.Position = endPos;
        }
        //this requires a seekable stream for now
        public void WriteArray(object obj, Type elemType)
        {
            Array val = (Array)obj;

            //TODO: more fast paths for primitive arrays
            if (elemType == typeof(byte))
            {
                if (val.Length > Protocol.MaxArrayLength)
                {
                    throw new Exception("Array length " + val.Length + " exceeds maximum allowed " + Protocol.MaxArrayLength + " bytes");
                }

                Write((uint)val.Length);
                stream.Write((byte[])val, 0, val.Length);
                return;
            }

            long origPos = stream.Position;

            Write((uint)0);

            //advance to the alignment of the element
            WritePad(Protocol.GetAlignment(Signature.TypeToDType(elemType)));

            long startPos = stream.Position;

            foreach (object elem in val)
            {
                Write(elemType, elem);
            }

            long endPos = stream.Position;
            uint ln     = (uint)(endPos - startPos);

            stream.Position = origPos;

            if (ln > Protocol.MaxArrayLength)
            {
                throw new Exception("Array length " + ln + " exceeds maximum allowed " + Protocol.MaxArrayLength + " bytes");
            }

            Write(ln);
            stream.Position = endPos;
        }
        //this could be made generic to avoid boxing
        public void GetValue(Type type, out Array val)
        {
            Type elemType = type.GetElementType();

            uint ln;

            GetValue(out ln);

            //TODO: more fast paths for primitive arrays
            if (elemType == typeof(byte))
            {
                byte[] valb = new byte[ln];
                Array.Copy(data, pos, valb, 0, (int)ln);
                val  = valb;
                pos += (int)ln;
                return;
            }

            //advance to the alignment of the element
            ReadPad(Protocol.GetAlignment(Signature.TypeToDType(elemType)));

            int endPos = pos + (int)ln;

            //List<T> vals = new List<T> ();
            System.Collections.ArrayList vals = new System.Collections.ArrayList();

            //while (stream.Position != endPos)
            while (pos < endPos)
            {
                object elem;
                //GetValue (Signature.TypeToDType (elemType), out elem);
                GetValue(elemType, out elem);
                vals.Add(elem);
            }

            if (pos != endPos)
            {
                throw new Exception("Read pos " + pos + " != ep " + endPos);
            }

            val = vals.ToArray(elemType);
            //val = Array.CreateInstance (elemType.UnderlyingSystemType, vals.Count);
        }
Example #4
0
        //this could be made generic to avoid boxing
        public Array ReadArray(Type elemType)
        {
            uint ln = ReadUInt32();

            if (ln > Protocol.MaxArrayLength)
            {
                throw new Exception("Array length " + ln + " exceeds maximum allowed " + Protocol.MaxArrayLength + " bytes");
            }

            //TODO: more fast paths for primitive arrays
            if (elemType == typeof(byte))
            {
                byte[] valb = new byte[ln];
                Array.Copy(data, pos, valb, 0, (int)ln);
                pos += (int)ln;
                return(valb);
            }

            //advance to the alignment of the element
            ReadPad(Protocol.GetAlignment(Signature.TypeToDType(elemType)));

            int endPos = pos + (int)ln;

            //List<T> vals = new List<T> ();
            System.Collections.ArrayList vals = new System.Collections.ArrayList();

            //while (stream.Position != endPos)
            while (pos < endPos)
            {
                vals.Add(ReadValue(elemType));
            }

            if (pos != endPos)
            {
                throw new Exception("Read pos " + pos + " != ep " + endPos);
            }

            return(vals.ToArray(elemType));
        }