| // Copyright 2017 Marc-Antoine Ruel. All rights reserved. |
| // Use of this source code is governed under the Apache License, Version 2.0 |
| // that can be found in the LICENSE file. |
| |
| // panic crashes in various ways. |
| // |
| // It is a tool to help test pp, it is used in its unit tests. |
| // |
| // To install, run: |
| // |
| // go install github.com/maruel/panicparse/v2/cmd/panic |
| // panic -help |
| // panic str |& pp |
| // |
| // Some panics require the race detector with -race: |
| // |
| // go install -race github.com/maruel/panicparse/v2/cmd/panic |
| // panic race |& pp |
| // |
| // To use with optimization (-N) and inlining (-l) disabled, build with |
| // -gcflags '-N -l' like: |
| // |
| // go install -gcflags '-N -l' github.com/maruel/panicparse/v2/cmd/panic |
| package main |
| |
| // To add a new panic stack signature, add it to types type below, keeping the |
| // list ordered by name. If you need utility functions, add it in the section |
| // below. That's it! |
| |
| import ( |
| "fmt" |
| "io" |
| "os" |
| "os/exec" |
| "runtime" |
| "sort" |
| "strings" |
| "sync" |
| "syscall" |
| "time" |
| |
| "github.com/maruel/panicparse/v2/cmd/panic/internal" |
| correct "github.com/maruel/panicparse/v2/cmd/panic/internal/incorrect" |
| ùtf8 "github.com/maruel/panicparse/v2/cmd/panic/internal/utf8" |
| ) |
| |
| func main() { |
| if len(os.Args) == 2 { |
| switch n := os.Args[1]; n { |
| case "-h", "-help", "--help", "help": |
| usage() |
| os.Exit(0) |
| |
| case "dump_commands": |
| // Undocumented command to do a raw dump of the supported commands. This |
| // is used by unit tests in ../../stack. |
| items := make([]string, 0, len(types)) |
| for n := range types { |
| items = append(items, n) |
| } |
| sort.Strings(items) |
| for _, n := range items { |
| fmt.Printf("%s\n", n) |
| } |
| os.Exit(0) |
| |
| default: |
| if f, ok := types[n]; ok { |
| fmt.Printf("GOTRACEBACK=%s\n", os.Getenv("GOTRACEBACK")) |
| if n == "simple" { |
| // Since the map lookup creates another call stack entry, add a |
| // one-off "simple" panic style to test the very minimal case. |
| // types["simple"].f is never called. |
| panic("simple") |
| } |
| f.f() |
| os.Exit(3) |
| } |
| fmt.Fprintf(stdErr, "unknown panic style %q\n", n) |
| os.Exit(1) |
| } |
| } |
| usage() |
| os.Exit(1) |
| } |
| |
| // Mocked in test. |
| var stdErr io.Writer = os.Stderr |
| |
| // Utility functions. |
| |
| func panicint(i int) { |
| panic(i) |
| } |
| |
| func panicfloat64(f float64) { |
| panic(f) |
| } |
| |
| func panicstr(a string) { |
| panic(a) |
| } |
| |
| func panicslicestr(a []string) { |
| panic(a) |
| } |
| |
| func panicArgsElided(a, b, c, d, e, f, g, h, i, j, k int) { |
| panic(a) |
| } |
| |
| func recurse(i int) { |
| if i > 0 { |
| recurse(i - 1) |
| return |
| } |
| panic(42) |
| } |
| |
| func panicRaceDisabled(name string) { |
| help := "'panic %s' can only be used when built with the race detector.\n" + |
| "To build, use:\n" + |
| " go install -race github.com/maruel/panicparse/v2/cmd/panic\n" |
| fmt.Fprintf(stdErr, help, name) |
| } |
| |
| func rerunWithFastCrash() { |
| if os.Getenv("GORACE") != "log_path=stderr halt_on_error=1" { |
| _ = os.Setenv("GORACE", "log_path=stderr halt_on_error=1") |
| /* #nosec G204 */ |
| c := exec.Command(os.Args[0], os.Args[1:]...) |
| c.Stderr = os.Stderr |
| if err, ok := c.Run().(*exec.ExitError); ok { |
| if status, ok := err.Sys().(syscall.WaitStatus); ok { |
| os.Exit(status.ExitStatus()) |
| } |
| os.Exit(1) |
| } |
| os.Exit(0) |
| } |
| } |
| |
| // panicDoRaceWrite and panicDoRaceRead are extracted from panicRace() to make |
| // the stack trace less trivial, but in general folks will do the error with |
| // this code inlined. |
| func panicDoRaceWrite(x *int) { |
| for i := 0; ; i++ { |
| *x = i |
| } |
| } |
| func panicDoRaceRead(x *int) { |
| for i := 0; ; { |
| i += *x |
| } |
| } |
| |
| func panicRace() { |
| if !raceEnabled { |
| panicRaceDisabled("race") |
| return |
| } |
| rerunWithFastCrash() |
| |
| i := 0 |
| // Do two separate calls so that the 'created at' stacks are different. |
| go func() { |
| panicDoRaceWrite(&i) |
| }() |
| go func() { |
| panicDoRaceRead(&i) |
| }() |
| time.Sleep(time.Minute) |
| } |
| |
| //go:noinline |
| func panicChanStruct(x chan struct{}) { |
| panic("test") |
| } |
| |
| /* TODO(maruel): This is not detected! |
| func panicRaceUnaligned() { |
| if !raceEnabled { |
| panicRaceDisabled("race_unaligned") |
| return |
| } |
| rerunWithFastCrash() |
| |
| a := [8]byte{} |
| b := (*int64)(unsafe.Pointer(&a[0])) |
| go func() { |
| for i := 0; ; i++ { |
| a[4] = byte(i) |
| } |
| }() |
| go func() { |
| for { |
| *b++ |
| } |
| }() |
| time.Sleep(time.Minute) |
| } |
| */ |
| |
| // |
| |
| // types is all the supported types of panics. |
| // |
| // Keep the list sorted. |
| // |
| // TODO(maruel): Figure out a way to reliably trigger "(scan)" output: |
| // - disable automatic GC with runtime.SetGCPercent(-1) |
| // - a goroutine with a large number of items in the stack |
| // - large heap to make the scanning process slow enough |
| // - trigger a manual GC with go runtime.GC() |
| // - panic in the meantime |
| // This would still not be deterministic. |
| // |
| // TODO(maruel): Figure out a way to reliably trigger sleep output. |
| var types = map[string]struct { |
| desc string |
| f func() |
| }{ |
| "args_elided": { |
| "too many args in stack line, causing the call arguments to be elided", |
| func() { |
| panicArgsElided(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11) |
| }, |
| }, |
| |
| "chan_receive": { |
| "goroutine blocked on <-c", |
| func() { |
| c := make(chan bool) |
| go func() { |
| <-c |
| <-c |
| }() |
| c <- true |
| panic(42) |
| }, |
| }, |
| |
| "chan_send": { |
| "goroutine blocked on c<-", |
| func() { |
| c := make(chan bool) |
| go func() { |
| c <- true |
| c <- true |
| }() |
| <-c |
| panic(42) |
| }, |
| }, |
| |
| "chan_struct": { |
| "panic with an empty chan struct{} as a parameter", |
| func() { |
| panicChanStruct(nil) |
| }, |
| }, |
| |
| "float": { |
| "panic(4.2)", |
| func() { |
| panicfloat64(4.2) |
| }, |
| }, |
| |
| "goroutine_1": { |
| "panic in one goroutine", |
| func() { |
| go func() { |
| panicint(42) |
| }() |
| time.Sleep(time.Minute) |
| }, |
| }, |
| |
| "goroutine_100": { |
| "start 100 goroutines before panicking", |
| func() { |
| var wg sync.WaitGroup |
| for i := 0; i < 100; i++ { |
| wg.Add(1) |
| go func() { |
| wg.Done() |
| time.Sleep(time.Minute) |
| }() |
| } |
| wg.Wait() |
| panicint(42) |
| }, |
| }, |
| |
| "goroutine_dedupe_pointers": { |
| "start 100 goroutines with different pointers before panicking", |
| func() { |
| var wg sync.WaitGroup |
| for i := 0; i < 100; i++ { |
| wg.Add(1) |
| go func(b *int) { |
| wg.Done() |
| time.Sleep(time.Minute) |
| }(new(int)) |
| } |
| wg.Wait() |
| panicint(42) |
| }, |
| }, |
| |
| "int": { |
| "panic(42)", |
| func() { |
| panicint(42) |
| }, |
| }, |
| |
| "locked": { |
| "thread locked goroutine via runtime.LockOSThread()", |
| func() { |
| runtime.LockOSThread() |
| panic(42) |
| }, |
| }, |
| |
| "other": { |
| "panics with other package in the call stack, with both exported and unexpected functions", |
| func() { |
| internal.Callback(func() { |
| panic("allo") |
| }) |
| }, |
| }, |
| |
| "asleep": { |
| "panics with 'all goroutines are asleep - deadlock'", |
| func() { |
| // When built with the race detector, this hangs. I suspect this is due |
| // because the race detector starts a separate goroutine which causes |
| // checkdead() to not trigger. See checkdead() in src/runtime/proc.go. |
| // https://github.com/golang/go/issues/20588 |
| // |
| // Repro: |
| // go install -race github.com/maruel/panicparse/v2/cmd/panic; panic asleep |
| var mu sync.Mutex |
| mu.Lock() |
| mu.Lock() |
| }, |
| }, |
| |
| "race": { |
| "cause a crash by race detector", |
| panicRace, |
| }, |
| |
| /* TODO(maruel): This is not detected! |
| "race_unaligned": { |
| "cause a crash by race detector with unaligned access", |
| panicRaceUnaligned, |
| }, |
| */ |
| |
| "stack_cut_off": { |
| "recursive calls with too many call lines in traceback, causing higher up calls to missing", |
| func() { |
| // Observed limit is 99. |
| // src/runtime/runtime2.go:const _TracebackMaxFrames = 100 |
| recurse(100) |
| }, |
| }, |
| |
| "stack_cut_off_named": { |
| "named calls with too many call lines in traceback, causing higher up calls to missing", |
| func() { |
| // The tool has difficulty with very deep static calls during linking. |
| // See https://github.com/golang/go/issues/51814 |
| recurse497() |
| }, |
| }, |
| |
| "simple": { |
| // This is not used for real, here for documentation. |
| "skip the map for a shorter stack trace", |
| func() {}, |
| }, |
| |
| "slice_str": { |
| "panic([]string{\"allo\"}) with cap=2", |
| func() { |
| a := make([]string, 1, 2) |
| a[0] = "allo" |
| panicslicestr(a) |
| }, |
| }, |
| |
| "stdlib": { |
| "panics with stdlib in the call stack, with both exported and unexpected functions", |
| func() { |
| strings.FieldsFunc("a", func(rune) bool { |
| panic("allo") |
| }) |
| }, |
| }, |
| |
| "stdlib_and_other": { |
| "panics with both other and stdlib packages in the call stack", |
| func() { |
| strings.FieldsFunc("a", func(rune) bool { |
| internal.Callback(func() { |
| panic("allo") |
| }) |
| return false |
| }) |
| }, |
| }, |
| |
| "str": { |
| "panic(\"allo\")", |
| func() { |
| panicstr("allo") |
| }, |
| }, |
| |
| "mismatched": { |
| "mismatched package and directory names", |
| func() { |
| correct.Panic() |
| }, |
| }, |
| |
| "utf8": { |
| "non-ascii package, struct and method names", |
| func() { |
| s := ùtf8.Strùct{} |
| s.Pànic() |
| }, |
| }, |
| } |
| |
| func usage() { |
| t := `usage: panic <way> |
| |
| This tool is meant to be used with pp to test different parsing scenarios and |
| ensure output on different version of the Go toolchain can be successfully |
| parsed. |
| |
| Set GOTRACEBACK before running this tool to see how it affects the panic output. |
| |
| Built with: ` + runtime.Version() + ` |
| |
| Select the way to panic: |
| ` |
| _, _ = io.WriteString(stdErr, t) |
| names := make([]string, 0, len(types)) |
| m := 0 |
| for n := range types { |
| names = append(names, n) |
| if i := len(n); i > m { |
| m = i |
| } |
| } |
| sort.Strings(names) |
| for _, n := range names { |
| fmt.Fprintf(stdErr, "- %-*s %s\n", m, n, types[n].desc) |
| } |
| } |
| |
| // |
| |
| func recurse00() { panic("the end") } |
| func recurse01() { recurse00() } |
| func recurse02() { recurse01() } |
| func recurse03() { recurse02() } |
| func recurse04() { recurse03() } |
| func recurse05() { recurse04() } |
| func recurse06() { recurse05() } |
| func recurse07() { recurse06() } |
| func recurse08() { recurse07() } |
| func recurse09() { recurse08() } |
| func recurse10() { recurse09() } |
| func recurse11() { recurse10() } |
| func recurse12() { recurse11() } |
| func recurse13() { recurse12() } |
| func recurse14() { recurse13() } |
| func recurse15() { recurse14() } |
| func recurse16() { recurse15() } |
| func recurse17() { recurse16() } |
| func recurse18() { recurse17() } |
| func recurse19() { recurse18() } |
| func recurse20() { recurse19() } |
| func recurse21() { recurse20() } |
| func recurse22() { recurse21() } |
| func recurse23() { recurse22() } |
| func recurse24() { recurse23() } |
| func recurse25() { recurse24() } |
| func recurse26() { recurse25() } |
| func recurse27() { recurse26() } |
| func recurse28() { recurse27() } |
| func recurse29() { recurse28() } |
| func recurse30() { recurse29() } |
| func recurse31() { recurse30() } |
| func recurse32() { recurse31() } |
| func recurse33() { recurse32() } |
| func recurse34() { recurse33() } |
| func recurse35() { recurse34() } |
| func recurse36() { recurse35() } |
| func recurse37() { recurse36() } |
| func recurse38() { recurse37() } |
| func recurse39() { recurse38() } |
| func recurse40() { recurse39() } |
| func recurse41() { recurse40() } |
| func recurse42() { recurse41() } |
| func recurse43() { recurse42() } |
| func recurse44() { recurse43() } |
| func recurse45() { recurse44() } |
| func recurse46() { recurse45() } |
| func recurse47() { recurse46() } |
| func recurse48() { recurse47() } |
| func recurse49() { recurse48() } |
| func recurse50() { recurse49() } |
| func recurse51() { recurse50() } |
| func recurse52() { recurse51() } |
| func recurse53() { recurse52() } |
| func recurse54() { recurse53() } |
| func recurse55() { recurse54() } |
| func recurse56() { recurse55() } |
| func recurse57() { recurse56() } |
| func recurse58() { recurse57() } |
| func recurse59() { recurse58() } |
| func recurse60() { recurse59() } |
| func recurse61() { recurse60() } |
| func recurse62() { recurse61() } |
| func recurse63() { recurse62() } |
| func recurse64() { recurse63() } |
| func recurse65() { recurse64() } |
| func recurse66() { recurse65() } |
| func recurse67() { recurse66() } |
| func recurse68() { recurse67() } |
| func recurse69() { recurse68() } |
| func recurse70() { recurse69() } |
| func recurse71() { recurse70() } |
| func recurse72() { recurse71() } |
| func recurse73() { recurse72() } |
| func recurse74() { recurse73() } |
| func recurse75() { recurse74() } |
| func recurse76() { recurse75() } |
| func recurse77() { recurse76() } |
| func recurse78() { recurse77() } |
| func recurse79() { recurse78() } |
| func recurse80() { recurse79() } |
| func recurse81() { recurse80() } |
| func recurse82() { recurse81() } |
| func recurse83() { recurse82() } |
| func recurse84() { recurse83() } |
| func recurse85() { recurse84() } |
| func recurse86() { recurse85() } |
| func recurse87() { recurse86() } |
| func recurse88() { recurse87() } |
| func recurse89() { recurse88() } |
| func recurse90() { recurse89() } |
| func recurse91() { recurse90() } |
| func recurse92() { recurse91() } |
| func recurse93() { recurse92() } |
| func recurse94() { recurse93() } |
| func recurse95() { recurse94() } |
| func recurse96() { recurse95() } |
| func recurse97() { recurse96() } |
| func recurse98() { recurse97() } |
| func recurse99() { recurse98() } |
| func recurse100() { recurse99() } |
| |
| func recurse101() { recurse100() } |
| func recurse102() { recurse101() } |
| func recurse103() { recurse102() } |
| func recurse104() { recurse103() } |
| func recurse105() { recurse104() } |
| func recurse106() { recurse105() } |
| func recurse107() { recurse106() } |
| func recurse108() { recurse107() } |
| func recurse109() { recurse108() } |
| func recurse110() { recurse109() } |
| func recurse111() { recurse110() } |
| func recurse112() { recurse111() } |
| func recurse113() { recurse112() } |
| func recurse114() { recurse113() } |
| func recurse115() { recurse114() } |
| func recurse116() { recurse115() } |
| func recurse117() { recurse116() } |
| func recurse118() { recurse117() } |
| func recurse119() { recurse118() } |
| func recurse120() { recurse119() } |
| func recurse121() { recurse120() } |
| func recurse122() { recurse121() } |
| func recurse123() { recurse122() } |
| func recurse124() { recurse123() } |
| func recurse125() { recurse124() } |
| func recurse126() { recurse125() } |
| func recurse127() { recurse126() } |
| func recurse128() { recurse127() } |
| func recurse129() { recurse128() } |
| func recurse130() { recurse129() } |
| func recurse131() { recurse130() } |
| func recurse132() { recurse131() } |
| func recurse133() { recurse132() } |
| func recurse134() { recurse133() } |
| func recurse135() { recurse134() } |
| func recurse136() { recurse135() } |
| func recurse137() { recurse136() } |
| func recurse138() { recurse137() } |
| func recurse139() { recurse138() } |
| func recurse140() { recurse139() } |
| func recurse141() { recurse140() } |
| func recurse142() { recurse141() } |
| func recurse143() { recurse142() } |
| func recurse144() { recurse143() } |
| func recurse145() { recurse144() } |
| func recurse146() { recurse145() } |
| func recurse147() { recurse146() } |
| func recurse148() { recurse147() } |
| func recurse149() { recurse148() } |
| func recurse150() { recurse149() } |
| func recurse151() { recurse150() } |
| func recurse152() { recurse151() } |
| func recurse153() { recurse152() } |
| func recurse154() { recurse153() } |
| func recurse155() { recurse154() } |
| func recurse156() { recurse155() } |
| func recurse157() { recurse156() } |
| func recurse158() { recurse157() } |
| func recurse159() { recurse158() } |
| func recurse160() { recurse159() } |
| func recurse161() { recurse160() } |
| func recurse162() { recurse161() } |
| func recurse163() { recurse162() } |
| func recurse164() { recurse163() } |
| func recurse165() { recurse164() } |
| func recurse166() { recurse165() } |
| func recurse167() { recurse166() } |
| func recurse168() { recurse167() } |
| func recurse169() { recurse168() } |
| func recurse170() { recurse169() } |
| func recurse171() { recurse170() } |
| func recurse172() { recurse171() } |
| func recurse173() { recurse172() } |
| func recurse174() { recurse173() } |
| func recurse175() { recurse174() } |
| func recurse176() { recurse175() } |
| func recurse177() { recurse176() } |
| func recurse178() { recurse177() } |
| func recurse179() { recurse178() } |
| func recurse180() { recurse179() } |
| func recurse181() { recurse180() } |
| func recurse182() { recurse181() } |
| func recurse183() { recurse182() } |
| func recurse184() { recurse183() } |
| func recurse185() { recurse184() } |
| func recurse186() { recurse185() } |
| func recurse187() { recurse186() } |
| func recurse188() { recurse187() } |
| func recurse189() { recurse188() } |
| func recurse190() { recurse189() } |
| func recurse191() { recurse190() } |
| func recurse192() { recurse191() } |
| func recurse193() { recurse192() } |
| func recurse194() { recurse193() } |
| func recurse195() { recurse194() } |
| func recurse196() { recurse195() } |
| func recurse197() { recurse196() } |
| func recurse198() { recurse197() } |
| func recurse199() { recurse198() } |
| |
| func recurse200() { recurse199() } |
| func recurse201() { recurse200() } |
| func recurse202() { recurse201() } |
| func recurse203() { recurse202() } |
| func recurse204() { recurse203() } |
| func recurse205() { recurse204() } |
| func recurse206() { recurse205() } |
| func recurse207() { recurse206() } |
| func recurse208() { recurse207() } |
| func recurse209() { recurse208() } |
| func recurse210() { recurse209() } |
| func recurse211() { recurse210() } |
| func recurse212() { recurse211() } |
| func recurse213() { recurse212() } |
| func recurse214() { recurse213() } |
| func recurse215() { recurse214() } |
| func recurse216() { recurse215() } |
| func recurse217() { recurse216() } |
| func recurse218() { recurse217() } |
| func recurse219() { recurse218() } |
| func recurse220() { recurse219() } |
| func recurse221() { recurse220() } |
| func recurse222() { recurse221() } |
| func recurse223() { recurse222() } |
| func recurse224() { recurse223() } |
| func recurse225() { recurse224() } |
| func recurse226() { recurse225() } |
| func recurse227() { recurse226() } |
| func recurse228() { recurse227() } |
| func recurse229() { recurse228() } |
| func recurse230() { recurse229() } |
| func recurse231() { recurse230() } |
| func recurse232() { recurse231() } |
| func recurse233() { recurse232() } |
| func recurse234() { recurse233() } |
| func recurse235() { recurse234() } |
| func recurse236() { recurse235() } |
| func recurse237() { recurse236() } |
| func recurse238() { recurse237() } |
| func recurse239() { recurse238() } |
| func recurse240() { recurse239() } |
| func recurse241() { recurse240() } |
| func recurse242() { recurse241() } |
| func recurse243() { recurse242() } |
| func recurse244() { recurse243() } |
| func recurse245() { recurse244() } |
| func recurse246() { recurse245() } |
| func recurse247() { recurse246() } |
| func recurse248() { recurse247() } |
| func recurse249() { recurse248() } |
| func recurse250() { recurse249() } |
| func recurse251() { recurse250() } |
| func recurse252() { recurse251() } |
| func recurse253() { recurse252() } |
| func recurse254() { recurse253() } |
| func recurse255() { recurse254() } |
| func recurse256() { recurse255() } |
| func recurse257() { recurse256() } |
| func recurse258() { recurse257() } |
| func recurse259() { recurse258() } |
| func recurse260() { recurse259() } |
| func recurse261() { recurse260() } |
| func recurse262() { recurse261() } |
| func recurse263() { recurse262() } |
| func recurse264() { recurse263() } |
| func recurse265() { recurse264() } |
| func recurse266() { recurse265() } |
| func recurse267() { recurse266() } |
| func recurse268() { recurse267() } |
| func recurse269() { recurse268() } |
| func recurse270() { recurse269() } |
| func recurse271() { recurse270() } |
| func recurse272() { recurse271() } |
| func recurse273() { recurse272() } |
| func recurse274() { recurse273() } |
| func recurse275() { recurse274() } |
| func recurse276() { recurse275() } |
| func recurse277() { recurse276() } |
| func recurse278() { recurse277() } |
| func recurse279() { recurse278() } |
| func recurse280() { recurse279() } |
| func recurse281() { recurse280() } |
| func recurse282() { recurse281() } |
| func recurse283() { recurse282() } |
| func recurse284() { recurse283() } |
| func recurse285() { recurse284() } |
| func recurse286() { recurse285() } |
| func recurse287() { recurse286() } |
| func recurse288() { recurse287() } |
| func recurse289() { recurse288() } |
| func recurse290() { recurse289() } |
| func recurse291() { recurse290() } |
| func recurse292() { recurse291() } |
| func recurse293() { recurse292() } |
| func recurse294() { recurse293() } |
| func recurse295() { recurse294() } |
| func recurse296() { recurse295() } |
| func recurse297() { recurse296() } |
| func recurse298() { recurse297() } |
| func recurse299() { recurse298() } |
| |
| func recurse300() { recurse299() } |
| func recurse301() { recurse300() } |
| func recurse302() { recurse301() } |
| func recurse303() { recurse302() } |
| func recurse304() { recurse303() } |
| func recurse305() { recurse304() } |
| func recurse306() { recurse305() } |
| func recurse307() { recurse306() } |
| func recurse308() { recurse307() } |
| func recurse309() { recurse308() } |
| func recurse310() { recurse309() } |
| func recurse311() { recurse310() } |
| func recurse312() { recurse311() } |
| func recurse313() { recurse312() } |
| func recurse314() { recurse313() } |
| func recurse315() { recurse314() } |
| func recurse316() { recurse315() } |
| func recurse317() { recurse316() } |
| func recurse318() { recurse317() } |
| func recurse319() { recurse318() } |
| func recurse320() { recurse319() } |
| func recurse321() { recurse320() } |
| func recurse322() { recurse321() } |
| func recurse323() { recurse322() } |
| func recurse324() { recurse323() } |
| func recurse325() { recurse324() } |
| func recurse326() { recurse325() } |
| func recurse327() { recurse326() } |
| func recurse328() { recurse327() } |
| func recurse329() { recurse328() } |
| func recurse330() { recurse329() } |
| func recurse331() { recurse330() } |
| func recurse332() { recurse331() } |
| func recurse333() { recurse332() } |
| func recurse334() { recurse333() } |
| func recurse335() { recurse334() } |
| func recurse336() { recurse335() } |
| func recurse337() { recurse336() } |
| func recurse338() { recurse337() } |
| func recurse339() { recurse338() } |
| func recurse340() { recurse339() } |
| func recurse341() { recurse340() } |
| func recurse342() { recurse341() } |
| func recurse343() { recurse342() } |
| func recurse344() { recurse343() } |
| func recurse345() { recurse344() } |
| func recurse346() { recurse345() } |
| func recurse347() { recurse346() } |
| func recurse348() { recurse347() } |
| func recurse349() { recurse348() } |
| func recurse350() { recurse349() } |
| func recurse351() { recurse350() } |
| func recurse352() { recurse351() } |
| func recurse353() { recurse352() } |
| func recurse354() { recurse353() } |
| func recurse355() { recurse354() } |
| func recurse356() { recurse355() } |
| func recurse357() { recurse356() } |
| func recurse358() { recurse357() } |
| func recurse359() { recurse358() } |
| func recurse360() { recurse359() } |
| func recurse361() { recurse360() } |
| func recurse362() { recurse361() } |
| func recurse363() { recurse362() } |
| func recurse364() { recurse363() } |
| func recurse365() { recurse364() } |
| func recurse366() { recurse365() } |
| func recurse367() { recurse366() } |
| func recurse368() { recurse367() } |
| func recurse369() { recurse368() } |
| func recurse370() { recurse369() } |
| func recurse371() { recurse370() } |
| func recurse372() { recurse371() } |
| func recurse373() { recurse372() } |
| func recurse374() { recurse373() } |
| func recurse375() { recurse374() } |
| func recurse376() { recurse375() } |
| func recurse377() { recurse376() } |
| func recurse378() { recurse377() } |
| func recurse379() { recurse378() } |
| func recurse380() { recurse379() } |
| func recurse381() { recurse380() } |
| func recurse382() { recurse381() } |
| func recurse383() { recurse382() } |
| func recurse384() { recurse383() } |
| func recurse385() { recurse384() } |
| func recurse386() { recurse385() } |
| func recurse387() { recurse386() } |
| func recurse388() { recurse387() } |
| func recurse389() { recurse388() } |
| func recurse390() { recurse389() } |
| func recurse391() { recurse390() } |
| func recurse392() { recurse391() } |
| func recurse393() { recurse392() } |
| func recurse394() { recurse393() } |
| func recurse395() { recurse394() } |
| func recurse396() { recurse395() } |
| func recurse397() { recurse396() } |
| func recurse398() { recurse397() } |
| func recurse399() { recurse398() } |
| |
| func recurse400() { recurse399() } |
| func recurse401() { recurse400() } |
| func recurse402() { recurse401() } |
| func recurse403() { recurse402() } |
| func recurse404() { recurse403() } |
| func recurse405() { recurse404() } |
| func recurse406() { recurse405() } |
| func recurse407() { recurse406() } |
| func recurse408() { recurse407() } |
| func recurse409() { recurse408() } |
| func recurse410() { recurse409() } |
| func recurse411() { recurse410() } |
| func recurse412() { recurse411() } |
| func recurse413() { recurse412() } |
| func recurse414() { recurse413() } |
| func recurse415() { recurse414() } |
| func recurse416() { recurse415() } |
| func recurse417() { recurse416() } |
| func recurse418() { recurse417() } |
| func recurse419() { recurse418() } |
| func recurse420() { recurse419() } |
| func recurse421() { recurse420() } |
| func recurse422() { recurse421() } |
| func recurse423() { recurse422() } |
| func recurse424() { recurse423() } |
| func recurse425() { recurse424() } |
| func recurse426() { recurse425() } |
| func recurse427() { recurse426() } |
| func recurse428() { recurse427() } |
| func recurse429() { recurse428() } |
| func recurse430() { recurse429() } |
| func recurse431() { recurse430() } |
| func recurse432() { recurse431() } |
| func recurse433() { recurse432() } |
| func recurse434() { recurse433() } |
| func recurse435() { recurse434() } |
| func recurse436() { recurse435() } |
| func recurse437() { recurse436() } |
| func recurse438() { recurse437() } |
| func recurse439() { recurse438() } |
| func recurse440() { recurse439() } |
| func recurse441() { recurse440() } |
| func recurse442() { recurse441() } |
| func recurse443() { recurse442() } |
| func recurse444() { recurse443() } |
| func recurse445() { recurse444() } |
| func recurse446() { recurse445() } |
| func recurse447() { recurse446() } |
| func recurse448() { recurse447() } |
| func recurse449() { recurse448() } |
| func recurse450() { recurse449() } |
| func recurse451() { recurse450() } |
| func recurse452() { recurse451() } |
| func recurse453() { recurse452() } |
| func recurse454() { recurse453() } |
| func recurse455() { recurse454() } |
| func recurse456() { recurse455() } |
| func recurse457() { recurse456() } |
| func recurse458() { recurse457() } |
| func recurse459() { recurse458() } |
| func recurse460() { recurse459() } |
| func recurse461() { recurse460() } |
| func recurse462() { recurse461() } |
| func recurse463() { recurse462() } |
| func recurse464() { recurse463() } |
| func recurse465() { recurse464() } |
| func recurse466() { recurse465() } |
| func recurse467() { recurse466() } |
| func recurse468() { recurse467() } |
| func recurse469() { recurse468() } |
| func recurse470() { recurse469() } |
| func recurse471() { recurse470() } |
| func recurse472() { recurse471() } |
| func recurse473() { recurse472() } |
| func recurse474() { recurse473() } |
| func recurse475() { recurse474() } |
| func recurse476() { recurse475() } |
| func recurse477() { recurse476() } |
| func recurse478() { recurse477() } |
| func recurse479() { recurse478() } |
| func recurse480() { recurse479() } |
| func recurse481() { recurse480() } |
| func recurse482() { recurse481() } |
| func recurse483() { recurse482() } |
| func recurse484() { recurse483() } |
| func recurse485() { recurse484() } |
| func recurse486() { recurse485() } |
| func recurse487() { recurse486() } |
| func recurse488() { recurse487() } |
| func recurse489() { recurse488() } |
| func recurse490() { recurse489() } |
| func recurse491() { recurse490() } |
| func recurse492() { recurse491() } |
| func recurse493() { recurse492() } |
| func recurse494() { recurse493() } |
| func recurse495() { recurse494() } |
| func recurse496() { recurse495() } |
| func recurse497() { recurse496() } |