1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
let toplevel name ~root = Filename.(concat root name)
module V1_and_v2 = struct
let pack = toplevel "store.pack"
let branch = toplevel "store.branches"
let dict = toplevel "store.dict"
let all ~root = [ pack ~root; branch ~root; dict ~root ]
end
module V3 = struct
let branch = toplevel "store.branches"
let dict = toplevel "store.dict"
let control = toplevel "store.control"
let suffix ~generation =
toplevel ("store." ^ string_of_int generation ^ ".suffix")
let gc_result ~generation =
toplevel ("store." ^ string_of_int generation ^ ".out")
let reachable ~generation =
toplevel ("store." ^ string_of_int generation ^ ".reachable")
let sorted ~generation =
toplevel ("store." ^ string_of_int generation ^ ".sorted")
let mapping ~generation =
toplevel ("store." ^ string_of_int generation ^ ".mapping")
let prefix ~generation =
toplevel ("store." ^ string_of_int generation ^ ".prefix")
let all ~generation ~root =
[ suffix ~generation ~root; branch ~root; dict ~root; control ~root ]
end
module V4 = struct
let branch = toplevel "store.branches"
let dict = toplevel "store.dict"
let control = toplevel "store.control"
let suffix_chunk ~chunk_idx =
toplevel ("store." ^ string_of_int chunk_idx ^ ".suffix")
let gc_result ~generation =
toplevel ("store." ^ string_of_int generation ^ ".out")
let reachable ~generation =
toplevel ("store." ^ string_of_int generation ^ ".reachable")
let sorted ~generation =
toplevel ("store." ^ string_of_int generation ^ ".sorted")
let mapping ~generation =
toplevel ("store." ^ string_of_int generation ^ ".mapping")
let prefix ~generation =
toplevel ("store." ^ string_of_int generation ^ ".prefix")
end
(** [is_number] is a less generic than [Stdlib.int_of_string_opt]. It matches
this equivalent regex: {v "([1-9][0-9]*|0)" v}. *)
let is_number s =
match String.to_seq s |> List.of_seq with
| [] -> false
| '0' :: _ :: _ -> false
| l ->
List.fold_left
(fun acc char ->
let is_digit = match char with '0' .. '9' -> true | _ -> false in
acc && is_digit)
true l
type classification =
[ `Branch
| `Control
| `Dict
| `Gc_result of int
| `Mapping of int
| `Prefix of int
| `Reachable of int
| `Sorted of int
| `Suffix of int
| `V1_or_v2_pack ]
[@@deriving irmin]
let classify_filename s : classification option =
match String.split_on_char '.' s with
| [ "store"; "pack" ] -> Some `V1_or_v2_pack
| [ "store"; "branches" ] -> Some `Branch
| [ "store"; "control" ] -> Some `Control
| [ "store"; "dict" ] -> Some `Dict
| [ "store"; g; "out" ] when is_number g ->
Some (`Gc_result (int_of_string g))
| [ "store"; g; "reachable" ] when is_number g ->
Some (`Reachable (int_of_string g))
| [ "store"; g; "sorted" ] when is_number g ->
Some (`Sorted (int_of_string g))
| [ "store"; g; "mapping" ] when is_number g ->
Some (`Mapping (int_of_string g))
| [ "store"; g; "prefix" ] when is_number g ->
Some (`Prefix (int_of_string g))
| [ "store"; g; "suffix" ] when is_number g ->
Some (`Suffix (int_of_string g))
| _ -> None