Beispiel #1
0
        private Object FastpathV3(Int32 fnid, Boolean resulttype, FastpathArg[] args)
        {
            // give  thread safety
            lock (stream)
            {
                // send the function call

                {
                    Int32 l_msgLen = 0;
                    l_msgLen += 16;
                    for (Int32 i = 0; i < args.Length; i++)
                    {
                        l_msgLen += args[i].SendSize();
                    }

                    stream
                        .WriteByte(ASCIIByteArrays.FunctionCallMessageCode)
                        .WriteInt32(l_msgLen)
                        .WriteInt32(fnid)
                        .WriteInt16(1)
                        .WriteInt16(1)
                        .WriteInt16((short)args.Length);

                    for (Int32 i = 0; i < args.Length; i++)
                    {
                        args[i].Send(stream);
                    }

                    stream.WriteInt16(1);

                    // This is needed, otherwise data can be lost
                    stream.Flush();
                }

                // Now handle the result

                // Now loop, reading the results
                Object result = null; // our result
                Exception error = null;
                Int32 c;
                Boolean l_endQuery = false;

                while (!l_endQuery)
                {
                    c = (Char) stream.ReadByte();

                    switch (c)
                    {
                        case 'A': // Asynchronous Notify
                            Int32 msglen = stream.ReadInt32();
                            Int32 pid = stream.ReadInt32();
                            String msg = stream.ReadString();
                            stream.ReadString();
                            String param = stream.ReadString();

                            break;
                            //------------------------------
                            // Error message returned
                        case 'E':
                            NpgsqlError e = new NpgsqlError(stream);
                            throw new NpgsqlException(e.ToString());

                            //------------------------------
                            // Notice from backend
                        case 'N':
                            Int32 l_nlen = stream.ReadInt32();

                            conn.Connector.FireNotice(new NpgsqlError(stream));

                            break;

                        case 'V':
                            Int32 l_msgLen = stream.ReadInt32();
                            Int32 l_valueLen = stream.ReadInt32();

                            if (l_valueLen == -1)
                            {
                                //null value
                            }
                            else if (l_valueLen == 0)
                            {
                                result = new Byte[0];
                            }
                            else
                            {
                                // Return an Integer if
                                if (resulttype)
                                {
                                    result = stream.ReadInt32();
                                }
                                else
                                {
                                    Byte[] buf = new Byte[l_valueLen];

                                    Int32 bytes_from_stream = 0;
                                    Int32 total_bytes_read = 0;
                                    Int32 size = l_valueLen;
                                    do
                                    {
                                        bytes_from_stream = stream.Read(buf, total_bytes_read, size);
                                        total_bytes_read += bytes_from_stream;
                                        size -= bytes_from_stream;
                                    }
                                    while (size > 0);

                                    result = buf;
                                }
                            }
                            break;

                        case 'Z':
                            //TODO: use size better
                            if (stream.ReadInt32() != 5)
                            {
                                throw new Exception("Received Z");
                            }
                            //TODO: handle transaction status
                            Char l_tStatus = (Char) stream.ReadByte();
                            l_endQuery = true;
                            break;

                        default:
                            throw new Exception(string.Format("postgresql.fp.protocol received {0}", c));
                    }
                }

                if (error != null)
                {
                    throw error;
                }

                return result;
            }
        }
Beispiel #2
0
 internal NpgsqlException(NpgsqlError error)
     : base(error.ToString())
 {
     this.errors = new NpgsqlError[1];
     errors[0]   = error;
 }
Beispiel #3
0
 internal NpgsqlException(NpgsqlError error)
     : base(error.ToString())
 {
     this.errors = new NpgsqlError[1];
     errors[0] = error;
 }
        private Object FastpathV3(Int32 fnid, Boolean resulttype, FastpathArg[] args)
        {
            // give  thread safety
            lock (stream)
            {
                // send the function call
                try
                {
                    Int32 l_msgLen = 0;
                    l_msgLen += 16;
                    for (Int32 i=0;i < args.Length;i++)
                        l_msgLen += args[i].SendSize();

                    stream.WriteByte((Byte)'F');
                    PGUtil.WriteInt32(stream,l_msgLen);
                    PGUtil.WriteInt32(stream,fnid);
                    PGUtil.WriteInt16(stream,1);
                    PGUtil.WriteInt16(stream,1);
                    PGUtil.WriteInt16(stream,(short)args.Length);

                    for (Int32 i = 0;i < args.Length;i++)
                        args[i].Send(stream);

                    PGUtil.WriteInt16(stream,1);

                    // This is needed, otherwise data can be lost
                    stream.Flush();

                }
                catch (Exception ex)
                {
                    throw new Exception(ex.ToString());
                }

                // Now handle the result

                // Now loop, reading the results
                Object result = null; // our result
                Exception error = null;
                Int32 c;
                Boolean l_endQuery = false;
                Byte[] input_buffer = new Byte[512];

                while (!l_endQuery)
                {
                    c = (Char)stream.ReadByte();

                    switch (c)
                    {
                    case 'A':	// Asynchronous Notify
                        Int32 msglen = PGUtil.ReadInt32(stream,input_buffer);
                        Int32 pid = PGUtil.ReadInt32(stream,input_buffer);
                        String msg = PGUtil.ReadString(stream,conn.Connector.Encoding);
                        PGUtil.ReadString(stream,conn.Connector.Encoding);
                        String param = PGUtil.ReadString(stream,conn.Connector.Encoding);

                        conn.Connector.CheckErrorsAndNotifications();
                        break;
                        //------------------------------
                        // Error message returned
                    case 'E':
                        NpgsqlError e = new NpgsqlError(conn.BackendProtocolVersion);
                        e.ReadFromStream(stream,conn.Connector.Encoding);
                        throw new Exception(e.ToString());

                        //------------------------------
                        // Notice from backend
                    case 'N':
                        Int32 l_nlen = PGUtil.ReadInt32(stream,input_buffer);

                        NpgsqlError e1 = new NpgsqlError(conn.BackendProtocolVersion);
                        e1.ReadFromStream(stream,conn.Connector.Encoding);
                        conn.Connector.Mediator.Errors.Add(e1);

                        break;

                    case 'V':
                        Int32 l_msgLen = PGUtil.ReadInt32(stream,input_buffer);
                        Int32 l_valueLen = PGUtil.ReadInt32(stream,input_buffer);

                        if (l_valueLen == -1)
                        {
                            //null value
                        }
                        else if (l_valueLen == 0)
                        {
                            result = new Byte[0];
                        }
                        else
                        {
                            // Return an Integer if
                            if (resulttype)

                                result = PGUtil.ReadInt32(stream,input_buffer);
                            else
                            {
                                Byte[] buf = new Byte[l_valueLen];

                                Int32 bytes_from_stream = 0;
                                Int32 total_bytes_read = 0;
                                Int32 size = l_valueLen;
                                do
                                {
                                    bytes_from_stream = stream.Read(buf, total_bytes_read, size);
                                    total_bytes_read += bytes_from_stream;
                                    size -= bytes_from_stream;
                                }
                                while(size > 0);

                                result = buf;
                            }
                        }
                        break;

                    case 'Z':
                        //TODO: use size better
                        if (PGUtil.ReadInt32(stream,input_buffer) != 5)
                            throw new Exception("Received Z" );
                        //TODO: handle transaction status
                        Char l_tStatus = (Char)stream.ReadByte();
                        l_endQuery = true;
                        break;

                    default:
                        throw new Exception("postgresql.fp.protocol received " + c.ToString());
                    }
                }

                if ( error != null )
                    throw error;

                return result;
            }
        }