代码之家  ›  专栏  ›  技术社区  ›  Schneck

Indy 10.6-连接到网络流时idHTTP 100%CPU使用率

  •  0
  • Schneck  · 技术社区  · 10 年前

    多年来,我一直在使用Indy 10.5和几个旧版本。为了支持HTTP摘要式身份验证,我从他们的SVN下载了最新版本。

    这是在修复我遇到的HTTP摘要身份验证问题。。。

    问题是10.6之后所有版本的CPU使用情况。

    我能够并行创建20个线程来检索HTTP流(准确地说是网络摄像机MJPEG流),根据分辨率和帧速率,每个任务使用大约1-3%的cpu。(包括解析和解码)

    我已经清理了通常使用IOHandler、CookieManager并依赖InternalWork方法的代码,直到我剩下idHttp的最基本用法,这可能是:

    procedure TForm1.Button1Click(Sender: TObject);
    var
        HTTPClient : TidHTTP;
    begin
      HTTPClient := TidHTTP.Create(nil);
      HTTPClient.Get('http://plazacam.studentaffairs.duke.edu/axis-cgi/mjpg/video.cgi?resolution=640x480');
      HTTPClient.Free();
    end;
    

    即使是上面的代码,在不改变任何设置的情况下,也会消耗25%的CPU(因此它会使我的计算机的1个内核饱和)。

    这是一个无限流,因此它不会返回到客户端是正常的;100kb/s,检索它的cpu使用率应该接近于零。。。

    我在另一个德语论坛上读到,添加此HTTPOptions可能会解决高CPU的问题,但在我的情况下,它对CPU没有影响: HTTPOptions:=[hoNoParseMetaHTTPEquiv]

    我已经尝试过Indy SVN的前几个版本,以确保它不是日常构建的特定内容。

    XE4、XE5和X6附带的10.6.0版本也有同样的问题,但如果我回滚到: Indy 10.5.5-RS2010 RTM

    然后一切都很好(除了HTTP摘要认证),它只使用了大约2%的cpu。。。

    有没有人遇到过同样的情况,并且有一种方法,当前版本的indy使用了合理数量的CPU来实现这一点?

    非常感谢。

    1 回复  |  直到 10 年前
        1
  •  2
  •   Remy Lebeau    10 年前

    想想你在做什么。您正在调用的版本 TIdHTTP.Get() 返回 String ,但您正在下载“无限”流。这意味着 Get() 正在不断地从套接字读取数据,并分配越来越多的内存来保存数据,以便最终将其转换为 一串 。因此,随着时间的推移,CPU使用率可能会很高,特别是当您在多个线程之间使用多个CPU时。

    作为测试,试着告诉 获取() 丢弃它下载的数据,而不是将其缓存在内存中,并查看CPU使用情况:

    HTTPClient.Get('http://plazacam.studentaffairs.duke.edu/axis-cgi/mjpg/video.cgi?resolution=640x480', TStream(nil));
    

    TIdHTTP 并不是真正为处理“无限”流而设计的,除非您提供 TStream 能够接收“无限”数据(如 TIdEventStream ),或启用 hoNoReadMultipartMIME 标记服务器是否使用MIME传递流数据,在这种情况下,您可以自己阅读流数据,如本文所述:

    New TIdHTTP hoNoReadMultipartMIME flag