Thank you! I change the code as your suggestion, it reduce 10% cpu usage. 在 2020年5月21日星期四 UTC+8下午1:04:34,Ian Lance Taylor写道: > > On Wed, May 20, 2020 at 9:26 PM <qing...@gmail.com <javascript:>> wrote: > > > > Hi all: > > I write a simpile HTTP proxy,and find the most alloctions appear in > io.copyBuffer > > > >>> (pprof) list io.copyBuffer > >>> > >>> Total: 2.80TB > >>> > >>> ROUTINE ======================== io.copyBuffer in > /usr/local/go/src/io/io.go > >>> > >>> 1.03TB 2.47TB (flat, cum) 88.16% of Total > >>> > >>> . . 383: if wt, ok := src.(WriterTo); ok { > >>> > >>> . . 384: return wt.WriteTo(dst) > >>> > >>> . . 385: } > >>> > >>> . . 386: // Similarly, if the writer has a > ReadFrom method, use it to do the copy. > >>> > >>> . . 387: if rt, ok := dst.(ReaderFrom); ok { > >>> > >>> . 3.02GB 388: return rt.ReadFrom(src) > >>> > >>> . . 389: } > >>> > >>> . . 390: if buf == nil { > >>> > >>> . . 391: size := 32 * 1024 > >>> > >>> . . 392: if l, ok := > src.(*LimitedReader); ok && int64(size) > l.N { > >>> > >>> . . 393: if l.N < 1 { > >>> > >>> . . 394: size = 1 > >>> > >>> . . 395: } else { > >>> > >>> . . 396: size = > int(l.N) > >>> > >>> . . 397: } > >>> > >>> . . 398: } > >>> > >>> 1.03TB 1.03TB 399: buf = make([]byte, size) > >>> > >>> . . 400: } > >>> > >>> . . 401: for { > >>> > >>> . 1.43TB 402: nr, er := src.Read(buf) > >>> > >>> . . 403: if nr > 0 { > >>> > >>> . 569.57MB 404: nw, ew := > dst.Write(buf[0:nr]) > >>> > >>> . . 405: if nw > 0 { > >>> > >>> . . 406: written += > int64(nw) > >>> > >>> . . 407: } > >>> > >>> . . 408: if ew != nil { > >>> > >>> . . 409: err = ew > > > > > > and this the stacktrace > >> > >> 0: 0 [2057907: 67433496576] @ 0x470169 0x6e508a 0x6e5042 0x6e4ca7 > 0x6cf82e 0x77bfe9 0x45f7a1 > >> > >> # 0x470168 io.copyBuffer+0x2a8 > /usr/local/go/src/io/io.go:399 > >> > >> # 0x6e5089 io.Copy+0x69 > /usr/local/go/src/io/io.go:364 > >> > >> # 0x6e5041 net/http.(*transferWriter).doBodyCopy+0x21 > /usr/local/go/src/net/http/transfer.go:400 > >> > >> # 0x6e4ca6 net/http.(*transferWriter).writeBody+0x426 > /usr/local/go/src/net/http/transfer.go:348 > >> > >> # 0x6cf82d net/http.(*Response).Write+0x42d > /usr/local/go/src/net/http/response.go:328 > >> > >> # 0x77bfe8 main.handler+0x318 > /root/ctrip/shendun/main.go:74 > > > The data being copied is presumably coming from the Body field of your > *http.Response. If you set the Body field to a type that implements > the WriteTo method, and set the ContentLength field to the length of > the data, then you can do the write however you like. > > Ian >
-- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/74064ed5-6650-4acc-9256-23e020182274%40googlegroups.com.