[patch] AVR: Support strict address space subset relations

Georg-Johann Lay <[email protected]>
Newsgroups gmane.comp.gcc.patches
Message-ID <[email protected]>
To date, each named address space is implemented as a subset
of all the other address spaces, which allows code like

    char read_char (const char *addr, bool in_flash)
    {
       return in_flash
         ? *(const __flash char*) addr  // Read from program memory.
         : *addr;                       // Read from RAM.
    }

even though __flash is not a subset of Generic.

This patch introduces new target option -mstrict-addr-space-subsets
which instructs avr_addr_space_subset_p to implement the address
space subset relations like they actually are, i.e.

    __memx > __flashx > __flash, __flash1, ..., __flash5
    __memx > Generic

Ok for trunk?

Johann

--

gcc/
	* config/avr/avr.opt (-mstrict-addr-space-subsets): New
	target option.
	* config/avr/avr.cc (avr_addr_space_subset_p): Use it.
	* doc/invoke.texi (AVR Options): Document it.
strict-as.diff (text/x-patch, 3.5 KB)
diff --git a/gcc/config/avr/avr.cc b/gcc/config/avr/avr.cc
index 87c4044f076..7c003941bdc 100644
--- a/gcc/config/avr/avr.cc
+++ b/gcc/config/avr/avr.cc
@@ -15404,18 +15404,7 @@ avr_addr_space_convert (rtx src, tree type_old, tree type_new)
 }
 
 
-/* Implement `TARGET_ADDR_SPACE_SUBSET_P'.  */
-
-static bool
-avr_addr_space_subset_p (addr_space_t /*subset*/, addr_space_t /*superset*/)
-{
-  /* Allow any kind of pointer mess.  */
-
-  return true;
-}
-
-
-/* Helps the next function.  */
+/* Helps the next two functions.  */
 
 static bool
 avr_addr_space_contains (addr_space_t super, addr_space_t sub)
@@ -15427,6 +15416,17 @@ avr_addr_space_contains (addr_space_t super, addr_space_t sub)
 }
 
 
+/* Implement `TARGET_ADDR_SPACE_SUBSET_P'.  */
+
+static bool
+avr_addr_space_subset_p (addr_space_t subset, addr_space_t superset)
+{
+  // Allow any kind of pointer casts with -mno-strict-addr-space-subsets.
+  return (!avropt_strict_addr_space_subsets
+	  || avr_addr_space_contains (superset, subset));
+}
+
+
 /* Implement `TARGET_CONVERT_TO_TYPE'.  */
 
 static tree
diff --git a/gcc/config/avr/avr.opt b/gcc/config/avr/avr.opt
index 97d207726ba..d56061b50b6 100644
--- a/gcc/config/avr/avr.opt
+++ b/gcc/config/avr/avr.opt
@@ -115,6 +115,10 @@ msplit-ldst
 Target Var(avropt_split_ldst) Init(0) Optimization
 Optimization. Split most of the load and store instructions into byte load and stores.
 
+mstrict-addr-space-subsets
+Target Var(avropt_strict_addr_space_subsets) Init(0)
+Implement strict named address space subset relations.
+
 mstrict-X
 Target Var(avropt_strict_X) Init(0) Optimization
 Optimization. When accessing RAM, use X as imposed by the hardware, i.e. just use pre-decrement, post-increment and indirect addressing with the X register.  Without this option, the compiler may assume that there is an addressing mode X+const similar to Y+const and Z+const and emit instructions to emulate such an addressing mode for X.
diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi
index 2e53a8c8a7e..d6cfc459853 100644
--- a/gcc/doc/invoke.texi
+++ b/gcc/doc/invoke.texi
@@ -991,7 +991,7 @@ Objective-C and Objective-C++ Dialects}.
 -mdouble=@var{bits}  -mlong-double=@var{bits}  -mno-call-main
 -mn_flash=@var{size}  -mfract-convert-truncate  -mno-interrupts
 -mmain-is-OS_task  -mrelax  -mpmem-wrap-around
--mrmw  -mstrict-X  -mtiny-stack
+-mrmw  -mstrict-addr-space-subsets  -mstrict-X  -mtiny-stack
 -mrodata-in-ram  -msplit-bit-shift  -msplit-ldst  -mshort-calls
 -mskip-bug  -muse-nonzero-bits  -nodevicelib  -nodevicespecs
 -Wasm-len-notes  -Waddr-space-convert  -Wmisspelled-isr}
@@ -24595,6 +24595,23 @@ aspect of the optimization.
 @item -mfuse-move2
 Run a post combine optimization pass that tries to fuse move instructions.
 
+@opindex mstrict-addr-space-subsets
+@item -mstrict-addr-space-subsets
+Impose strict named address space subset relations.  Without this option,
+every address space is considered to be a subset of all the other spaces,
+which allows to write code like
+@example
+char read_char (const char *addr, bool in_flash)
+@{
+   return in_flash
+     ? *(const __flash char*) addr  // Read from program memory.
+     : *addr;                       // Read from RAM.
+@}
+@end example
+When the option is on, such code is rejected since address space
+@code{__flash} is not a subset of the generic space, and hence the
+cast in the above code is prohibited.
+
 @opindex mstrict-X
 @item -mstrict-X
 Use address register @code{X} in a way proposed by the hardware.  This means
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.