예제 #1
0
파일: CUDT.cs 프로젝트: Wiladams/NewTOAPIA
      // Functionality:
      //    Request UDT to receive data into a file described as "fd", starting from "offset", with expected size of "size".
      // Parameters:
      //    0) [out] ofs: The output file stream.
      //    1) [in] offset: From where to write data;
      //    2) [in] size: How many data to be received.
      //    3) [in] block: size of block per write to disk
      // Returned value:
      //    Actual size of data received.

public Int64 recvfile(Stream ofs, Int64 offset, Int64 size, int block)
{
   if (UDT_DGRAM == m_iSockType)
      throw new CUDTException(5, 10, 0);

   if (!m_bConnected)
      throw new CUDTException(2, 2, 0);
   else if ((m_bBroken || m_bClosing) && (0 == m_pRcvBuffer.getRcvDataSize()))
      throw new CUDTException(2, 1, 0);

   if (size <= 0)
      return 0;

   CGuard recvguard = new CGuard(m_RecvLock);

   long torecv = size;
   int unitsize = block;
   int recvsize;

   // positioning...
   try
   {
      ofs.seekp((streamoff)offset);
   }
   catch (Exception e)
   {
      throw new CUDTException(4, 3);
   }

   // receiving... "recvfile" is always blocking
   while (torecv > 0)
   {
      if (ofs.bad() || ofs.fail())
         break;

         while (!m_bBroken && m_bConnected && !m_bClosing && (0 == m_pRcvBuffer.getRcvDataSize()))
             m_RecvDataCond.WaitOne(-1);

      if (!m_bConnected)
         throw new CUDTException(2, 2, 0);
      else if ((m_bBroken || m_bClosing) && (0 == m_pRcvBuffer.getRcvDataSize()))
         throw new CUDTException(2, 1, 0);

      unitsize = (int)((torecv >= block) ? block : torecv);
      recvsize = m_pRcvBuffer.readBufferToFile(ofs, unitsize);

      torecv -= recvsize;
   }

   return size - torecv;
}
예제 #2
0
        // Functionality:
        //    Read a block of data from file and insert it into the sending list.
        // Parameters:
        //    0) [in] ifs: input file stream.
        //    1) [in] len: size of the block.
        // Returned value:
        //    actual size of data added from the file.

        public int addBufferFromFile(Stream ifs, int len)
        {
            int size = len / m_iMSS;
            if ((len % m_iMSS) != 0)
                size++;

            // dynamically increase sender buffer
            while (size + m_iCount >= m_iSize)
                increase();

            Block s = m_pLastBlock;
            int total = 0;
            for (int i = 0; i < size; ++i)
            {
                if (ifs.bad() || ifs.fail() || ifs.eof())
                    break;

                int pktlen = len - i * m_iMSS;
                if (pktlen > m_iMSS)
                    pktlen = m_iMSS;

                ifs.Read(s.m_pcData, 0, pktlen);
                if ((pktlen = ifs.gcount()) <= 0)
                    break;

                s.m_iLength = pktlen;
                s.m_iTTL = -1;
                s = s.m_pNext;

                total += pktlen;
            }
            m_pLastBlock = s;

            lock (m_BufLock)
            {
                m_iCount += size;
            }

            return total;
        }
예제 #3
0
파일: CUDT.cs 프로젝트: Wiladams/NewTOAPIA
      // Functionality:
      //    Request UDT to send out a file described as "fd", starting from "offset", with size of "size".
      // Parameters:
      //    0) [in] ifs: The input file stream.
      //    1) [in] offset: From where to read and send data;
      //    2) [in] size: How many data to be sent.
      //    3) [in] block: size of block per read from disk
      // Returned value:
      //    Actual size of data sent.

        public Int64 sendfile(Stream ifs, Int64 offset, Int64 size, int block)
{
   if (UDT_DGRAM == m_iSockType)
      throw new CUDTException(5, 10, 0);

   if (m_bBroken || m_bClosing)
      throw new CUDTException(2, 1, 0);
   else if (!m_bConnected)
      throw new CUDTException(2, 2, 0);

   if (size <= 0)
      return 0;

   CGuard sendguard = new CGuard(m_SendLock);

   long tosend = size;
   int unitsize;

   // positioning...
   try
   {
      ifs.seekg((streamoff)offset);
   }
   catch (Exception e)
   {
      throw new CUDTException(4, 1);
   }

   // sending block by block
   while (tosend > 0)
   {
      if (ifs.bad() || ifs.fail() || ifs.eof())
         break;

      unitsize = (int)((tosend >= block) ? block : tosend);

         while (!m_bBroken && m_bConnected && !m_bClosing && (m_iSndBufSize <= m_pSndBuffer.getCurrBufSize()))
            WaitForSingleObject(m_SendBlockCond, INFINITE);

      if (m_bBroken || m_bClosing)
         throw new CUDTException(2, 1, 0);
      else if (!m_bConnected)
         throw new CUDTException(2, 2, 0);

      // record total time used for sending
      if (0 == m_pSndBuffer.getCurrBufSize())
         m_llSndDurationCounter = CClock.getTime();

      tosend -= m_pSndBuffer.addBufferFromFile(ifs, unitsize);

      // insert this socket to snd list if it is not on the list yet
      m_pSndQueue.m_pSndUList.update(this, false);
   }

   return size - tosend;
}