shad-go/docs/allocation_profiling.md
2023-03-14 21:30:02 +03:00

89 lines
3.6 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Поиск лишних аллокаций
Для анализа аллокаций в задачах с бенчмарками удобно использовать встроенный в язык профайлер `pprof`.
Сперва нужно запустить бенчмарк с профайлером
```
✗ go test -v -run=^$ -bench=BenchmarkSprintf -memprofile=mem.out ./varfmt/...
goos: linux
goarch: amd64
pkg: gitlab.com/slon/shad-go/varfmt
cpu: Intel(R) Core(TM) i7-8650U CPU @ 1.90GHz
BenchmarkSprintf
BenchmarkSprintf/small
BenchmarkSprintf/small-8 19429222 62.93 ns/op 2 B/op 1 allocs/op
BenchmarkSprintf/small_string
BenchmarkSprintf/small_string-8 13282659 84.48 ns/op 16 B/op 1 allocs/op
BenchmarkSprintf/big
BenchmarkSprintf/big-8 20089 62372 ns/op 16388 B/op 1 allocs/op
PASS
ok gitlab.com/slon/shad-go/varfmt 4.363s
```
Сэмплы профайлера будут записаны в бинарный файл `mem.out`.
Этот файл можно открыть командой
```
✗ go tool pprof mem.out
File: varfmt.test
Type: alloc_space
Time: Mar 14, 2023 at 9:07pm (MSK)
Entering interactive mode (type "help" for commands, "o" for options)
(pprof)
```
В результате откроется интерактивная среда, в которой есть всякие команды, например `help`.
Чтобы узнать как запускать конкретную команду нужно вызвать `help` для неё
```
(pprof) help top
Outputs top entries in text form
Usage:
top [n] [focus_regex]* [-ignore_regex]* [-cum] >f
Include up to n samples
Include samples matching focus_regex, and exclude ignore_regex.
-cum sorts the output by cumulative weight
Optionally save the report on the file f
```
Команда `top` покажет места, где суммарно было больше всего аллокаций
```
(pprof) top -cum
Showing nodes accounting for 715.73MB, 99.37% of 720.23MB total
Dropped 24 nodes (cum <= 3.60MB)
flat flat% sum% cum cum%
715.73MB 99.37% 99.37% 716.73MB 99.51% fmt.Sprintf
0 0% 99.37% 716.73MB 99.51% gitlab.com/slon/shad-go/varfmt.BenchmarkSprintf.func1
0 0% 99.37% 716.73MB 99.51% testing.(*B).launch
0 0% 99.37% 716.73MB 99.51% testing.(*B).runN
(pprof)
```
Команда `svg` сдампит `top` в картинку.
```
(pprof) svg
Generating report in profile001.svg
```
Команда `list` покажет строчки, в которых происходят аллокации
```
(pprof) list fmt.Sprintf
Total: 720.23MB
ROUTINE ======================== fmt.Sprintf in /usr/local/go/src/fmt/print.go
715.73MB 716.73MB (flat, cum) 99.51% of Total
. . 213: return Fprintf(os.Stdout, format, a...)
. . 214:}
. . 215:
. . 216:// Sprintf formats according to a format specifier and returns the resulting string.
. . 217:func Sprintf(format string, a ...any) string {
. 512kB 218: p := newPrinter()
. . 219: p.doPrintf(format, a)
715.73MB 715.73MB 220: s := string(p.buf)
. 512.50kB 221: p.free()
. . 222: return s
. . 223:}
. . 224:
. . 225:// Appendf formats according to a format specifier, appends the result to the byte
. . 226:// slice, and returns the updated slice.
```