diff options
Diffstat (limited to 'internal/util/fns.go')
-rw-r--r-- | internal/util/fns.go | 68 |
1 files changed, 68 insertions, 0 deletions
diff --git a/internal/util/fns.go b/internal/util/fns.go new file mode 100644 index 000000000..53f5ebeed --- /dev/null +++ b/internal/util/fns.go @@ -0,0 +1,68 @@ +// GoToSocial +// Copyright (C) GoToSocial Authors admin@gotosocial.org +// SPDX-License-Identifier: AGPL-3.0-or-later +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU Affero General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Affero General Public License for more details. +// +// You should have received a copy of the GNU Affero General Public License +// along with this program. If not, see <http://www.gnu.org/licenses/>. + +package util + +import ( + "fmt" + "os" + "runtime" + + "codeberg.org/gruf/go-errors/v2" +) + +// Must executes 'fn' repeatedly until +// it successfully returns without panic. +func Must(fn func()) { + if fn == nil { + panic("nil func") + } + for !func() (done bool) { + defer func() { + if r := recover(); r != nil { + // Gather calling func frames. + pcs := make([]uintptr, 10) + n := runtime.Callers(3, pcs) + i := runtime.CallersFrames(pcs[:n]) + c := gatherFrames(i, n) + + const msg = "recovered panic: %v\n\n%s\n" + fmt.Fprintf(os.Stderr, msg, r, c.String()) + } + }() + fn() + done = true + return + }() { //nolint + } +} + +// gatherFrames collates runtime frames from a frame iterator. +func gatherFrames(iter *runtime.Frames, n int) errors.Callers { + if iter == nil { + return nil + } + frames := make([]runtime.Frame, 0, n) + for { + f, ok := iter.Next() + if !ok { + break + } + frames = append(frames, f) + } + return frames +} |