      subroutine sock.read(sockfd, maxlen, short.timeout, long.timeout, endstr, buf, err)
*
*
*
*
*
*
*
*
*
*
$include ccall.common
$catalog local

      equate PF$INET to 2
      equate SOCK$STREAM to 1
      equate F$SETFL to 4
      equate O$NONBLOCK to 2048
      equate EAGAIN to 11

* display 'sock.read [1]'
      call time.ms(tm)
      long.tm0 = tm
      short.tm0 = tm

      err = ''

      loop while 1 do

         avail.tm = short.timeout - ( tm - short.tm0 )
         t = long.timeout - ( tm - long.tm0 )
         if avail.tm > t then avail.tm = t
         if avail.tm < 0 then avail.tm = 0

         call csub.poll(sockfd,'rueh',events,avail.tm,res)
         if res < 0 then
            err = 'Error calling csub.poll - ' : cc$errno
            call csub.close(sockfd,'')
            return
         end
         if index(events,'e',1) then
            err = 'csub.poll returned error flag'
            call csub.close(sockfd,'')
            return
         end

         if index(events,'h',1) then
            err = 'csub.poll returned hangup flag'
            call csub.close(sockfd,'')
            return
         end

         if index(events,'i',1) then
            err = 'csub.poll returned invalid socket flag'
            call csub.close(sockfd,'')
            return
         end

         read.len = maxlen - len(buf)
*$*display 'read.len = ' : read.len : '  maxlen = ' : maxlen : '  len(buf) = ' : len(buf)
         rd.flg = 0
         call csub.read(sockfd,bb,read.len,res)
*$*display 'csub.read read.len =  ' : read.len : ' res = ' : res : ' cc$errno = ' : cc$errno
         begin case
            case res < 0 and cc$errno = EAGAIN
            case res = 0
               err = 'EOF'
               return
            case res > 0
               rd.flg = 1
               buf := bb[1,res]
            case res < 0
               err = 'Error calling csub.read - ' : cc$errno
               call csub.close(sockfd,'')
               return
         end case

         if len(buf) >= maxlen then return

         if endstr <> '' then
            if index(buf,endstr,1) then return
         end

         call time.ms(tm)
         if rd.flg then
            if ( tm - long.tm0 ) >= long.timeout then
               err = 'long timeout'
               return
            end
         end else
            if ( tm - short.tm0 ) >= short.timeout then
               err = 'short timeout'
               return
            end
         end
      repeat
   end
