예제 #1
0
        /**
         * Wait for a message to arrive for this mailbox.
         *
         * @param timeout
         *                the time, in milliseconds, to wait for a message.
         *
         * @return an {@link OtpMsg OtpMsg} containing the header information as
         *         well as the body of the next message waiting in this mailbox.
         *
         * @exception OtpErlangExit
         *                    if a linked {@link OtpErlangPid pid} has exited or has
         *                    sent an exit signal to this mailbox.
         *
         * @exception InterruptedException
         *                    if no message if the method times out before a message
         *                    becomes available.
         */
        public virtual OtpMsg receiveMsg(long timeout)
        {
            OtpMsg m = (OtpMsg)queue.get(timeout);

            if (m == null)
            {
                return(null);
            }

            switch (m.type())
            {
            case OtpMsg.exitTag:
            case OtpMsg.exit2Tag:
                try
                {
                    OtpErlangObject o = m.getMsg();
                    throw new OtpErlangExit(o, m.getSenderPid());
                }
                catch (OtpErlangDecodeException)
                {
                    throw new OtpErlangExit("unknown", m.getSenderPid());
                }

            default:
                return(m);
            }
        }
예제 #2
0
        /*
         * this method simulates net_kernel only for the purpose of replying to
         * pings.
         */
        private bool netKernel(OtpMsg m)
        {
            OtpMbox mbox = null;

            try
            {
                OtpErlangTuple t   = (OtpErlangTuple)m.getMsg();
                OtpErlangTuple req = (OtpErlangTuple)t.elementAt(1); // actual
                // request

                OtpErlangPid pid = (OtpErlangPid)req.elementAt(0); // originating
                // pid

                OtpErlangObject[] pong = new OtpErlangObject[2];
                pong[0] = req.elementAt(1); // his #Ref
                pong[1] = new OtpErlangAtom("yes");

                mbox = createMbox(true);
                mbox.send(pid, new OtpErlangTuple(pong));
                return(true);
            }
            catch (Exception)
            {
            }
            finally
            {
                closeMbox(mbox);
            }
            return(false);
        }
예제 #3
0
        /*
         * Pass a message to the node for final delivery. Note that the connection
         * itself needs to know about links (in case of connection failure), so we
         * snoop for link/unlink too here.
         */
        public override void Deliver(OtpMsg msg)
        {
            bool delivered = self.Deliver(msg);

            switch (msg.Type)
            {
            case OtpMsg.linkTag:
                if (delivered)
                {
                    lock (lockObj)
                        links.AddLink(msg.ToPid, msg.FromPid);
                    break;
                }

                // no such pid - send exit to sender
                try { SendExit(msg.ToPid, msg.FromPid, new OtpErlangAtom("noproc")); }
                catch (IOException) { }
                break;

            case OtpMsg.unlinkTag:
            case OtpMsg.exitTag:
                lock (lockObj)
                    links.RemoveLink(msg.ToPid, msg.FromPid);
                break;

            case OtpMsg.exit2Tag:
                break;
            }
        }
예제 #4
0
        /*
         * pass the message to the node for final delivery. Note that the connection
         * itself needs to know about links (in case of connection failure), so we
         * snoop for link/unlink too here.
         */
        public override void deliver(OtpMsg msg)
        {
            bool delivered = self.deliver(msg);

            switch (msg.type())
            {
            case OtpMsg.linkTag:
                if (delivered)
                {
                    links.addLink(msg.getRecipientPid(), msg.getSenderPid());
                }
                else
                {
                    try
                    {
                        // no such pid - send exit to sender
                        base.sendExit(msg.getRecipientPid(), msg.getSenderPid(), new OtpErlangAtom("noproc"));
                    }
                    catch (IOException)
                    {
                    }
                }
                break;

            case OtpMsg.unlinkTag:
            case OtpMsg.exitTag:
                links.removeLink(msg.getRecipientPid(), msg.getSenderPid());
                break;

            case OtpMsg.exit2Tag:
                break;
            }

            return;
        }
예제 #5
0
        /**
         * Wait for a message to arrive for this mailbox.
         *
         * @param timeout
         *                the time, in milliseconds, to wait for a message before
         *                returning null.
         *
         * @return a byte array representing the still-encoded body of the next
         *         message waiting in this mailbox.
         *
         * @exception OtpErlangExit
         *                    if a linked {@link OtpErlangPid pid} has exited or has
         *                    sent an exit signal to this mailbox.
         *
         * @exception InterruptedException
         *                    if no message if the method times out before a message
         *                    becomes available.
         */
        public OtpInputStream receiveBuf(long timeout)
        {
            OtpMsg m = receiveMsg(timeout);

            if (m != null)
            {
                return(m.getMsgBuf());
            }

            return(null);
        }
예제 #6
0
        /*
         * Process EXIT by throwing OtpExit, otherwise return message
         */
        private OtpMsg ProcessMsg(OtpMsg m)
        {
            switch (m.Type)
            {
            case OtpMsg.exitTag:
            case OtpMsg.exit2Tag:
                try
                {
                    throw new OtpExit(m.Payload, m.FromPid);
                }
                catch (OtpDecodeException)
                {
                    throw new OtpExit("unknown", m.FromPid);
                }

            default:
                return(m);
            }
        }
예제 #7
0
        /*
         * OtpCookedConnection delivers messages here return true if message was
         * delivered successfully, or false otherwise.
         */
        public bool deliver(OtpMsg m)
        {
            OtpMbox mbox = null;

            try
            {
                int t = m.type();

                if (t == OtpMsg.regSendTag)
                {
                    String name = m.getRecipientName();
                    /* special case for netKernel requests */
                    if (name.Equals("net_kernel"))
                    {
                        return(netKernel(m));
                    }
                    else
                    {
                        mbox = mboxes.get(name);
                    }
                }
                else
                {
                    mbox = mboxes.get(m.getRecipientPid());
                }

                if (mbox == null)
                {
                    return(false);
                }
                mbox.deliver(m);
            }
            catch (Exception)
            {
                return(false);
            }

            return(true);
        }
예제 #8
0
 /**
  * Wait for a message to arrive for this mailbox.
  *
  * @param timeout
  *                the time, in milliseconds, to wait for a message before
  *                returning null.
  *
  * @return an {@link OtpErlangObject OtpErlangObject} representing the body
  *         of the next message waiting in this mailbox.
  *
  * @exception OtpErlangDecodeException
  *                    if the message can not be decoded.
  *
  * @exception OtpErlangExit
  *                    if a linked {@link OtpErlangPid pid} has exited or has
  *                    sent an exit signal to this mailbox.
  */
 public OtpErlangObject receive(long timeout)
 {
     try
     {
         OtpMsg m = receiveMsg(timeout);
         if (m != null)
         {
             return(m.getMsg());
         }
     }
     catch (OtpErlangExit e)
     {
         throw e;
     }
     catch (OtpErlangDecodeException f)
     {
         throw f;
     }
     catch (ThreadInterruptedException)
     {
     }
     return(null);
 }
예제 #9
0
        /*
         * called by OtpNode to deliver message to this mailbox.
         *
         * About exit and exit2: both cause exception to be raised upon receive().
         * However exit (not 2) causes any link to be removed as well, while exit2
         * leaves any links intact.
         */
        public virtual void deliver(OtpMsg m)
        {
            switch (m.type())
            {
            case OtpMsg.linkTag:
                links.addLink(self, m.getSenderPid());
                break;

            case OtpMsg.unlinkTag:
                links.removeLink(self, m.getSenderPid());
                break;

            case OtpMsg.exitTag:
                links.removeLink(self, m.getSenderPid());
                queue.put(m);
                break;

            case OtpMsg.exit2Tag:
            default:
                queue.put(m);
                break;
            }
        }
예제 #10
0
        /**
         * called by OtpNode to deliver message to this mailbox.
         *
         * About exit and exit2: both cause exception to be raised upon receive().
         * However exit (not 2) causes any link to be removed as well, while exit2
         * leaves any links intact.
         */
        public virtual void Deliver(OtpMsg m)
        {
            switch (m.Type)
            {
            case OtpMsg.linkTag:
                links.AddLink(Self, m.FromPid);
                break;

            case OtpMsg.unlinkTag:
                links.RemoveLink(Self, m.FromPid);
                break;

            case OtpMsg.exitTag:
                links.RemoveLink(Self, m.FromPid);
                if (Received != null)
                {
                    Received?.Invoke(new MessageEventArgs(this, m));
                }
                else
                {
                    Queue.Enqueue(m);
                }
                break;

            case OtpMsg.exit2Tag:
            default:
                if (Received != null)
                {
                    Received?.Invoke(new MessageEventArgs(this, m));
                }
                else
                {
                    Queue.Enqueue(m);
                }
                break;
            }
        }
예제 #11
0
        /*
         * OtpCookedConnection delivers messages here return true if message was
         * delivered successfully, or false otherwise.
         */
        public bool deliver(OtpMsg m)
        {
            OtpMbox mbox = null;

            try
            {
                int t = m.type();

                if (t == OtpMsg.regSendTag)
                {
                    String name = m.getRecipientName();
                    /* special case for netKernel requests */
                    if (name.Equals("net_kernel"))
                    {
                        return netKernel(m);
                    }
                    else
                    {
                        mbox = mboxes.get(name);
                    }
                }
                else
                {
                    mbox = mboxes.get(m.getRecipientPid());
                }

                if (mbox == null)
                {
                    return false;
                }
                mbox.deliver(m);
            }
            catch (Exception)
            {
                return false;
            }

            return true;
        }
예제 #12
0
 /**
  * Deliver messages to the recipient.
  */
 public abstract void Deliver(OtpMsg msg);
예제 #13
0
 internal MessageEventArgs(OtpMbox mbox, OtpMsg msg)
 {
     Mbox = mbox;
     Msg  = msg;
 }
예제 #14
0
 public override void Deliver(OtpMsg msg) => queue.Enqueue(msg);
예제 #15
0
 public override void deliver(OtpMsg msg)
 {
     queue.put(msg);
 }
예제 #16
0
        private void schedule()
        {
            Monitor.Enter(runnable);
            try
            {
                while (runnable.Count == 0)
                {
                    Monitor.Wait(runnable);
                }

                OtpActorSchedTask task  = runnable.Dequeue();
                OtpActor          actor = task.Actor;
                IEnumerator <OtpActor.Continuation> enumerator = task.Enumerator;

                Monitor.Enter(task);
                try
                {
                    if (task.Active)
                    {
                        OtpMsg msg = actor.Mbox.receiveMsg();

                        if (msg == null)
                        {
                            return;
                        }

                        ThreadPool.QueueUserWorkItem
                            (delegate(Object state)
                        {
                            Monitor.Enter(task);
                            try
                            {
                                OtpActor.Continuation cont = enumerator.Current;

                                cont(msg);

                                if (!enumerator.MoveNext())
                                {
                                    task.Active = false;
                                }
                            }
                            catch (Exception e)
                            {
                                log.Info("Exception was thrown from running actor: " + e.Message);
                            }
                            finally
                            {
                                Monitor.Exit(task);
                            }
                        });
                    }
                }
                finally
                {
                    Monitor.Exit(task);
                }
            }
            finally
            {
                Monitor.Exit(runnable);
            }
        }
        /*
         * pass the message to the node for final delivery. Note that the connection
         * itself needs to know about links (in case of connection failure), so we
         * snoop for link/unlink too here.
         */
        public override void deliver(OtpMsg msg)
        {
            bool delivered = self.deliver(msg);

            switch (msg.type())
            {
                case OtpMsg.linkTag:
                    if (delivered)
                    {
                        links.addLink(msg.getRecipientPid(), msg.getSenderPid());
                    }
                    else
                    {
                        try
                        {
                            // no such pid - send exit to sender
                            base.sendExit(msg.getRecipientPid(), msg.getSenderPid(), new OtpErlangAtom("noproc"));
                        }
                        catch (IOException)
                        {
                        }
                    }
                    break;

                case OtpMsg.unlinkTag:
                case OtpMsg.exitTag:
                    links.removeLink(msg.getRecipientPid(), msg.getSenderPid());
                    break;

                case OtpMsg.exit2Tag:
                    break;
            }

            return;
        }
예제 #18
0
        /*
         * called by OtpNode to deliver message to this mailbox.
         *
         * About exit and exit2: both cause exception to be raised upon receive().
         * However exit (not 2) causes any link to be removed as well, while exit2
         * leaves any links intact.
         */
        public virtual void deliver(OtpMsg m)
        {
            switch (m.type())
            {
                case OtpMsg.linkTag:
                    links.addLink(self, m.getSenderPid());
                    break;

                case OtpMsg.unlinkTag:
                    links.removeLink(self, m.getSenderPid());
                    break;

                case OtpMsg.exitTag:
                    links.removeLink(self, m.getSenderPid());
                    queue.put(m);
                    break;

                case OtpMsg.exit2Tag:
                default:
                    queue.put(m);
                    break;
            }
        }
예제 #19
0
 public override void deliver(OtpMsg msg)
 {
     queue.put(msg);
 }
예제 #20
0
        /**
         * Wait for a message to arrive for this mailbox.
         */
        public OtpInputStream ReceiveBuf(long timeout)
        {
            OtpMsg m = ReceiveMsg(timeout);

            return(m?.Stream);
        }
예제 #21
0
        /**
         * Wait for a message to arrive for this mailbox.
         */
        public IOtpErlangObject Receive(long timeout)
        {
            OtpMsg m = ReceiveMsg(timeout);

            return(m?.Payload);
        }
예제 #22
0
        /*
         * this method simulates net_kernel only for the purpose of replying to
         * pings.
         */
        private bool netKernel(OtpMsg m)
        {
            OtpMbox mbox = null;
            try
            {
                OtpErlangTuple t = (OtpErlangTuple)m.getMsg();
                OtpErlangTuple req = (OtpErlangTuple)t.elementAt(1); // actual
                // request

                OtpErlangPid pid = (OtpErlangPid)req.elementAt(0); // originating
                // pid

                OtpErlangObject[] pong = new OtpErlangObject[2];
                pong[0] = req.elementAt(1); // his #Ref
                pong[1] = new OtpErlangAtom("yes");

                mbox = createMbox(true);
                mbox.send(pid, new OtpErlangTuple(pong));
                return true;
            }
            catch (Exception)
            {
            }
            finally
            {
                closeMbox(mbox);
            }
            return false;
        }
예제 #23
0
 public override void deliver(OtpMsg m)
 {
     base.deliver(m);
     sched.notify(this);
 }
예제 #24
0
 public override void deliver(OtpMsg m)
 {
     base.deliver(m);
     sched.notify(this);
 }
 /**
  * Deliver messages to the recipient.
  */
 public abstract void deliver(OtpMsg msg);