From 7914523a16c8545adbd7271d07ab28ad6ac209f1 Mon Sep 17 00:00:00 2001 From: Kovid Goyal Date: Thu, 9 Nov 2023 21:31:37 +0530 Subject: [PATCH] Add a CSI + ascii test --- tools/cmd/benchmark/main.go | 72 +++++++++++++++++++++++++++---------- 1 file changed, 53 insertions(+), 19 deletions(-) diff --git a/tools/cmd/benchmark/main.go b/tools/cmd/benchmark/main.go index 69ff352cd..251c9eeba 100644 --- a/tools/cmd/benchmark/main.go +++ b/tools/cmd/benchmark/main.go @@ -74,25 +74,16 @@ func benchmark_data(data string, opts benchmark_options) (duration time.Duration return duration, nil } +var rand_src = sync.OnceValue(func() *rand.Rand { + return rand.New(rand.NewSource(time.Now().UnixNano())) +}) + func random_string_of_bytes(n int, alphabet string) string { - var src = rand.NewSource(time.Now().UnixNano()) - const ( - letterIdxBits = 7 // 7 bits to represent a letter index - letterIdxMask = 1<= 0; { - if remain == 0 { - cache, remain = src.Int63(), letterIdxMax - } - if idx := int(cache & letterIdxMask); idx < len(alphabet) { - b[i] = alphabet[idx] - i-- - } - cache >>= letterIdxBits - remain-- + al := len(alphabet) + src := rand_src() + for i := 0; i < n; i++ { + b[i] = alphabet[src.Intn(al)] } return utils.UnsafeBytesToString(b) } @@ -103,8 +94,10 @@ type result struct { duration time.Duration } +const ascii_printable = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ \n\t\r `~!@#$%^&*()_+-=[]{}\\|;:'\",<.>/?" + func simple_ascii() (r result, err error) { - data := random_string_of_bytes(1024*1024+13, "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ \n\t\r `~!@#$%^&*()_+-=[]{}\\|;:'\",<.>/?") + data := random_string_of_bytes(1024*1024+13, ascii_printable) duration, err := benchmark_data(data, default_benchmark_options()) if err != nil { return result{}, err @@ -112,6 +105,38 @@ func simple_ascii() (r result, err error) { return result{"Simple ascii characters", len(data), duration}, nil } +func ascii_with_csi() (r result, err error) { + const sz = 1024 * 1024 * 17 + out := make([]byte, 0, sz+48) + src := rand_src() + chunk := "" + for len(out) < sz { + q := src.Intn(100) + switch { + case (q < 10): + chunk = random_string_of_bytes(src.Intn(72)+1, ascii_printable) + case (10 <= q && q < 30): + chunk = "\x1b[m;\x1b[?1h\x1b[H" + case (30 <= q && q < 40): + chunk = "\x1b[1;2;3;4:3;31m" + case (40 <= q && q < 50): + chunk = "\x1b[38:5:24;48:2:125:136:147m" + case (50 <= q && q < 60): + chunk = "\x1b[58;5;44;2m" + case (60 <= q && q < 80): + chunk = "\x1b[m;\x1b[10A\x1b[3E\x1b[2K" + case (80 <= q && q < 100): + chunk = "\x1b[39m;\x1b[10`a\x1b[100b\x1b[?1l" + } + out = append(out, utils.UnsafeStringToBytes(chunk)...) + } + duration, err := benchmark_data(utils.UnsafeBytesToString(out), default_benchmark_options()) + if err != nil { + return result{}, err + } + return result{"CSI codes with ASCII text", len(out), duration}, nil +} + var divs = []time.Duration{ time.Duration(1), time.Duration(10), time.Duration(100), time.Duration(1000)} @@ -141,7 +166,16 @@ func main() (err error) { } results = append(results, r) - fmt.Println(reset + "Results:") + if r, err = ascii_with_csi(); err != nil { + return err + } + results = append(results, r) + + fmt.Print(reset) + fmt.Println( + "These results measure the time it takes the terminal to fully parse all the data sent to it. Some terminals will not render all the data, skipping frames, thereby \"cheating\" in their results. kitty does render all data.") + fmt.Println() + fmt.Println("Results:") for _, r := range results { present_result(r) }