Reading from socket file handle took too long

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • Etienne Desautels

    #1

    Reading from socket file handle took too long


    Hi,

    I'm working on project where I need to grab video from an Axis IP
    camera. This camera send a stream of a multipart message on HTTP. I
    write this code (at the bottom of the message) to read and uncompress
    each jpeg images. I call nextFrame() 24 times per seconds (or every
    0,0416 sec.) to read the next image that arrived.

    Everything works well but one thing. My problem is that running
    nextFrame() took, most of the time, more then 0,0414 sec. so my video
    is lagging. I monitor every call and I found that the culprit is when I
    read from the socket file handle. It's the only bottleneck in my code.
    I try different approaches to the problem but I always hit the same
    problem.

    I don't think it's normal that read() take more then 0,04 sec to read
    1000 bytes from memory (the socket file handle). How can I avoid this
    problem ?

    I'm on Linux 2.6 (last Ubuntu) with python 2.4 on P4 2.3.

    Thanks

    Etienne


    CODE
    ------------------------------------------------------------------------
    ----------------------------

    class Axis:
    url = ""
    user = "user"
    password = "password"
    header = {}
    header["Authorizat ion"] = "Basic " + b64encode(user + ":" + password)
    http = urllib2.HTTPHan dler()
    state = 0
    limit = 1000
    imageData = None
    sizeX = 352
    sizeY = 240
    fps = 24
    compression = 25

    def startGrab(self) :
    try:
    url = self.url + "/axis-cgi/mjpg/video.cgi?resol ution=" +
    str(self.sizeX) \
    + "x" + str(self.sizeY) + "&compressi on=" \
    + str(self.compre ssion) + "&req_fps=" + str(self.fps)
    req = urllib2.Request (url, None, self.header)
    self.fh = self.http.http_ open(req)
    self.buffer = ""
    self.state = 1
    except:
    self.state = 0

    def stopGrab(self):
    self.fh.close()
    self.state = 0

    def nextFrame(self) :
    if self.state:
    try:
    temp = self.fh.read(se lf.limit) # <-- TAKE A LOT OF TIME
    self.buffer += temp
    boundary = self.buffer.fin d("\r\nConten t-Type: image/jpeg\r\n") + 30
    if boundary >= 30:
    end = self.buffer.fin d("\r\n\r\n--myboundary", boundary) + 2
    if end >= 2:
    image = Image.open(Stri ngIO(self.buffe r[boundary:end]))
    self.imageData = image.tostring( "raw",image.mod e,0,-1)
    self.buffer = self.buffer[end:]

    except:
    pass

  • Ben Sizer

    #2
    Re: Reading from socket file handle took too long

    Etienne Desautels wrote:[color=blue]
    > Everything works well but one thing. My problem is that running
    > nextFrame() took, most of the time, more then 0,0414 sec. so my video
    > is lagging. I monitor every call and I found that the culprit is when I
    > read from the socket file handle. It's the only bottleneck in my code.[/color]

    If you're sure this is the problem, you might try calling setSockOpt on
    the socket to set the nodelay flag, something like this:

    mySocket.setsoc kopt(IPPROTO_TC P, TCP_NODELAY, 1)

    I don't know enough about the option to be sure it'll work, but it
    can't hurt to try.

    --
    Ben Sizer

    Comment

    Working...