Exemplo n.º 1
0
        public int select(ref UDTSOCKET[] readfds, ref UDTSOCKET[] writefds, ref UDTSOCKET[] exceptfds, timeval timeout)
        {
            Int64 entertime = CClock.getTime();

            Int64 to;
            if (null == timeout)
                to = 0xFFFFFFFFFFFFFFFF;
            else
                to = timeout.tv_sec * 1000000 + timeout.tv_usec;

            // initialize results
            int count = 0;
            HashSet<UDTSOCKET> rs = new HashSet<int>();
            HashSet<UDTSOCKET> ws = new HashSet<int>();
            HashSet<UDTSOCKET> es = new HashSet<int>();

            // retrieve related UDT sockets
            List<UdtSocket> ru = new List<UdtSocket>();
            List<UdtSocket> wu = new List<UdtSocket>();
            List<UdtSocket> eu = new List<UdtSocket>();
            UdtSocket s;

            if (null != readfds)
            {
                foreach (UDTSOCKET sockid in readfds)
                {
                    if (UDTSTATUS.BROKEN == getStatus(sockid))
                    {
                        rs.Add(sockid);
                        ++count;
                    }
                    else if (null == (s = locate(sockid)))
                        throw new CUDTException(5, 4, 0);
                    else
                        ru.Add(s);
                }
            }

            if (null != writefds)
            {
                foreach (UDTSOCKET i2 in writefds)
                {
                    if (UDTSTATUS.BROKEN == getStatus(i2))
                    {
                        ws.Add(i2);
                        ++count;
                    }
                    else if (null == (s = locate(i2)))
                        throw new CUDTException(5, 4, 0);
                    else
                        wu.Add(s);
                }
            }

            if (null != exceptfds)
            {
                //for (set<UDTSOCKET>::iterator i3 = exceptfds.begin(); i3 != exceptfds.end(); ++ i3)
                foreach (UDTSOCKET i3 in exceptfds)
                {
                    if (UDTSTATUS.BROKEN == getStatus(i3))
                    {
                        es.Add(i3);
                        ++count;
                    }
                    else if (null == (s = locate(i3)))
                        throw new CUDTException(5, 4, 0);
                    else
                        eu.Add(s);
                }
            }

            do
            {
                // query read sockets
                //for (vector<UdtSocket*>::iterator j1 = ru.begin(); j1 != ru.end(); ++ j1)
                foreach (UdtSocket j1 in ru)
                {
                    s = j1;

                    if ((s.m_pUDT.m_bConnected && (s.m_pUDT.m_pRcvBuffer.getRcvDataSize() > 0) && ((s.m_pUDT.m_iSockType == UDTSockType.UDT_STREAM) || (s.m_pUDT.m_pRcvBuffer.getRcvMsgNum() > 0)))
                       || (!s.m_pUDT.m_bListening && (s.m_pUDT.m_bBroken || !s.m_pUDT.m_bConnected))
                       || (s.m_pUDT.m_bListening && (s.m_pQueuedSockets.size() > 0))
                       || (s.m_Status == UDTSTATUS.CLOSED))
                    {
                        rs.insert(s.m_SocketID);
                        ++count;
                    }
                }

                // query write sockets
                //for (vector<UdtSocket*>::iterator j2 = wu.begin(); j2 != wu.end(); ++ j2)
                foreach (UdtSocket j2 in wu)
                {
                    s = j2;

                    if ((s.m_pUDT.m_bConnected && (s.m_pUDT.m_pSndBuffer.getCurrBufSize() < s.m_pUDT.m_iSndBufSize))
                       || s.m_pUDT.m_bBroken || !s.m_pUDT.m_bConnected || (s.m_Status == UDTSTATUS.CLOSED))
                    {
                        ws.insert(s.m_SocketID);
                        ++count;
                    }
                }

                // query exceptions on sockets
                //for (vector<UdtSocket*>::iterator j3 = eu.begin(); j3 != eu.end(); ++ j3)
                foreach (UdtSocket j3 in eu)
                {
                    // check connection request status, not supported now
                }

                if (0 < count)
                    break;

                CClock.waitForEvent();
            } while (to > CClock.getTime() - entertime);

            if (null != readfds)
                readfds = rs.ToArray();

            if (null != writefds)
                writefds = ws.ToArray();

            if (null != exceptfds)
                exceptfds = es.ToArray();

            return count;
        }