public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
From: Richard Biener <rguenther@suse.de>
To: gcc-patches@gcc.gnu.org
Cc: "Joseph S. Myers" <joseph@codesourcery.com>
Subject: [PATCH] Handle wide-chars in native_encode_string
Date: Mon, 04 Sep 2017 14:27:00 -0000	[thread overview]
Message-ID: <alpine.LSU.2.20.1709041617300.14191@zhemvz.fhfr.qr> (raw)


The following patch cures the missed optimization in PR82084, vectorizing
a wide-char initializer

  wchar_t strs[4][2]= {  L"A", L"B", L"C" , L"D"};

with AVX to

  MEM[(wchar_t[2] *)&strs] = { 65, 66, 67, 68 };

it's not entirely clear to me whether the individual STRING_CSTs we
build for the gimplified code

        strs[0] = "A";
        strs[1] = "B";
        strs[2] = "C";
        strs[3] = "D";

always have a consistend "character" size and how the individual
"characters" are encoded.  The patch assumes that the array element
type of the STRING_CST can be used to get access to individual
characters by means of the element type size and those elements
are stored in host byteorder.  Which means the patch simply handles
16bit and 32bit "characters" as 16bit and 32bit integers and encodes
them with the same rules as such integers.

Joseph, are there more considerations for encoding the target
representation of STRING_CSTs?

Looks I was too lazy to lookup answers to those questions from
the RTL expansion code which hopefully outputs constant initializers
properly.

Apart from vectorization in the mentioned testcase we also gain
constant folding from pices from this change (but I don't adjust
fold_read_from_constant_string yet).

Thanks,
Richard.

2017-09-04  Richard Biener  <rguenther@suse.de>

	PR tree-optimization/82084
	* fold-const.c (native_encode_string): Handle wide characters.
	(can_native_encode_string_p): Likewise.

Index: gcc/fold-const.c
===================================================================
--- gcc/fold-const.c	(revision 251661)
+++ gcc/fold-const.c	(working copy)
@@ -7187,26 +7187,71 @@ native_encode_string (const_tree expr, u
   if (! can_native_encode_string_p (expr))
     return 0;
 
-  HOST_WIDE_INT total_bytes = tree_to_shwi (TYPE_SIZE_UNIT (TREE_TYPE (expr)));
+  tree type = TREE_TYPE (expr);
+  HOST_WIDE_INT total_bytes = tree_to_shwi (TYPE_SIZE_UNIT (type));
+  int orig_off = off;
   if ((off == -1 && total_bytes > len)
       || off >= total_bytes)
     return 0;
   if (off == -1)
     off = 0;
-  if (TREE_STRING_LENGTH (expr) - off < MIN (total_bytes, len))
+
+  HOST_WIDE_INT elsz = tree_to_shwi (TYPE_SIZE_UNIT (TREE_TYPE (type)));
+  if (elsz == 1)
     {
-      int written = 0;
-      if (off < TREE_STRING_LENGTH (expr))
+      if (TREE_STRING_LENGTH (expr) - off < MIN (total_bytes, len))
 	{
-	  written = MIN (len, TREE_STRING_LENGTH (expr) - off);
-	  memcpy (ptr, TREE_STRING_POINTER (expr) + off, written);
+	  int written = 0;
+	  if (off < TREE_STRING_LENGTH (expr))
+	    {
+	      written = MIN (len, TREE_STRING_LENGTH (expr) - off);
+	      memcpy (ptr, TREE_STRING_POINTER (expr) + off, written);
+	    }
+	  memset (ptr + written, 0,
+		  MIN (total_bytes - written, len - written));
 	}
-      memset (ptr + written, 0,
-	      MIN (total_bytes - written, len - written));
+      else
+	memcpy (ptr, TREE_STRING_POINTER (expr) + off, MIN (total_bytes, len));
+      return MIN (total_bytes - off, len);
     }
   else
-    memcpy (ptr, TREE_STRING_POINTER (expr) + off, MIN (total_bytes, len));
-  return MIN (total_bytes - off, len);
+    {
+      tree ielt = build_nonstandard_integer_type (elsz * 8, true);
+      int offset = 0;
+      bool first = true;
+      for (int o = off & ~(elsz - 1); o < total_bytes; o += elsz)
+	{
+	  unsigned HOST_WIDE_INT c;
+	  switch (elsz)
+	    {
+	    case 2:
+	      {
+		uint16_t s;
+		memcpy (&s, TREE_STRING_POINTER (expr) + o, 2);
+		c = s;
+		break;
+	      }
+	    case 4:
+	      {
+		uint32_t i;
+		memcpy (&i, TREE_STRING_POINTER (expr) + o, 4);
+		c = i;
+		break;
+	      }
+	    default:
+	      gcc_unreachable ();
+	    }
+	  tree elem = build_int_cstu (ielt, c);
+	  int res = native_encode_expr (elem, ptr+offset, len-offset,
+					first ? off & (elsz - 1) : 0);
+	  if ((orig_off == -1 && res != elsz)
+	      || res == 0)
+	    return 0;
+	  offset += res;
+	  first = false;
+	}
+      return offset;
+    }
 }
 
 
@@ -7491,10 +7536,11 @@ can_native_encode_string_p (const_tree e
 
   if (TREE_CODE (type) != ARRAY_TYPE
       || TREE_CODE (TREE_TYPE (type)) != INTEGER_TYPE
-      || (GET_MODE_BITSIZE (SCALAR_INT_TYPE_MODE (TREE_TYPE (type)))
-	  != BITS_PER_UNIT)
       || !tree_fits_shwi_p (TYPE_SIZE_UNIT (type)))
     return false;
+  HOST_WIDE_INT elsz = tree_to_shwi (TYPE_SIZE_UNIT (TREE_TYPE (type)));
+  if (elsz != 1 && elsz != 2 && elsz != 4)
+    return false;
   return true;
 }
 

             reply	other threads:[~2017-09-04 14:27 UTC|newest]

Thread overview: 4+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-09-04 14:27 Richard Biener [this message]
2017-09-04 14:52 ` Joseph Myers
2017-09-05  8:25   ` Richard Biener
2017-09-05 12:39     ` Joseph Myers

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=alpine.LSU.2.20.1709041617300.14191@zhemvz.fhfr.qr \
    --to=rguenther@suse.de \
    --cc=gcc-patches@gcc.gnu.org \
    --cc=joseph@codesourcery.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).