gguf_test.go 5.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220
  1. package llm
  2. import (
  3. "crypto/sha256"
  4. "fmt"
  5. "io"
  6. "math"
  7. "os"
  8. "path/filepath"
  9. "strings"
  10. "testing"
  11. "github.com/google/go-cmp/cmp"
  12. )
  13. func TestGGUFRewrite(t *testing.T) {
  14. tests := []string{
  15. "phi3.gguf",
  16. }
  17. for i := range tests {
  18. tt := tests[i]
  19. t.Run(tt, func(t *testing.T) {
  20. t.Parallel()
  21. p := filepath.Join("testdata", tt)
  22. if _, err := os.Stat(p); err != nil {
  23. t.Fatalf("%s not found", p)
  24. }
  25. f, err := os.Open(p)
  26. if err != nil {
  27. t.Fatal(err)
  28. }
  29. defer f.Close()
  30. ggml, _, err := decodeGGML(t, f)
  31. if err != nil {
  32. t.Fatal(err)
  33. }
  34. temp, err := os.CreateTemp("testdata", "2"+tt)
  35. if err != nil {
  36. t.Fatal(err)
  37. }
  38. defer temp.Close()
  39. n, ggml2, err := rewriteGGML(t, ggml, temp, f)
  40. /* if n != m {
  41. t.Fatalf("n: %d, m: %d", n, m)
  42. } */
  43. if err != nil {
  44. t.Fatal(err)
  45. }
  46. //t.Fatal("FULL SIZE JFAKFJJEFJAJFLAEJJAFAJKLFJ", n)
  47. if diff, diff2, ok := compareGGML(n, ggml2, ggml, temp, f); !ok {
  48. if cmp.Diff(diff, diff2) != "" {
  49. t.Fatalf("\n%s,\n%s\n%s\n%s\ndiff: %s", diff["token_embd.weight"], diff2["token_embd.weight"], diff["token_embd.weight size"], diff["token_embd.weight offset"], cmp.Diff(diff, diff2))
  50. }
  51. }
  52. })
  53. }
  54. }
  55. func formatDiff(diff map[string]string) string {
  56. var builder strings.Builder
  57. for k, v := range diff {
  58. builder.WriteString(fmt.Sprintf("%s: %s\n", k, v))
  59. }
  60. return builder.String()
  61. }
  62. func compareGGML(n int64, ggml1, ggml2 *GGML, f *os.File, f2 *os.File) (map[string]string, map[string]string, bool) {
  63. diff := make(map[string]string)
  64. diff2 := make(map[string]string)
  65. kv1 := ggml1.KV()
  66. kv2 := ggml2.KV()
  67. if len(kv1) != len(kv2) {
  68. diff["lenKV"] = fmt.Sprintf("kv1: %d, kv2: %d", len(kv1), len(kv2))
  69. fmt.Println("lenKV", diff["lenKV"])
  70. }
  71. for k, v := range kv1 {
  72. // if v2, ok := kv2[k]; !ok {
  73. // diff[k] = fmt.Sprintf("missing key %s", k)
  74. // } else if v != v2 {
  75. // diff[fmt.Sprintf("%s type diff", k)] = fmt.Sprintf("kv1 type: %T, kv2 type: %T", v.(*array).values, v2.(*array).values)
  76. // diff[k] = fmt.Sprintf("kv1: %d, kv2: %d", len(v.(*array).values), len(v2.(*array).values))
  77. // diff[fmt.Sprintf("%s values first 10", k)] = fmt.Sprintf("\nkv1: %#v, \nkv2: %#v", v.(*array).values[0:10], v2.(*array).values[0:10])
  78. // diff[fmt.Sprintf("%s values last 10", k)] = fmt.Sprintf("\nkv1: %#v, \nkv2: %#v", v.(*array).values[len(v.(*array).values)-10:], v2.(*array).values[len(v2.(*array).values)-10:])
  79. // diff[fmt.Sprintf("%s diff", k)] = cmp.Diff(v.(*array).values, v2.(*array).values)
  80. switch t := v.(type) {
  81. case *array:
  82. if diffy := cmp.Diff(t.values, kv2[k].(*array).values); diffy != "" {
  83. diff[k] = diffy
  84. }
  85. default:
  86. if v != kv2[k] {
  87. diff[k] = fmt.Sprintf("kv1: %v, kv2: %v", v, kv2[k])
  88. }
  89. }
  90. // }
  91. }
  92. t1 := ggml1.Tensors()
  93. t2 := ggml2.Tensors()
  94. if len(t1) != len(t2) {
  95. diff["lenTensors"] = fmt.Sprintf("t1: %d, t2: %d", len(t1), len(t2))
  96. }
  97. for _, tensor := range t1 {
  98. sha256sum := sha256.New()
  99. sr := io.NewSectionReader(f, n+int64(tensor.Offset), int64(tensor.Size()))
  100. var s int64
  101. s, err := io.Copy(sha256sum, sr)
  102. if err != nil {
  103. fmt.Println(err)
  104. }
  105. diff[tensor.Name] = fmt.Sprintf("%x", sha256sum.Sum(nil))
  106. diff[tensor.Name+" size"] = fmt.Sprintf("%d", s)
  107. diff[tensor.Name+" offset"] = fmt.Sprintf("%v", tensor.Offset)
  108. }
  109. /* sha256Sum2 := sha256.New()
  110. sr1 := io.NewSectionReader(f2, 0, n)
  111. s1, err := io.Copy(sha256Sum2, sr1)
  112. if err != nil {
  113. return nil, nil, true
  114. }
  115. sha256Sum3 := sha256.New()
  116. sr2 := io.NewSectionReader(f, 0, n)
  117. s2, err := io.Copy(sha256Sum3, sr2)
  118. if err != nil {
  119. return nil, nil, true
  120. }
  121. diff["sha"] = fmt.Sprintf("%d", s1)
  122. diff2["sha"] = fmt.Sprintf("%d", s2) */
  123. for _, tensor := range t2 {
  124. sha256sum := sha256.New()
  125. var s int64
  126. sr := io.NewSectionReader(f2, n+int64(tensor.Offset), int64(tensor.Size()))
  127. s, err := io.Copy(sha256sum, sr)
  128. if err != nil {
  129. fmt.Println(err)
  130. }
  131. diff2[tensor.Name] = fmt.Sprintf("%x", sha256sum.Sum(nil))
  132. diff2[tensor.Name+" size"] = fmt.Sprintf("%d", s)
  133. diff2[tensor.Name+" offset"] = fmt.Sprintf("%v", tensor.Offset)
  134. }
  135. return diff, diff2, len(diff) == 0
  136. }
  137. func decodeGGML(t *testing.T, f *os.File) (*GGML, int64, error) {
  138. ggml, n, err := DecodeGGML(f, math.MaxInt)
  139. if err != nil {
  140. t.Fatal(err)
  141. }
  142. return ggml, n, nil
  143. }
  144. func rewriteGGML(t *testing.T, ggml *GGML, temp *os.File, f *os.File) (int64, *GGML, error) {
  145. var tensors Tensors
  146. fmt.Println("11111111111111111111111111111111111111111")
  147. for _, tensor := range ggml.Tensors() {
  148. shape := make([]uint64, len(tensor.Shape))
  149. for i := range len(tensor.Shape) {
  150. shape[i] = tensor.Shape[len(tensor.Shape)-i-1]
  151. }
  152. fmt.Println("tensors", tensor.Name, shape, tensor.Kind, 737414+int64(tensor.Offset))
  153. tensors = append(tensors, &Tensor{
  154. Name: tensor.Name,
  155. Kind: tensor.Kind,
  156. Shape: shape,
  157. WriterTo: TensorWriter{
  158. Reader: io.NewSectionReader(f, 737414+int64(tensor.Offset), int64(tensor.Size())),
  159. },
  160. })
  161. }
  162. reader := &GGUFWriter{
  163. KV: ggml.KV(),
  164. // Update .Tensors
  165. Tensors: tensors,
  166. }
  167. n, err := io.Copy(temp, reader)
  168. if err != nil {
  169. t.Fatal(err)
  170. }
  171. fmt.Println(n, " is my offset")
  172. file, err := os.Open(temp.Name())
  173. if err != nil {
  174. t.Fatal(err)
  175. }
  176. ggml2, _, err := DecodeGGML(file, math.MaxInt)
  177. if err != nil {
  178. t.Fatal(err)
  179. }
  180. return n, ggml2, nil
  181. }