Source file uid_builder.ml

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
open! Core0

module type S = Uid_builder_intf.S

module Make () = struct
  module T = struct
    type t = Int.t [@@deriving bin_io, compare ~localize, sexp]

    (* We need a hash function compatible with native code and javascript. Currently the
       only type which allows this is [Int64]. So we perform a conversion to int64 here,
       and reach out directly to the (unboxed) hash_fold function in base to implement it.
       This allows zero alloc operation even in fast-build mode. *)

    external fold_int64
      :  Hash.state
      -> (int64[@unboxed])
      -> Hash.state
      = "Base_internalhash_fold_int64" "Base_internalhash_fold_int64_unboxed"
    [@@noalloc]

    let hash_fold_t state t = fold_int64 state (Int64.of_int_exn t)
    let hash t = Hash.get_hash_value (hash_fold_t (Hash.alloc ()) t)
  end

  include T
  include Comparator.Make (T)
  include Hashable.Make_binable (T)

  include%template Comparable.Make [@mode local] (T)

  let zero = Int.of_int 0
  let one = Int.of_int 1
  let to_int t = Int.to_int_exn t
  let to_string t = Int.to_string t

  let generator () =
    let id = ref one in
    let new_id () =
      let x = !id in
      (id := Int.(!id + one));
      x
    in
    let reset_id () = id := one in
    `New new_id, `Reset reset_id
  ;;

  module Expert = struct
    let of_int a = a
  end
end