Skip to content

Commit 7bd6587

Browse files
nojbmshinwell
authored andcommitted
Add new module Targetint (ocaml#759)
1 parent 7747145 commit 7bd6587

File tree

4 files changed

+291
-1
lines changed

4 files changed

+291
-1
lines changed

.depend

+3
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,9 @@ utils/strongly_connected_components.cmo : utils/numbers.cmi utils/misc.cmi \
3131
utils/strongly_connected_components.cmx : utils/numbers.cmx utils/misc.cmx \
3232
utils/identifiable.cmx utils/strongly_connected_components.cmi
3333
utils/strongly_connected_components.cmi : utils/identifiable.cmi
34+
utils/targetint.cmo : utils/misc.cmi utils/targetint.cmi
35+
utils/targetint.cmx : utils/misc.cmx utils/targetint.cmi
36+
utils/targetint.cmi :
3437
utils/tbl.cmo : utils/tbl.cmi
3538
utils/tbl.cmx : utils/tbl.cmi
3639
utils/tbl.cmi :

Makefile.shared

+2-1
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,8 @@ UTILS=utils/config.cmo utils/misc.cmo \
4747
utils/clflags.cmo utils/tbl.cmo utils/timings.cmo \
4848
utils/terminfo.cmo utils/ccomp.cmo utils/warnings.cmo \
4949
utils/consistbl.cmo \
50-
utils/strongly_connected_components.cmo
50+
utils/strongly_connected_components.cmo \
51+
utils/targetint.cmo
5152

5253
PARSING=parsing/location.cmo parsing/longident.cmo \
5354
parsing/docstrings.cmo parsing/ast_helper.cmo \

utils/targetint.ml

+98
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
(**************************************************************************)
2+
(* *)
3+
(* OCaml *)
4+
(* *)
5+
(* Xavier Leroy, projet Cristal, INRIA Rocquencourt *)
6+
(* Nicolas Ojeda Bar, LexiFi *)
7+
(* *)
8+
(* Copyright 2016 Institut National de Recherche en Informatique et *)
9+
(* en Automatique. *)
10+
(* *)
11+
(* All rights reserved. This file is distributed under the terms of *)
12+
(* the GNU Lesser General Public License version 2.1, with the *)
13+
(* special exception on linking described in the file LICENSE. *)
14+
(* *)
15+
(**************************************************************************)
16+
17+
type repr =
18+
| Int32 of int32
19+
| Int64 of int64
20+
21+
module type S = sig
22+
type t
23+
val zero : t
24+
val one : t
25+
val minus_one : t
26+
val neg : t -> t
27+
val add : t -> t -> t
28+
val sub : t -> t -> t
29+
val mul : t -> t -> t
30+
val div : t -> t -> t
31+
val rem : t -> t -> t
32+
val succ : t -> t
33+
val pred : t -> t
34+
val abs : t -> t
35+
val max_int : t
36+
val min_int : t
37+
val logand : t -> t -> t
38+
val logor : t -> t -> t
39+
val logxor : t -> t -> t
40+
val lognot : t -> t
41+
val shift_left : t -> int -> t
42+
val shift_right : t -> int -> t
43+
val shift_right_logical : t -> int -> t
44+
val of_int : int -> t
45+
val of_int_exn : int -> t
46+
val to_int : t -> int
47+
val of_float : float -> t
48+
val to_float : t -> float
49+
val of_int32 : int32 -> t
50+
val to_int32 : t -> int32
51+
val of_int64 : int64 -> t
52+
val to_int64 : t -> int64
53+
val of_string : string -> t
54+
val to_string : t -> string
55+
val compare: t -> t -> int
56+
val equal: t -> t -> bool
57+
val repr: t -> repr
58+
end
59+
60+
let size = Sys.word_size
61+
(* Later, this will be set by the configure script
62+
in order to support cross-compilation. *)
63+
64+
module Int32 = struct
65+
include Int32
66+
let of_int_exn =
67+
match Sys.word_size with (* size of [int] *)
68+
| 32 ->
69+
Int32.of_int
70+
| 64 ->
71+
fun n ->
72+
if n < Int32.(to_int min_int) || n > Int32.(to_int max_int) then
73+
Misc.fatal_errorf "Targetint.of_int_exn: 0x%x out of range" n
74+
else
75+
Int32.of_int n
76+
| _ ->
77+
assert false
78+
let of_int32 x = x
79+
let to_int32 x = x
80+
let of_int64 = Int64.to_int32
81+
let to_int64 = Int64.of_int32
82+
let repr x = Int32 x
83+
end
84+
85+
module Int64 = struct
86+
include Int64
87+
let of_int_exn = Int64.of_int
88+
let of_int64 x = x
89+
let to_int64 x = x
90+
let repr x = Int64 x
91+
end
92+
93+
include (val
94+
(match size with
95+
| 32 -> (module Int32)
96+
| 64 -> (module Int64)
97+
| _ -> assert false
98+
) : S)

utils/targetint.mli

+188
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,188 @@
1+
(**************************************************************************)
2+
(* *)
3+
(* OCaml *)
4+
(* *)
5+
(* Xavier Leroy, projet Cristal, INRIA Rocquencourt *)
6+
(* Nicolas Ojeda Bar, LexiFi *)
7+
(* *)
8+
(* Copyright 2016 Institut National de Recherche en Informatique et *)
9+
(* en Automatique. *)
10+
(* *)
11+
(* All rights reserved. This file is distributed under the terms of *)
12+
(* the GNU Lesser General Public License version 2.1, with the *)
13+
(* special exception on linking described in the file LICENSE. *)
14+
(* *)
15+
(**************************************************************************)
16+
17+
(** Target processor-native integers.
18+
19+
This module provides operations on the type of
20+
signed 32-bit integers (on 32-bit target platforms) or
21+
signed 64-bit integers (on 64-bit target platforms).
22+
This integer type has exactly the same width as that of a
23+
pointer type in the C compiler. All arithmetic operations over
24+
are taken modulo 2{^32} or 2{^64} depending
25+
on the word size of the target architecture.
26+
*)
27+
28+
type t
29+
(** The type of target integers. *)
30+
31+
val zero : t
32+
(** The target integer 0.*)
33+
34+
val one : t
35+
(** The target integer 1.*)
36+
37+
val minus_one : t
38+
(** The target integer -1.*)
39+
40+
val neg : t -> t
41+
(** Unary negation. *)
42+
43+
val add : t -> t -> t
44+
(** Addition. *)
45+
46+
val sub : t -> t -> t
47+
(** Subtraction. *)
48+
49+
val mul : t -> t -> t
50+
(** Multiplication. *)
51+
52+
val div : t -> t -> t
53+
(** Integer division. Raise [Division_by_zero] if the second
54+
argument is zero. This division rounds the real quotient of
55+
its arguments towards zero, as specified for {!Pervasives.(/)}. *)
56+
57+
val rem : t -> t -> t
58+
(** Integer remainder. If [y] is not zero, the result
59+
of [Targetint.rem x y] satisfies the following properties:
60+
[Targetint.zero <= Nativeint.rem x y < Targetint.abs y] and
61+
[x = Targetint.add (Targetint.mul (Targetint.div x y) y)
62+
(Targetint.rem x y)].
63+
If [y = 0], [Targetint.rem x y] raises [Division_by_zero]. *)
64+
65+
val succ : t -> t
66+
(** Successor.
67+
[Targetint.succ x] is [Targetint.add x Targetint.one]. *)
68+
69+
val pred : t -> t
70+
(** Predecessor.
71+
[Targetint.pred x] is [Targetint.sub x Targetint.one]. *)
72+
73+
val abs : t -> t
74+
(** Return the absolute value of its argument. *)
75+
76+
val size : int
77+
(** The size in bits of a target native integer. *)
78+
79+
val max_int : t
80+
(** The greatest representable target integer,
81+
either 2{^31} - 1 on a 32-bit platform,
82+
or 2{^63} - 1 on a 64-bit platform. *)
83+
84+
val min_int : t
85+
(** The greatest representable target integer,
86+
either -2{^31} on a 32-bit platform,
87+
or -2{^63} on a 64-bit platform. *)
88+
89+
val logand : t -> t -> t
90+
(** Bitwise logical and. *)
91+
92+
val logor : t -> t -> t
93+
(** Bitwise logical or. *)
94+
95+
val logxor : t -> t -> t
96+
(** Bitwise logical exclusive or. *)
97+
98+
val lognot : t -> t
99+
(** Bitwise logical negation *)
100+
101+
val shift_left : t -> int -> t
102+
(** [Targetint.shift_left x y] shifts [x] to the left by [y] bits.
103+
The result is unspecified if [y < 0] or [y >= bitsize],
104+
where [bitsize] is [32] on a 32-bit platform and
105+
[64] on a 64-bit platform. *)
106+
107+
val shift_right : t -> int -> t
108+
(** [Targetint.shift_right x y] shifts [x] to the right by [y] bits.
109+
This is an arithmetic shift: the sign bit of [x] is replicated
110+
and inserted in the vacated bits.
111+
The result is unspecified if [y < 0] or [y >= bitsize]. *)
112+
113+
val shift_right_logical : t -> int -> t
114+
(** [Targetint.shift_right_logical x y] shifts [x] to the right
115+
by [y] bits.
116+
This is a logical shift: zeroes are inserted in the vacated bits
117+
regardless of the sign of [x].
118+
The result is unspecified if [y < 0] or [y >= bitsize]. *)
119+
120+
val of_int : int -> t
121+
(** Convert the given integer (type [int]) to a target integer
122+
(type [t]), module the target word size. *)
123+
124+
val of_int_exn : int -> t
125+
(** Convert the given integer (type [int]) to a target integer
126+
(type [t]). Raises a fatal error if the conversion is not exact. *)
127+
128+
val to_int : t -> int
129+
(** Convert the given target integer (type [t]) to an
130+
integer (type [int]). The high-order bit is lost during
131+
the conversion. *)
132+
133+
val of_float : float -> t
134+
(** Convert the given floating-point number to a target integer,
135+
discarding the fractional part (truncate towards 0).
136+
The result of the conversion is undefined if, after truncation,
137+
the number is outside the range
138+
\[{!Targetint.min_int}, {!Targetint.max_int}\]. *)
139+
140+
val to_float : t -> float
141+
(** Convert the given target integer to a floating-point number. *)
142+
143+
val of_int32 : int32 -> t
144+
(** Convert the given 32-bit integer (type [int32])
145+
to a target integer. *)
146+
147+
val to_int32 : t -> int32
148+
(** Convert the given target integer to a
149+
32-bit integer (type [int32]). On 64-bit platforms,
150+
the 64-bit native integer is taken modulo 2{^32},
151+
i.e. the top 32 bits are lost. On 32-bit platforms,
152+
the conversion is exact. *)
153+
154+
val of_int64 : int64 -> t
155+
(** Convert the given 64-bit integer (type [int64])
156+
to a target integer. *)
157+
158+
val to_int64 : t -> int64
159+
(** Convert the given target integer to a
160+
64-bit integer (type [int64]). *)
161+
162+
val of_string : string -> t
163+
(** Convert the given string to a target integer.
164+
The string is read in decimal (by default) or in hexadecimal,
165+
octal or binary if the string begins with [0x], [0o] or [0b]
166+
respectively.
167+
Raise [Failure "int_of_string"] if the given string is not
168+
a valid representation of an integer, or if the integer represented
169+
exceeds the range of integers representable in type [nativeint]. *)
170+
171+
val to_string : t -> string
172+
(** Return the string representation of its argument, in decimal. *)
173+
174+
val compare: t -> t -> int
175+
(** The comparison function for target integers, with the same specification as
176+
{!Pervasives.compare}. Along with the type [t], this function [compare]
177+
allows the module [Targetint] to be passed as argument to the functors
178+
{!Set.Make} and {!Map.Make}. *)
179+
180+
val equal: t -> t -> bool
181+
(** The equal function for target ints. *)
182+
183+
type repr =
184+
| Int32 of int32
185+
| Int64 of int64
186+
187+
val repr : t -> repr
188+
(** The concrete representation of a native integer. *)

0 commit comments

Comments
 (0)