1// Copyright 2019 The Go Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style
3// license that can be found in the LICENSE file.
4
5//go:build ignore
6
7// Gen generates sais2.go by duplicating functions in sais.go
8// using different input types.
9// See the comment at the top of sais.go for details.
10package main
11
12import (
13	"bytes"
14	"log"
15	"os"
16	"strings"
17)
18
19func main() {
20	log.SetPrefix("gen: ")
21	log.SetFlags(0)
22
23	data, err := os.ReadFile("sais.go")
24	if err != nil {
25		log.Fatal(err)
26	}
27
28	x := bytes.Index(data, []byte("\n\n"))
29	if x < 0 {
30		log.Fatal("cannot find blank line after copyright comment")
31	}
32
33	var buf bytes.Buffer
34	buf.Write(data[:x])
35	buf.WriteString("\n\n// Code generated by go generate; DO NOT EDIT.\n\npackage suffixarray\n")
36
37	for {
38		x := bytes.Index(data, []byte("\nfunc "))
39		if x < 0 {
40			break
41		}
42		data = data[x:]
43		p := bytes.IndexByte(data, '(')
44		if p < 0 {
45			p = len(data)
46		}
47		name := string(data[len("\nfunc "):p])
48
49		x = bytes.Index(data, []byte("\n}\n"))
50		if x < 0 {
51			log.Fatalf("cannot find end of func %s", name)
52		}
53		fn := string(data[:x+len("\n}\n")])
54		data = data[x+len("\n}"):]
55
56		if strings.HasSuffix(name, "_32") {
57			buf.WriteString(fix32.Replace(fn))
58		}
59		if strings.HasSuffix(name, "_8_32") {
60			// x_8_32 -> x_8_64 done above
61			fn = fix8_32.Replace(stripByteOnly(fn))
62			buf.WriteString(fn)
63			buf.WriteString(fix32.Replace(fn))
64		}
65	}
66
67	if err := os.WriteFile("sais2.go", buf.Bytes(), 0666); err != nil {
68		log.Fatal(err)
69	}
70}
71
72var fix32 = strings.NewReplacer(
73	"32", "64",
74	"int32", "int64",
75)
76
77var fix8_32 = strings.NewReplacer(
78	"_8_32", "_32",
79	"byte", "int32",
80)
81
82func stripByteOnly(s string) string {
83	lines := strings.SplitAfter(s, "\n")
84	w := 0
85	for _, line := range lines {
86		if !strings.Contains(line, "256") && !strings.Contains(line, "byte-only") {
87			lines[w] = line
88			w++
89		}
90	}
91	return strings.Join(lines[:w], "")
92}
93