Possible TLS connection handling memory leak?

xuanbao · · 559 次点击    
这是一个分享于 的资源,其中的信息可能已经有所发展或是发生改变。
<p>Hi,</p> <p>after a few minutes of running this simple application: <a href="http://pastebin.com/raw/09jauR7j" rel="nofollow">http://pastebin.com/raw/09jauR7j</a> I am experiencing a constant heap grow up: <a href="http://pastebin.com/raw/w46rjjiz" rel="nofollow">http://pastebin.com/raw/w46rjjiz</a></p> <p>Is there a mistake in the source code or is it just bad TLS implementation and I am facing some kind of object pooling?</p> <p>Hint: go version go1.6 darwin/amd64</p> <hr/>**评论:**<br/><br/>SoftwareEngineur: <pre><p>I&#39;m going to go ahead and suggest that no one else reply to the snarky OP who obviously knows the answer and is just testing us.</p></pre>anacrolix: <pre><p>Yoda expressions aren&#39;t necessary in Go. Don&#39;t use error as a variable name. Response.Body is guaranteed to be valid if there&#39;s no error, so don&#39;t check if it&#39;s nil.</p></pre>m173314: <pre><p>Thanks for the reply, but please focus on the problem instead of code reviewing.</p></pre>tv64738: <pre><p>A lot of the time, the problem is caused by one of the little code smells, like the fact that on error you just log a line and continue.</p></pre>m173314: <pre><p>sorry, but nope. No errors appeared at all. btw it is just a simple sample code. </p></pre>tv64738: <pre><p>Not in this case; I&#39;m defending the general attitude of &#34;only good code should be extensively debugged&#34;.</p></pre>izuriel: <pre><blockquote> <p>btw it is just a simple sample code. </p> </blockquote> <p>So you can see the problem happening in this &#34;simple sample code?&#34; <em>Are you sure you didn&#39;t omit something you did that might be causing the leak</em>? What tools are you using to determine there is a leak?</p></pre>YesSoupForYou: <pre><p>Can you check the headers returned by Twitter? It might be asking to keep the TLS session alive and you might be recreating a new session every time.</p></pre>m173314: <pre><p>According to your suggestion, it means that this is a really common problem. Why would the client, with default TLS configuration provided, recreate new session every time if it sent requests one after another (not in parallel)?</p></pre>YesSoupForYou: <pre><p>It is common but you&#39;re not explicitly doing TLS, you&#39;re creating a new session every time with http.Get(), which doesn&#39;t preserve state between connections, what you need is a http server. <a href="https://golang.org/pkg/net/http/" rel="nofollow">https://golang.org/pkg/net/http/</a> says: </p> <p>For control over proxies, TLS configuration, keep-alives, compression, and other settings, create a Transport:</p> <pre><code>tr := &amp;http.Transport{ TLSClientConfig: &amp;tls.Config{RootCAs: pool}, DisableCompression: true, } client := &amp;http.Client{Transport: tr} resp, err := client.Get(&#34;https://example.com&#34;) </code></pre> <p>Try something similar to that in your code and see if it keeps happening</p></pre>m173314: <pre><p>I&#39;ve tried your advise but the problem still occurs. I found a similar post at google groups:</p> <p><a href="https://groups.google.com/forum/#!searchin/golang-nuts/https$20leak/golang-nuts/AhtZS3OgGM4/8cJIzcAPMhgJ" rel="nofollow">https://groups.google.com/forum/#!searchin/golang-nuts/https$20leak/golang-nuts/AhtZS3OgGM4/8cJIzcAPMhgJ</a> <a href="https://gist.github.com/rnapier/dfbae391898e11c2598c" rel="nofollow">https://gist.github.com/rnapier/dfbae391898e11c2598c</a></p> <p>Maybe it is in fact a leak...</p></pre>YesSoupForYou: <pre><p>From what I see in the mailing list you sent me near the end of the thread it seems like they came to a resolution and a explanation. It doesn&#39;t seem to actually be a leak from the looks of it but more of a &#34;you need to optimize your code&#34; situation. Go is making it very easy to build a scalable webserver but to make it scale in every sense (resource consumption etc) you need to fine tune it a bit</p></pre>chlunde: <pre><p>Try</p> <pre><code>io.Copy(ioutil.Discard, response.Body) </code></pre> <p>before calling Close. In most real programs this is not required, because you actually consume the body to do something with it, maybe except for handling special HTTP status codes.</p> <p>By consuming the whole body the TLS connection may be reused on the next request.</p> <p>Here&#39;s the references to the implementation in 1.6: an early .Close() will send false to the readLoop(): <a href="https://go.googlesource.com/go/+/go1.6/src/net/http/transport.go#1154" rel="nofollow">https://go.googlesource.com/go/+/go1.6/src/net/http/transport.go#1154</a> the readLoop will not call <code>tryPutIdleConn</code> then: <a href="https://go.googlesource.com/go/+/go1.6/src/net/http/transport.go#1179" rel="nofollow">https://go.googlesource.com/go/+/go1.6/src/net/http/transport.go#1179</a></p> <p>Does this explain what you are seeing?</p></pre>m173314: <pre><p>And that&#39;s a perfect explanation. Thank you for your efforts!</p></pre>

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

559 次点击  
加入收藏 微博
暂无回复
添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传