From 77214b7243c8268a15ac467bd1f19251b438fb6e Mon Sep 17 00:00:00 2001 From: Mark Shinwell Date: Mon, 19 Jul 2021 09:54:29 +0100 Subject: [PATCH] flambda-backend: Obj changes for Flambda 2 (#71) --- stdlib/obj.ml | 8 ++++++ stdlib/obj.mli | 6 ++-- .../tests/warnings/w59.flambda.reference | 28 +++++++++---------- testsuite/tests/warnings/w59.ml | 17 +++++++---- 4 files changed, 36 insertions(+), 23 deletions(-) diff --git a/stdlib/obj.ml b/stdlib/obj.ml index ca86e0fb4e2..3a1f981354c 100644 --- a/stdlib/obj.ml +++ b/stdlib/obj.ml @@ -30,10 +30,18 @@ external magic : 'a -> 'b = "%identity" external is_int : t -> bool = "%obj_is_int" let [@inline always] is_block a = not (is_int a) external tag : t -> int = "caml_obj_tag" [@@noalloc] +(* For Flambda 2 there is a strict distinction between arrays and other + blocks. %obj_size and %obj_field may only be used on blocks. As such + they are protected here using [Sys.opaque_identity], since this + restriction is likely not respected by callees of this module. *) external size : t -> int = "%obj_size" +let [@inline always] size t = size (Sys.opaque_identity t) external reachable_words : t -> int = "caml_obj_reachable_words" external field : t -> int -> t = "%obj_field" +let [@inline always] field t = field (Sys.opaque_identity t) external set_field : t -> int -> t -> unit = "%obj_set_field" +let [@inline always] set_field t index new_value = + set_field (Sys.opaque_identity t) index new_value external floatarray_get : floatarray -> int -> float = "caml_floatarray_get" external floatarray_set : floatarray -> int -> float -> unit = "caml_floatarray_set" diff --git a/stdlib/obj.mli b/stdlib/obj.mli index 3574e1cec1e..36be47cb95c 100644 --- a/stdlib/obj.mli +++ b/stdlib/obj.mli @@ -31,7 +31,7 @@ external magic : 'a -> 'b = "%identity" val [@inline always] is_block : t -> bool external is_int : t -> bool = "%obj_is_int" external tag : t -> int = "caml_obj_tag" [@@noalloc] -external size : t -> int = "%obj_size" +val size : t -> int external reachable_words : t -> int = "caml_obj_reachable_words" (** Computes the total size (in words, including the headers) of all @@ -42,7 +42,7 @@ external reachable_words : t -> int = "caml_obj_reachable_words" @Since 4.04 *) -external field : t -> int -> t = "%obj_field" +val field : t -> int -> t (** When using flambda: @@ -55,7 +55,7 @@ external field : t -> int -> t = "%obj_field" {!Sys.opaque_identity}, so any information about its contents will not be propagated. *) -external set_field : t -> int -> t -> unit = "%obj_set_field" +val set_field : t -> int -> t -> unit val [@inline always] double_field : t -> int -> float (* @since 3.11.2 *) val [@inline always] set_double_field : t -> int -> float -> unit diff --git a/testsuite/tests/warnings/w59.flambda.reference b/testsuite/tests/warnings/w59.flambda.reference index 8277d948589..a2efe91848c 100644 --- a/testsuite/tests/warnings/w59.flambda.reference +++ b/testsuite/tests/warnings/w59.flambda.reference @@ -1,29 +1,29 @@ -File "w59.ml", line 46, characters 2-43: -46 | Obj.set_field (Obj.repr o) 0 (Obj.repr 3); - ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +File "w59.ml", line 51, characters 2-39: +51 | set_field (Obj.repr o) 0 (Obj.repr 3); + ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Warning 59 [flambda-assignment-to-non-mutable-value]: A potential assignment to a non-mutable value was detected in this source file. Such assignments may generate incorrect code when using Flambda. -File "w59.ml", line 47, characters 2-43: -47 | Obj.set_field (Obj.repr p) 0 (Obj.repr 3); - ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +File "w59.ml", line 52, characters 2-39: +52 | set_field (Obj.repr p) 0 (Obj.repr 3); + ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Warning 59 [flambda-assignment-to-non-mutable-value]: A potential assignment to a non-mutable value was detected in this source file. Such assignments may generate incorrect code when using Flambda. -File "w59.ml", line 48, characters 2-43: -48 | Obj.set_field (Obj.repr q) 0 (Obj.repr 3); - ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +File "w59.ml", line 53, characters 2-39: +53 | set_field (Obj.repr q) 0 (Obj.repr 3); + ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Warning 59 [flambda-assignment-to-non-mutable-value]: A potential assignment to a non-mutable value was detected in this source file. Such assignments may generate incorrect code when using Flambda. -File "w59.ml", line 49, characters 2-43: -49 | Obj.set_field (Obj.repr r) 0 (Obj.repr 3) - ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ +File "w59.ml", line 54, characters 2-39: +54 | set_field (Obj.repr r) 0 (Obj.repr 3) + ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Warning 59 [flambda-assignment-to-non-mutable-value]: A potential assignment to a non-mutable value was detected in this source file. Such assignments may generate incorrect code when using Flambda. -File "w59.ml", line 56, characters 2-7: -56 | set o +File "w59.ml", line 61, characters 2-7: +61 | set o ^^^^^ Warning 59 [flambda-assignment-to-non-mutable-value]: A potential assignment to a non-mutable value was detected in this source file. Such assignments may generate incorrect code diff --git a/testsuite/tests/warnings/w59.ml b/testsuite/tests/warnings/w59.ml index 119e3638747..0a6d35291b2 100644 --- a/testsuite/tests/warnings/w59.ml +++ b/testsuite/tests/warnings/w59.ml @@ -42,14 +42,19 @@ let p = fun x -> x let q = 3.14 let r = 1 +(* %obj_set_field is OK here for Flambda 2 because we never use + it on an array. We can't use Obj.field since that function + contains a [Sys.opaque_identity]. *) +external set_field : Obj.t -> int -> Obj.t -> unit = "%obj_set_field" + let () = - Obj.set_field (Obj.repr o) 0 (Obj.repr 3); - Obj.set_field (Obj.repr p) 0 (Obj.repr 3); - Obj.set_field (Obj.repr q) 0 (Obj.repr 3); - Obj.set_field (Obj.repr r) 0 (Obj.repr 3) + set_field (Obj.repr o) 0 (Obj.repr 3); + set_field (Obj.repr p) 0 (Obj.repr 3); + set_field (Obj.repr q) 0 (Obj.repr 3); + set_field (Obj.repr r) 0 (Obj.repr 3) let set v = - Obj.set_field (Obj.repr v) 0 (Obj.repr 3) + set_field (Obj.repr v) 0 (Obj.repr 3) [@@inline] let () = @@ -59,7 +64,7 @@ let () = let opaque = Sys.opaque_identity (1,2) let set_opaque = - Obj.set_field + set_field (Obj.repr opaque) 0 (Obj.repr 3)