diff mbox series

RISC-V: Canonicalize --with-arch

Message ID 20201201081313.68385-1-kito.cheng@sifive.com
State New
Headers show
Series RISC-V: Canonicalize --with-arch | expand

Commit Message

Kito Cheng Dec. 1, 2020, 8:13 a.m. UTC
- We would like to canonicalize the arch string for --with-arch for
   easier handling multilib, so split canonicalization part to a stand
   along script to shared the logic.

gcc/ChangeLog:

	* config/riscv/multilib-generator (arch_canonicalize): Move
	code to arch-canonicalize, and call that script to canonicalize arch
	string.
	(canonical_order): Move code to arch-canonicalize.
	(LONG_EXT_PREFIXES): Ditto.
	(IMPLIED_EXT): Ditto.
	* config/riscv/arch-canonicalize: New.
	* config.gcc (riscv*-*-*): Canonicalize --with-arch.
---
 gcc/config.gcc                      |   1 +
 gcc/config/riscv/arch-canonicalize  | 102 ++++++++++++++++++++++++++++
 gcc/config/riscv/multilib-generator |  83 +++-------------------
 3 files changed, 111 insertions(+), 75 deletions(-)
 create mode 100755 gcc/config/riscv/arch-canonicalize

Comments

Jim Wilson Dec. 3, 2020, 12:51 a.m. UTC | #1
On Tue, Dec 1, 2020 at 12:13 AM Kito Cheng <kito.cheng@sifive.com> wrote:

>  - We would like to canonicalize the arch string for --with-arch for
>    easier handling multilib, so split canonicalization part to a stand
>    along script to shared the logic.
>
> gcc/ChangeLog:
>
>         * config/riscv/multilib-generator (arch_canonicalize): Move
>         code to arch-canonicalize, and call that script to canonicalize
> arch
>         string.
>         (canonical_order): Move code to arch-canonicalize.
>         (LONG_EXT_PREFIXES): Ditto.
>         (IMPLIED_EXT): Ditto.
>         * config/riscv/arch-canonicalize: New.
>         * config.gcc (riscv*-*-*): Canonicalize --with-arch.
>

Looks OK to me.

Jim
Kito Cheng Dec. 4, 2020, 8:07 a.m. UTC | #2
Committed, thanks :)

On Thu, Dec 3, 2020 at 8:51 AM Jim Wilson <jimw@sifive.com> wrote:
>
> On Tue, Dec 1, 2020 at 12:13 AM Kito Cheng <kito.cheng@sifive.com> wrote:
>>
>>  - We would like to canonicalize the arch string for --with-arch for
>>    easier handling multilib, so split canonicalization part to a stand
>>    along script to shared the logic.
>>
>> gcc/ChangeLog:
>>
>>         * config/riscv/multilib-generator (arch_canonicalize): Move
>>         code to arch-canonicalize, and call that script to canonicalize arch
>>         string.
>>         (canonical_order): Move code to arch-canonicalize.
>>         (LONG_EXT_PREFIXES): Ditto.
>>         (IMPLIED_EXT): Ditto.
>>         * config/riscv/arch-canonicalize: New.
>>         * config.gcc (riscv*-*-*): Canonicalize --with-arch.
>
>
> Looks OK to me.
>
> Jim
>
Matthias Klose Dec. 4, 2020, 1:38 p.m. UTC | #3
On 12/4/20 9:07 AM, Kito Cheng via Gcc-patches wrote:
> Committed, thanks :)
> 
> On Thu, Dec 3, 2020 at 8:51 AM Jim Wilson <jimw@sifive.com> wrote:
>>
>> On Tue, Dec 1, 2020 at 12:13 AM Kito Cheng <kito.cheng@sifive.com> wrote:
>>>
>>>  - We would like to canonicalize the arch string for --with-arch for
>>>    easier handling multilib, so split canonicalization part to a stand
>>>    along script to shared the logic.
>>>
>>> gcc/ChangeLog:
>>>
>>>         * config/riscv/multilib-generator (arch_canonicalize): Move
>>>         code to arch-canonicalize, and call that script to canonicalize arch
>>>         string.
>>>         (canonical_order): Move code to arch-canonicalize.
>>>         (LONG_EXT_PREFIXES): Ditto.
>>>         (IMPLIED_EXT): Ditto.
>>>         * config/riscv/arch-canonicalize: New.
>>>         * config.gcc (riscv*-*-*): Canonicalize --with-arch.
>>
>>
>> Looks OK to me.

that breaks the bootstrap if python is not available. The python command might
not be available, so please check for python3, python, or python2.

And it adds an unconditional build dependency on python for building the riscv
targets.

Matthias
Jakub Jelinek Dec. 4, 2020, 1:43 p.m. UTC | #4
On Fri, Dec 04, 2020 at 02:38:54PM +0100, Matthias Klose wrote:
> On 12/4/20 9:07 AM, Kito Cheng via Gcc-patches wrote:
> > Committed, thanks :)
> > 
> > On Thu, Dec 3, 2020 at 8:51 AM Jim Wilson <jimw@sifive.com> wrote:
> >>
> >> On Tue, Dec 1, 2020 at 12:13 AM Kito Cheng <kito.cheng@sifive.com> wrote:
> >>>
> >>>  - We would like to canonicalize the arch string for --with-arch for
> >>>    easier handling multilib, so split canonicalization part to a stand
> >>>    along script to shared the logic.
> >>>
> >>> gcc/ChangeLog:
> >>>
> >>>         * config/riscv/multilib-generator (arch_canonicalize): Move
> >>>         code to arch-canonicalize, and call that script to canonicalize arch
> >>>         string.
> >>>         (canonical_order): Move code to arch-canonicalize.
> >>>         (LONG_EXT_PREFIXES): Ditto.
> >>>         (IMPLIED_EXT): Ditto.
> >>>         * config/riscv/arch-canonicalize: New.
> >>>         * config.gcc (riscv*-*-*): Canonicalize --with-arch.
> >>
> >>
> >> Looks OK to me.
> 
> that breaks the bootstrap if python is not available. The python command might
> not be available, so please check for python3, python, or python2.
> 
> And it adds an unconditional build dependency on python for building the riscv
> targets.

Yeah, doing it in awk or shell might be better.  We do use python for
various things, but generally try not to require it for build and make
check, e.g. some contrib/ scripts used during build and make check have
shell variants etc.

	Jakub
Matthias Klose Dec. 4, 2020, 2:41 p.m. UTC | #5
On 12/4/20 2:38 PM, Matthias Klose wrote:
> On 12/4/20 9:07 AM, Kito Cheng via Gcc-patches wrote:
>> Committed, thanks :)
>>
>> On Thu, Dec 3, 2020 at 8:51 AM Jim Wilson <jimw@sifive.com> wrote:
>>>
>>> On Tue, Dec 1, 2020 at 12:13 AM Kito Cheng <kito.cheng@sifive.com> wrote:
>>>>
>>>>  - We would like to canonicalize the arch string for --with-arch for
>>>>    easier handling multilib, so split canonicalization part to a stand
>>>>    along script to shared the logic.
>>>>
>>>> gcc/ChangeLog:
>>>>
>>>>         * config/riscv/multilib-generator (arch_canonicalize): Move
>>>>         code to arch-canonicalize, and call that script to canonicalize arch
>>>>         string.
>>>>         (canonical_order): Move code to arch-canonicalize.
>>>>         (LONG_EXT_PREFIXES): Ditto.
>>>>         (IMPLIED_EXT): Ditto.
>>>>         * config/riscv/arch-canonicalize: New.
>>>>         * config.gcc (riscv*-*-*): Canonicalize --with-arch.
>>>
>>>
>>> Looks OK to me.
> 
> that breaks the bootstrap if python is not available. The python command might
> not be available, so please check for python3, python, or python2.

same for config/riscv/arch-canonicalize
Kito Cheng Dec. 6, 2020, 3:35 a.m. UTC | #6
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=98152

Andreas Schwab has created a bug entry for this issue,
using awk or shell should be fine to get the same functionality, but
it might take some time,
so I plan to add some checking to detect python, python2 or python3,
and skip this step if none of above is found.
The arch string canonicalize is not a must, it's a kind of improvement,
trying to reduce the build # of multi-lib, so I think skip that should
not be a problem if python is not available.

On Fri, Dec 4, 2020 at 10:41 PM Matthias Klose <doko@ubuntu.com> wrote:
>
> On 12/4/20 2:38 PM, Matthias Klose wrote:
> > On 12/4/20 9:07 AM, Kito Cheng via Gcc-patches wrote:
> >> Committed, thanks :)
> >>
> >> On Thu, Dec 3, 2020 at 8:51 AM Jim Wilson <jimw@sifive.com> wrote:
> >>>
> >>> On Tue, Dec 1, 2020 at 12:13 AM Kito Cheng <kito.cheng@sifive.com> wrote:
> >>>>
> >>>>  - We would like to canonicalize the arch string for --with-arch for
> >>>>    easier handling multilib, so split canonicalization part to a stand
> >>>>    along script to shared the logic.
> >>>>
> >>>> gcc/ChangeLog:
> >>>>
> >>>>         * config/riscv/multilib-generator (arch_canonicalize): Move
> >>>>         code to arch-canonicalize, and call that script to canonicalize arch
> >>>>         string.
> >>>>         (canonical_order): Move code to arch-canonicalize.
> >>>>         (LONG_EXT_PREFIXES): Ditto.
> >>>>         (IMPLIED_EXT): Ditto.
> >>>>         * config/riscv/arch-canonicalize: New.
> >>>>         * config.gcc (riscv*-*-*): Canonicalize --with-arch.
> >>>
> >>>
> >>> Looks OK to me.
> >
> > that breaks the bootstrap if python is not available. The python command might
> > not be available, so please check for python3, python, or python2.
>
> same for config/riscv/arch-canonicalize
diff mbox series

Patch

diff --git a/gcc/config.gcc b/gcc/config.gcc
index 4808b698f3a..c348596b1ac 100644
--- a/gcc/config.gcc
+++ b/gcc/config.gcc
@@ -4615,6 +4615,7 @@  case "${target}" in
 			exit 1
 			;;
 		esac
+		with_arch=`${srcdir}/config/riscv/arch-canonicalize ${with_arch}`
 		tm_defines="${tm_defines} TARGET_RISCV_DEFAULT_ARCH=${with_arch}"
 
 		# Make sure --with-abi is valid.  If it was not specified,
diff --git a/gcc/config/riscv/arch-canonicalize b/gcc/config/riscv/arch-canonicalize
new file mode 100755
index 00000000000..2b4289e320d
--- /dev/null
+++ b/gcc/config/riscv/arch-canonicalize
@@ -0,0 +1,102 @@ 
+#!/usr/bin/env python
+
+# Tool for canonical RISC-V architecture string.
+# Copyright (C) 2011-2020 Free Software Foundation, Inc.
+# Contributed by Andrew Waterman (andrew@sifive.com).
+#
+# This file is part of GCC.
+#
+# GCC is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3, or (at your option)
+# any later version.
+#
+# GCC is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with GCC; see the file COPYING3.  If not see
+# <http://www.gnu.org/licenses/>.
+
+
+from __future__ import print_function
+import sys
+import collections
+import itertools
+from functools import reduce
+
+
+CANONICAL_ORDER = "mafdgqlcbjtpvn"
+LONG_EXT_PREFIXES = ['z', 's', 'h', 'x']
+
+#
+# IMPLIED_EXT(ext) -> implied extension list.
+#
+IMPLIED_EXT = {
+  "d" : ["f"],
+}
+
+def arch_canonicalize(arch):
+  # TODO: Support extension version.
+  new_arch = ""
+  if arch[:5] in ['rv32e', 'rv32i', 'rv32g', 'rv64i', 'rv64g']:
+    # TODO: We should expand g to imad_zifencei once we support newer spec.
+    new_arch = arch[:5].replace("g", "imafd")
+  else:
+    raise Exception("Unexpected arch: `%s`" % arch[:5])
+
+  # Find any Z, S, H or X
+  long_ext_prefixes_idx = map(lambda x: arch.find(x), LONG_EXT_PREFIXES)
+
+  # Filter out any non-existent index.
+  long_ext_prefixes_idx = list(filter(lambda x: x != -1, long_ext_prefixes_idx))
+  if long_ext_prefixes_idx:
+    first_long_ext_idx = min(long_ext_prefixes_idx)
+    long_exts = arch[first_long_ext_idx:].split("_")
+    std_exts = list(arch[5:first_long_ext_idx])
+  else:
+    long_exts = []
+    std_exts = list(arch[5:])
+
+  #
+  # Handle implied extensions.
+  #
+  for ext in std_exts + long_exts:
+    if ext in IMPLIED_EXT:
+      implied_exts = IMPLIED_EXT[ext]
+      for implied_ext in implied_exts:
+        if implied_ext not in std_exts + long_exts:
+          long_exts.append(implied_ext)
+
+  # Single letter extension might appear in the long_exts list,
+  # becasue we just append extensions list to the arch string.
+  std_exts += list(filter(lambda x:len(x) == 1, long_exts))
+
+  # Multi-letter extension must be in lexicographic order.
+  long_exts = list(sorted(filter(lambda x:len(x) != 1, long_exts)))
+
+  # Put extensions in canonical order.
+  for ext in CANONICAL_ORDER:
+    if ext in std_exts:
+      new_arch += ext
+
+  # Check every extension is processed.
+  for ext in std_exts:
+    if ext == '_':
+      continue
+    if ext not in CANONICAL_ORDER:
+      raise Exception("Unsupported extension `%s`" % ext)
+
+  # Concat rest of the multi-char extensions.
+  if long_exts:
+    new_arch += "_" + "_".join(long_exts)
+  return new_arch
+
+if len(sys.argv) < 2:
+  print ("Usage: %s <arch_str> [<arch_str>*]" % sys.argv)
+  sys.exit(1)
+
+for arg in sys.argv[1:]:
+  print (arch_canonicalize(arg))
diff --git a/gcc/config/riscv/multilib-generator b/gcc/config/riscv/multilib-generator
index 0d9ebcb321f..53c51dfa53f 100755
--- a/gcc/config/riscv/multilib-generator
+++ b/gcc/config/riscv/multilib-generator
@@ -35,9 +35,11 @@ 
 
 from __future__ import print_function
 import sys
+import os
 import collections
 import itertools
 from functools import reduce
+import subprocess
 
 #
 # TODO: Add test for this script.
@@ -48,82 +50,13 @@  abis = collections.OrderedDict()
 required = []
 reuse = []
 
-canonical_order = "mafdgqlcbjtpvn"
-LONG_EXT_PREFIXES = ['z', 's', 'h', 'x']
-
-#
-# IMPLIED_EXT(ext) -> implied extension list.
-#
-IMPLIED_EXT = {
-  "d" : ["f"],
-}
-
 def arch_canonicalize(arch):
-  # TODO: Support extension version.
-  new_arch = ""
-  if arch[:5] in ['rv32e', 'rv32i', 'rv32g', 'rv64i', 'rv64g']:
-    # TODO: We should expand g to imad_zifencei once we support newer spec.
-    new_arch = arch[:5].replace("g", "imafd")
-  else:
-    raise Exception("Unexpected arch: `%s`" % arch[:5])
-
-  # Find any Z, S, H or X
-  long_ext_prefixes_idx = map(lambda x: arch.find(x), LONG_EXT_PREFIXES)
-
-  # Filter out any non-existent index.
-  long_ext_prefixes_idx = list(filter(lambda x: x != -1, long_ext_prefixes_idx))
-  if long_ext_prefixes_idx:
-    first_long_ext_idx = min(long_ext_prefixes_idx)
-    long_exts = arch[first_long_ext_idx:].split("_")
-    std_exts = list(arch[5:first_long_ext_idx])
-  else:
-    long_exts = []
-    std_exts = list(arch[5:])
-
-  #
-  # Handle implied extensions.
-  #
-  for ext in std_exts + long_exts:
-    if ext in IMPLIED_EXT:
-      implied_exts = IMPLIED_EXT[ext]
-      for implied_ext in implied_exts:
-        if implied_ext not in std_exts + long_exts:
-          long_exts.append(implied_ext)
-
-  # Single letter extension might appear in the long_exts list,
-  # becasue we just append extensions list to the arch string.
-  std_exts += list(filter(lambda x:len(x) == 1, long_exts))
-
-  # Multi-letter extension must be in lexicographic order.
-  long_exts = list(sorted(filter(lambda x:len(x) != 1, long_exts)))
-
-  # Put extensions in canonical order.
-  for ext in canonical_order:
-    if ext in std_exts:
-      new_arch += ext
-
-  # Check every extension is processed.
-  for ext in std_exts:
-    if ext == '_':
-      continue
-    if ext not in canonical_order:
-      raise Exception("Unsupported extension `%s`" % ext)
-
-  # Concat rest of the multi-char extensions.
-  if long_exts:
-    new_arch += "_" + "_".join(long_exts)
-  return new_arch
-
-#
-# add underline for each multi-char extensions.
-# e.g. ["a", "zfh"] -> ["a", "_zfh"]
-#
-def add_underline_prefix(ext):
-  for long_ext_prefix in LONG_EXT_PREFIXES:
-    if ext.startswith(long_ext_prefix):
-      return "_" + ext
-
-  return ext
+  this_file = os.path.abspath(os.path.join( __file__))
+  arch_can_script = \
+    os.path.join(os.path.dirname(this_file), "arch-canonicalize")
+  proc = subprocess.Popen([arch_can_script, arch], stdout=subprocess.PIPE)
+  out, err = proc.communicate()
+  return out.strip()
 
 #
 # Handle expansion operation.