[Ada] New restriction for lock-free implementation

Message ID 20120730151227.GA14362@adacore.com
State New
Headers show

Commit Message

Arnaud Charlet July 30, 2012, 3:12 p.m.
This patch implements a new lock-free restriction. Thus, implicit dereferences
of access values prevent, as well as explicit dereference, the lock-free
implementation of protected objects.

The test below illustrates the new lock-free restriction:

-- Source --

   type Elmt_Type is private;
   type Elmt_Access is access Elmt_Type;

package Test is
   type Node_Type;
   type Node_Access is access all Node_Type;

   type Node_Type is limited record
      Elmt : Elmt_Access;
      Prev : Node_Access;
   end record;

   protected List with Lock_Free is
      procedure Swap (L, R : Node_Access);
      L : Node_Access := null;
   end List;
end Test;

package body Test is
   protected body List is
      -- Swap --

      procedure Swap (L, R : Node_Access) is
         LP : constant Node_Access := L.Prev;
         RP : constant Node_Access := R.Prev;

         L.Prev := RP;
         R.Prev := LP;
      end Swap;
   end List;
end Test;

-- Compilation --

$ gnatmake -q -gnat12 test.adb
test.adb:7:07: illegal body when Lock_Free given
test.adb:8:40: dereference of access value not allowed
test.adb:9:40: dereference of access value not allowed
test.adb:12:11: dereference of access value not allowed
test.adb:13:11: dereference of access value not allowed

Tested on x86_64-pc-linux-gnu, committed on trunk

2012-07-30  Vincent Pucci  <pucci@adacore.com>

	* sem_ch9.adb (Allows_Lock_Free_Implementation): Restrict implicit
	dereferences of access values.


Index: sem_ch9.adb
--- sem_ch9.adb	(revision 189974)
+++ sem_ch9.adb	(working copy)
@@ -411,12 +411,15 @@ 
                         return Abandon;
-                     --  Explicit dereferences restricted (i.e. dereferences of
-                     --  access values).
+                     --  Dereferences of access values restricted
-                     elsif Kind = N_Explicit_Dereference then
+                     elsif Kind = N_Explicit_Dereference
+                       or else (Kind = N_Selected_Component
+                                 and then Is_Access_Type (Etype (Prefix (N))))
+                     then
                         if Lock_Free_Given then
-                           Error_Msg_N ("explicit dereference not allowed", N);
+                           Error_Msg_N ("dereference of access value " &
+                                        "not allowed", N);
                            return Skip;
                         end if;