chunkedGrab fetches the profiles described in source and merges them into a single profile. It fetches a chunk of profiles concurrently, with a maximum chunk size to limit its memory usage.
(sources []profileSource, fetch plugin.Fetcher, obj plugin.ObjTool, ui plugin.UI, tr http.RoundTripper)
| 171 | // a single profile. It fetches a chunk of profiles concurrently, with a maximum |
| 172 | // chunk size to limit its memory usage. |
| 173 | func chunkedGrab(sources []profileSource, fetch plugin.Fetcher, obj plugin.ObjTool, ui plugin.UI, tr http.RoundTripper) (*profile.Profile, plugin.MappingSources, bool, int, error) { |
| 174 | const chunkSize = 128 |
| 175 | |
| 176 | var p *profile.Profile |
| 177 | var msrc plugin.MappingSources |
| 178 | var save bool |
| 179 | var count int |
| 180 | |
| 181 | for start := 0; start < len(sources); start += chunkSize { |
| 182 | end := min(start+chunkSize, len(sources)) |
| 183 | chunkP, chunkMsrc, chunkSave, chunkCount, chunkErr := concurrentGrab(sources[start:end], fetch, obj, ui, tr) |
| 184 | switch { |
| 185 | case chunkErr != nil: |
| 186 | return nil, nil, false, 0, chunkErr |
| 187 | case chunkP == nil: |
| 188 | continue |
| 189 | case p == nil: |
| 190 | p, msrc, save, count = chunkP, chunkMsrc, chunkSave, chunkCount |
| 191 | default: |
| 192 | p, msrc, chunkErr = combineProfiles([]*profile.Profile{p, chunkP}, []plugin.MappingSources{msrc, chunkMsrc}) |
| 193 | if chunkErr != nil { |
| 194 | return nil, nil, false, 0, chunkErr |
| 195 | } |
| 196 | if chunkSave { |
| 197 | save = true |
| 198 | } |
| 199 | count += chunkCount |
| 200 | } |
| 201 | } |
| 202 | |
| 203 | return p, msrc, save, count, nil |
| 204 | } |
| 205 | |
| 206 | // concurrentGrab fetches multiple profiles concurrently |
| 207 | func concurrentGrab(sources []profileSource, fetch plugin.Fetcher, obj plugin.ObjTool, ui plugin.UI, tr http.RoundTripper) (*profile.Profile, plugin.MappingSources, bool, int, error) { |
no test coverage detected
searching dependent graphs…