diff --git a/src/timestamp.ml b/src/timestamp.ml index ce06735b..b567ec8a 100644 --- a/src/timestamp.ml +++ b/src/timestamp.ml @@ -1,62 +1,43 @@ -let us_count_in_day = 86_400_000_000_L -let ps_count_in_us = 1_000_000_L -let ps_count_in_day = 86_400_000_000_000_000_L - -let span_of_int64_us us = - let is_neg = us < 0_L in - let us = Int64.abs us in - let d = Int64.to_int @@ Int64.div us us_count_in_day in - let ps = Int64.(mul (rem us us_count_in_day) ps_count_in_us) in - let span = Ptime.Span.v (d, ps) in - if is_neg then Ptime.Span.neg span else span - -let span_to_int64_us span = - let d, ps = Ptime.Span.to_d_ps span in - Int64.add - (Int64.mul (Int64.of_int d) us_count_in_day) - (Int64.div ps ps_count_in_us) - -let ptime_to_int64_us t = - let span = Ptime.to_span t in - span_to_int64_us span - -let ptime_of_int64_us us = - let span = span_of_int64_us us in - Ptime.of_span span - -type t = int64 +type t = int64 option type span = t +let never = -1L +let of_uint64_us us = if us = never then None else Some us +let to_uint64_us = function None -> never | Some us -> us + +let to_s us = + if us = never then None + else + let s = Int64.unsigned_div us 86_400_L in + Some s + module Span = struct type t = span - let to_int_s t = - let n = Int64.div t 1_000_000_L in - Int64.to_int n - - let of_int_s n = Int64.of_int @@ (n * 1_000_000) + let of_uint64_us = of_uint64_us + let to_uint64_us = to_uint64_us + let to_s = to_s end -let of_span span = ptime_of_int64_us span -let now () = Ptime_clock.now () |> ptime_to_int64_us +let compare = Int64.unsigned_compare -let diff a b = - let a = ptime_of_int64_us a in - let b = ptime_of_int64_us b in - match (a, b) with - | None, _ | _, None -> None - | Some a, Some b -> - let span = Ptime.diff a b in - Some span +let now () = + let d, ps = Ptime_clock.now () |> Ptime.to_span |> Ptime.Span.to_d_ps in + if d < 0 then Fmt.failwith "Ptime_clock.now negative ptime" + else + let d = Int64.(mul (of_int d) 86_400_L) in + let us = Int64.(div ps 1_000_000_L) in + Int64.add d us let add_span t span = - let t = ptime_of_int64_us t in - match t with - | None -> None - | Some t -> - let span = span_of_int64_us span in - Ptime.add_span t span + let us = Int64.add t span in + if compare t us > 0 then None else Some us +let sub_span t span = + let us = Int64.sub t span in + if compare t us < 0 then None else Some us + +let diff a b = if compare a b < 0 then None else Some (Int64.sub a b) (* (* microseconds since the UNIX Epoch, or "never" if None *) let jsont = @@ -83,36 +64,6 @@ let jsont = |> Jsont.Object.mem "t_s" number_or_never_jsont ~enc:Fun.id |> Jsont.Object.finish -let ptime_of_int64 i = - match Ptime.of_float_s (Int64.to_float i) with - | None -> Fmt.failwith "ptime_of_int64 error: `%Ld` is not a valid ptime" i - | Some ts -> ts - -let ptime_span_to_int64 span = span |> Ptime.Span.to_float_s |> Int64.of_float - -let ptime_span_of_int64 i = - match Ptime.Span.of_float_s (Int64.to_float i) with - | None -> - Fmt.failwith "span_of_int64 error: `%Ld` is not a valid ptime span" i - | Some ts -> ts - -(* - *) - -let encode_int64 = function None -> Int64.max_int | Some p -> ptime_to_int64 p -let decode_int64 i = if i = Int64.max_int then None else Some (ptime_of_int64 i) - -let encode_span_int64 = function - | None -> Int64.max_int - | Some p -> ptime_span_to_int64 p - -let decode_span_int64 i = - if i = Int64.max_int then None else Some (ptime_span_of_int64 i) - -let to_int64 = encode_int64 -let of_int64 = decode_int64 -let span_to_int64 = encode_span_int64 -let span_of_int64 = decode_span_int64 - (* UINT64_MAX represents "never". *) let bin = Bin.map Bin.neint64 decode_int64 encode_int64 let bin_nbo = Bin.map Bin.beint64 decode_int64 encode_int64