*** ARC port for review ***

2021-04-05 Thread cupertinomiranda
Hello everyone,

Here is a long due refresh of ARC port patches.

The reason for taking so long was that I did a big refreshement to the
code due to the adition of the soon to release ARCv3 (64 bit) architecture.
In order to avoid further big changes in the original patches we decided to
delay the submittion and include all the changes done to support ARCv3.

Special thanks and apologies for Richard Henderson that has (long time ago)
given his feedback which unfortunately took us a while to address and improve.

Requests addressed:
 - Long list of fixes/improvements by Richard.
 - Generalization of the code to support both 32 and 64 bit targets.

Pending to be addressed:
 - Refactor of the decoder code which currently depends on string
   matching of the mnemonic.

In order to simplify the review process, we have separated the patches 
for ARCv3 from the previous emailed ARCv2 ones. Being the patches from
1 to 16 for ARCv2 and 17 to 27 for ARCv3.

Best regards,
Cupertino Miranda



___
linux-snps-arc mailing list
linux-snps-arc@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-snps-arc


[PATCH 01/27] arc: Add initial core cpu files

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

Signed-off-by: Cupertino Miranda 
---
 target/arc/arc-common.h |  54 +
 target/arc/cpu-param.h  |  32 +++
 target/arc/cpu-qom.h|  52 +
 target/arc/cpu.c| 472 
 target/arc/cpu.h| 445 +
 target/arc/meson.build  |  21 ++
 6 files changed, 1076 insertions(+)
 create mode 100644 target/arc/arc-common.h
 create mode 100644 target/arc/cpu-param.h
 create mode 100644 target/arc/cpu-qom.h
 create mode 100644 target/arc/cpu.c
 create mode 100644 target/arc/cpu.h
 create mode 100644 target/arc/meson.build

diff --git a/target/arc/arc-common.h b/target/arc/arc-common.h
new file mode 100644
index 00..ff9f97d457
--- /dev/null
+++ b/target/arc/arc-common.h
@@ -0,0 +1,54 @@
+/*
+ *  Common header file to be used by cpu and disassembler.
+ *  Copyright (C) 2017 Free Software Foundation, Inc.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with GAS or GDB; see the file COPYING3. If not, write to
+ *  the Free Software Foundation, 51 Franklin Street - Fifth Floor, Boston,
+ *  MA 02110-1301, USA.
+ */
+
+#ifndef ARC_COMMON_H
+#define ARC_COMMON_H
+
+
+/* CPU combi. */
+#define ARC_OPCODE_ARCALL  (ARC_OPCODE_ARC600 | ARC_OPCODE_ARC700   \
+| ARC_OPCODE_ARCv2EM | ARC_OPCODE_ARCv2HS)
+#define ARC_OPCODE_ARCFPX  (ARC_OPCODE_ARC700 | ARC_OPCODE_ARCv2EM)
+#define ARC_OPCODE_ARCV1   (ARC_OPCODE_ARC700 | ARC_OPCODE_ARC600)
+#define ARC_OPCODE_ARCV2   (ARC_OPCODE_ARCv2EM | ARC_OPCODE_ARCv2HS)
+#define ARC_OPCODE_ARCMPY6E  (ARC_OPCODE_ARC700 | ARC_OPCODE_ARCV2)
+
+
+enum arc_cpu_family {
+ARC_OPCODE_NONE= 0,
+ARC_OPCODE_DEFAULT = 1 << 0,
+ARC_OPCODE_ARC600  = 1 << 1,
+ARC_OPCODE_ARC700  = 1 << 2,
+ARC_OPCODE_ARCv2EM = 1 << 3,
+ARC_OPCODE_ARCv2HS = 1 << 4
+};
+
+typedef struct {
+uint32_t value;
+uint32_t type;
+} operand_t;
+
+typedef struct {
+uint32_t class;
+uint32_t limm;
+uint8_t len;
+bool limm_p;
+operand_t operands[3];
+uint8_t n_ops;
+uint8_t cc;
+uint8_t aa;
+uint8_t zz;
+bool d;
+bool f;
+bool di;
+bool x;
+} insn_t;
+
+#endif
diff --git a/target/arc/cpu-param.h b/target/arc/cpu-param.h
new file mode 100644
index 00..512f4c8b75
--- /dev/null
+++ b/target/arc/cpu-param.h
@@ -0,0 +1,32 @@
+/*
+ * ARC cpu parameters for qemu.
+ *
+ * Copyright (c) 2020 Synopsys Inc.
+ * Contributed by Shahab Vahedi 
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2 or later, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope 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
+ * this program.  If not, see .
+ */
+
+#ifndef ARC_CPU_PARAM_H
+#define ARC_CPU_PARAM_H 1
+
+#define TARGET_LONG_BITS32
+#define TARGET_PAGE_BITS13
+#define TARGET_PHYS_ADDR_SPACE_BITS 32
+#define TARGET_VIRT_ADDR_SPACE_BITS 32
+#define NB_MMU_MODES2
+
+#endif
+
+/*-*-indent-tabs-mode:nil;tab-width:4;indent-line-function:'insert-tab'-*-*/
+/* vim: set ts=4 sw=4 et: */
diff --git a/target/arc/cpu-qom.h b/target/arc/cpu-qom.h
new file mode 100644
index 00..ee60db158d
--- /dev/null
+++ b/target/arc/cpu-qom.h
@@ -0,0 +1,52 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synopsys Inc.
+ * Contributed by Cupertino Miranda 
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms and conditions of the GNU General Public License,
+ * version 2 or later, as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope 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
+ * this program.  If not, see .
+ */
+
+#ifndef QEMU_ARC_CPU_QOM_H
+#define QEMU_ARC_CPU_QOM_H
+
+#include "hw/core/cpu.h"
+
+#define TYPE_ARC_CPU"arc-cpu"
+
+#define ARC_CPU_CLASS(klass)\
+OBJECT_CLASS_CHECK(ARCCPUClass, (klass), TYPE_ARC_CPU)
+#define ARC_CPU(obj)\
+OBJECT_CHECK(ARCCPU, (obj), TYPE_ARC_CPU)
+#define ARC_CPU_GET_CLASS(obj)  \
+OBJECT_GET_CLASS(ARCCPUClass, (obj), TYPE_ARC_CPU)
+
+/*
+ *  ARCCPUClass:
+ *  @parent_realize: The parent class' realize handler.
+ *  @parent_reset: The parent class' r

[PATCH 02/27] arc: Decoder code

2021-04-05 Thread cupertinomiranda
From: Claudiu Zissulescu 

The decoder and the disassembler inspired by ARC GNU binutils.

Signed-off-by: Claudiu Zissulescu 
---
 disas/arc.c |  422 +
 target/arc/decoder.c| 1297 +++
 target/arc/decoder.h|  351 +++
 target/arc/flags.def|   85 +++
 target/arc/operands.def |  123 
 5 files changed, 2278 insertions(+)
 create mode 100644 disas/arc.c
 create mode 100644 target/arc/decoder.c
 create mode 100644 target/arc/decoder.h
 create mode 100644 target/arc/flags.def
 create mode 100644 target/arc/operands.def

diff --git a/disas/arc.c b/disas/arc.c
new file mode 100644
index 00..f8b2e31be9
--- /dev/null
+++ b/disas/arc.c
@@ -0,0 +1,422 @@
+/*
+ * Disassembler code for ARC.
+ *
+ * Copyright 2020 Synopsys Inc.
+ * Contributed by Claudiu Zissulescu 
+ *
+ * QEMU ARCv2 Disassembler.
+ *
+ * This program 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 2, or (at your option) any later
+ * version.
+ *
+ * This program 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 this program; if not, see .
+ */
+
+#include "qemu/osdep.h"
+#include "qemu-common.h"
+#include "disas/dis-asm.h"
+#include "target/arc/arc-common.h"
+
+#include "target/arc/decoder.h"
+
+#define ARRANGE_ENDIAN(info, buf)   \
+(info->endian == BFD_ENDIAN_LITTLE ? bfd_getm32(bfd_getl32(buf))\
+ : bfd_getb32(buf))
+
+/*
+ * Helper function to convert middle-endian data to something more
+ * meaningful.
+ */
+
+static bfd_vma bfd_getm32(unsigned int data)
+{
+bfd_vma value = 0;
+
+value  = (data & 0x) << 16;
+value |= (data & 0x) >> 16;
+return value;
+}
+
+/* Helper for printing instruction flags. */
+
+bool special_flag_p(const char *opname, const char *flgname);
+bool special_flag_p(const char *opname, const char *flgname)
+{
+const struct arc_flag_special *flg_spec;
+unsigned i, j, flgidx;
+
+for (i = 0; i < arc_num_flag_special; ++i) {
+flg_spec = &arc_flag_special_cases[i];
+
+if (strcmp(opname, flg_spec->name) != 0) {
+continue;
+}
+
+/* Found potential special case instruction. */
+for (j = 0; ; ++j) {
+flgidx = flg_spec->flags[j];
+if (flgidx == 0) {
+break; /* End of the array. */
+}
+
+if (strcmp(flgname, arc_flag_operands[flgidx].name) == 0) {
+return TRUE;
+}
+}
+}
+return FALSE;
+}
+
+/* Print instruction flags. */
+
+static void print_flags(const struct arc_opcode *opcode,
+uint64_t insn,
+struct disassemble_info *info)
+{
+const unsigned char *flgidx;
+unsigned int value;
+
+/* Now extract and print the flags. */
+for (flgidx = opcode->flags; *flgidx; flgidx++) {
+/* Get a valid flag class. */
+const struct arc_flag_class *cl_flags = &arc_flag_classes[*flgidx];
+const unsigned *flgopridx;
+
+/* Check first the extensions. Not supported yet. */
+if (cl_flags->flag_class & F_CLASS_EXTEND) {
+value = insn & 0x1F;
+}
+
+for (flgopridx = cl_flags->flags; *flgopridx; ++flgopridx) {
+const struct arc_flag_operand *flg_operand =
+&arc_flag_operands[*flgopridx];
+
+/* Implicit flags are only used for the insn decoder. */
+if (cl_flags->flag_class & F_CLASS_IMPLICIT) {
+continue;
+}
+
+if (!flg_operand->favail) {
+continue;
+}
+
+value = (insn >> flg_operand->shift) &
+((1 << flg_operand->bits) - 1);
+if (value == flg_operand->code) {
+/* FIXME!: print correctly nt/t flag. */
+if (!special_flag_p(opcode->name, flg_operand->name)) {
+(*info->fprintf_func)(info->stream, ".");
+}
+(*info->fprintf_func)(info->stream, "%s", flg_operand->name);
+}
+}
+}
+}
+
+/*
+ * When dealing with auxiliary registers, output the proper name if we
+ * have it.
+ */
+extern const char *get_auxreg(const struct arc_opcode *opcode,
+  int value,
+  unsigned isa_mask);
+
+/* Print the operands of an instruction. */
+
+static void print_operands(const struct arc_opcode *opcode,
+   bfd_vma memaddr,
+   uint64_t

[PATCH 08/27] arc: Add BCR and AUX registers implementation

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

Add the infrastructure to define build configuration (BCR) and auxiliary
registers allowing independent modules (MMU, MPU, etc.) to use and extend
them.

Signed-off-by: Cupertino Miranda 
---
 target/arc/cache.c | 182 +
 target/arc/cache.h |  36 +++
 target/arc/regs-detail.def | 540 +
 target/arc/regs-impl.c | 181 +
 target/arc/regs.c  | 183 +
 target/arc/regs.def| 412 
 target/arc/regs.h  | 139 ++
 7 files changed, 1673 insertions(+)
 create mode 100644 target/arc/cache.c
 create mode 100644 target/arc/cache.h
 create mode 100644 target/arc/regs-detail.def
 create mode 100644 target/arc/regs-impl.c
 create mode 100644 target/arc/regs.c
 create mode 100644 target/arc/regs.def
 create mode 100644 target/arc/regs.h

diff --git a/target/arc/cache.c b/target/arc/cache.c
new file mode 100644
index 00..86fae84ccb
--- /dev/null
+++ b/target/arc/cache.c
@@ -0,0 +1,182 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synppsys Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "hw/hw.h"
+#include "cpu.h"
+#include "target/arc/regs.h"
+#include "target/arc/cache.h"
+
+void arc_cache_aux_set(const struct arc_aux_reg_detail *aux_reg_detail,
+   target_ulong val, void *data)
+{
+
+CPUARCState *env = (CPUARCState *) data;
+struct arc_cache *cache = &env->cache;
+
+switch (aux_reg_detail->id) {
+case AUX_ID_ic_ivic:
+case AUX_ID_ic_ivil:
+case AUX_ID_dc_ivdc:
+case AUX_ID_dc_ivdl:
+case AUX_ID_dc_flsh:
+case AUX_ID_dc_fldl:
+case AUX_ID_dc_startr:
+   /* Do nothing as we don't simulate cache memories */
+   break;
+
+case AUX_ID_ic_ctrl:
+cache->ic_disabled = val & 1;
+break;
+
+case AUX_ID_ic_ivir:
+cache->ic_ivir = val & 0xff00;
+break;
+
+case AUX_ID_ic_endr:
+cache->ic_endr = val & 0xff00;
+break;
+
+case AUX_ID_ic_ptag:
+cache->ic_ptag = val;
+break;
+
+case AUX_ID_ic_ptag_hi:
+cache->ic_ptag_hi = val & 0xff;
+break;
+
+/*
+ * Description of the register content in order:
+ *   DC - Disable Cache: Enables/Disables the cache: 0 - Enabled, 1 - Disabled
+ *   IM - Invalidate Mode: Selects the invalidate type
+ */
+case AUX_ID_dc_ctrl:
+cache->dc_disabled = val & 1; /* DC */
+cache->dc_inv_mode = (val >> 6) & 1; /* IM */
+break;
+
+case AUX_ID_dc_endr:
+cache->dc_endr = val & 0xff00;
+break;
+
+case AUX_ID_dc_ptag_hi:
+cache->dc_ptag_hi = val & 0xff;
+break;
+
+default:
+hw_error("%s@%d: Attempt to write read-only register 0x%02x!\n",
+ __func__, __LINE__, (unsigned int)aux_reg_detail->id);
+break;
+}
+
+return;
+}
+
+target_ulong arc_cache_aux_get(const struct arc_aux_reg_detail *aux_reg_detail,
+   void *data)
+{
+CPUARCState *env = (CPUARCState *) data;
+struct arc_cache *cache = &env->cache;
+uint32_t reg = 0;
+
+switch (aux_reg_detail->id) {
+/*
+ * Description of the register content in order.
+ * Layout:   -DFF  
+ *   D - indicates that IC is disabled on reset
+ *   FL - Feature level: 10b - line lock, invalidate, advanced debug features
+ *   BSize - indicates the cache block size in bytes: 0011b - 64 bytes
+ *   Cache capacity: 0111b - 64 Kbytes
+ *   Cache Associativiy: 0010b - Four-way set associative
+ *   Version number: 4 - ARCv2
+ */
+case AUX_ID_i_cache_build:
+reg = (0 << 22) | /* D */
+  (2 << 20) | /* FL */
+  (3 << 16) | /* BBSixe*/
+  (7 << 12) | /* Cache capacity */
+  (2 << 8)  | /* Cache Associativiy */
+  (4 << 0);   /* Version Number */
+break;
+
+case AUX_ID_ic_ctrl:
+reg = cache->ic_disabled & 1;
+break;
+
+case AUX_ID_ic_ivir:
+reg = cache->ic_ivir;
+break;
+
+case AUX_ID_ic_endr:
+reg = cache->ic_endr;
+break;
+
+case AUX_ID_ic_ptag:
+reg = cache->ic_ptag;
+break;
+
+case AUX_ID_ic_ptag_hi:
+reg = cac

[PATCH 06/27] arc: semfunc.c tcg code generator.

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

TCG generator scripts for semfunc.c file.

Signed-off-by: Cupertino Miranda 
---
 target/arc/semfunc_generator/Gemfile  |   3 +
 target/arc/semfunc_generator/README   |  35 ++
 .../classes/CreateInternalVars.rb | 117 
 .../classes/DecomposeExpressions.rb   |  45 ++
 .../classes/IdentifyQEmuStaticInferedParts.rb |  91 +++
 .../semfunc_generator/classes/QEmuCompiler.rb |  15 +
 .../classes/QEmuTranslator.rb | 269 +
 .../classes/SemanticFunctionAST.rb| 466 +++
 .../classes/SpaghettiCodePass.rb  |  55 ++
 .../classes/SpaghettiCodePass1.rb |  66 +++
 .../semfunc_generator/classes/UnfoldCode.rb   | 305 ++
 target/arc/semfunc_generator/init.rb  |  15 +
 .../arc/semfunc_generator/modules/Compiler.rb |  42 ++
 .../modules/ConstantTables.rb |  57 ++
 target/arc/semfunc_generator/modules/Pass.rb  |  11 +
 .../SemanticFunctionASTBlockOperators.rb  | 145 +
 .../modules/SemanticFunctionASTFactory.rb |  55 ++
 .../semfunc_generator/modules/Translator.rb   | 102 
 .../modules/TranslatorAST.rb  |  80 +++
 .../modules/TranslatorFinal.rb| 103 
 .../parsers/SemanticFunctionParser.tab.rb | 553 ++
 .../parsers/SemanticFunctionParser.y  | 126 
 .../semfunc_generator/regenerate_semfunc.rb   | 245 
 23 files changed, 3001 insertions(+)
 create mode 100644 target/arc/semfunc_generator/Gemfile
 create mode 100644 target/arc/semfunc_generator/README
 create mode 100644 target/arc/semfunc_generator/classes/CreateInternalVars.rb
 create mode 100644 target/arc/semfunc_generator/classes/DecomposeExpressions.rb
 create mode 100644 
target/arc/semfunc_generator/classes/IdentifyQEmuStaticInferedParts.rb
 create mode 100644 target/arc/semfunc_generator/classes/QEmuCompiler.rb
 create mode 100644 target/arc/semfunc_generator/classes/QEmuTranslator.rb
 create mode 100644 target/arc/semfunc_generator/classes/SemanticFunctionAST.rb
 create mode 100644 target/arc/semfunc_generator/classes/SpaghettiCodePass.rb
 create mode 100644 target/arc/semfunc_generator/classes/SpaghettiCodePass1.rb
 create mode 100644 target/arc/semfunc_generator/classes/UnfoldCode.rb
 create mode 100644 target/arc/semfunc_generator/init.rb
 create mode 100644 target/arc/semfunc_generator/modules/Compiler.rb
 create mode 100644 target/arc/semfunc_generator/modules/ConstantTables.rb
 create mode 100644 target/arc/semfunc_generator/modules/Pass.rb
 create mode 100644 
target/arc/semfunc_generator/modules/SemanticFunctionASTBlockOperators.rb
 create mode 100644 
target/arc/semfunc_generator/modules/SemanticFunctionASTFactory.rb
 create mode 100644 target/arc/semfunc_generator/modules/Translator.rb
 create mode 100644 target/arc/semfunc_generator/modules/TranslatorAST.rb
 create mode 100644 target/arc/semfunc_generator/modules/TranslatorFinal.rb
 create mode 100644 
target/arc/semfunc_generator/parsers/SemanticFunctionParser.tab.rb
 create mode 100644 
target/arc/semfunc_generator/parsers/SemanticFunctionParser.y
 create mode 100644 target/arc/semfunc_generator/regenerate_semfunc.rb

diff --git a/target/arc/semfunc_generator/Gemfile 
b/target/arc/semfunc_generator/Gemfile
new file mode 100644
index 00..ad695b4d11
--- /dev/null
+++ b/target/arc/semfunc_generator/Gemfile
@@ -0,0 +1,3 @@
+source 'http://rubygems.org'
+
+gem 'racc'
diff --git a/target/arc/semfunc_generator/README 
b/target/arc/semfunc_generator/README
new file mode 100644
index 00..965e79b894
--- /dev/null
+++ b/target/arc/semfunc_generator/README
@@ -0,0 +1,35 @@
+Helper file for ARC instruction traslation functions.
+
+The code generator was implemented using ruby language.
+In order to change the content of semfunc.c file these scripts should be used.
+
+Ruby instalation process:
+
+The recommended way to obtain a compatible ruby is to install it in a user
+local directory using RVM.
+Instructions to install RVM can be found in https://rvm.io/.
+
+Using RVM one can install Ruby interpreter executing the following
+steps/commands.
+
+Install Ruby version 2.6:
+  # rvm install ruby-2.6
+Set ruby version 2.6 as current in use.
+  # rvm use 2.6
+Create an isolated environment for the required ruby dependencies.
+  # rvm gemset create arc_generator
+Install bundler tool
+  # gem install bundler
+Bundle tool reads the Gemfile file and installs project dependencies.
+  # cd ${QEMU_SOURCE}/target/arc/semfunc_generator & bundle install
+
+
+In order to regenerate the semfunc.c file, please execute the following 
command.
+  # ruby regenerate_semfunc.rb > ../semfunc.c
+
+By default the tool reads the semfunc.c file and prints the new content for
+the same file.
+The information of what is generated is presented as comment in the file.
+In order to change the functionality of those functions one should change the
+"pseudo code" in the comments, which 

[PATCH 05/27] arc: TCG instruction generator and hand-definitions

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

Add the most generic parts of TCG constructions. It contains the
basic infrastructure for fundamental ARC features, such as
ZOL (zero overhead loops) and delay-slots.
Also includes hand crafted TCG for more intricate instructions, such
as vector instructions.

Signed-off-by: Shahab Vahedi 
---
 target/arc/translate.c | 1530 
 target/arc/translate.h |  168 +
 2 files changed, 1698 insertions(+)
 create mode 100644 target/arc/translate.c
 create mode 100644 target/arc/translate.h

diff --git a/target/arc/translate.c b/target/arc/translate.c
new file mode 100644
index 00..1712fcc9c3
--- /dev/null
+++ b/target/arc/translate.c
@@ -0,0 +1,1530 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synppsys Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "translate.h"
+#include "qemu/qemu-print.h"
+#include "tcg/tcg-op-gvec.h"
+#include "target/arc/semfunc.h"
+#include "target/arc/arc-common.h"
+
+/* Globals */
+TCGvcpu_S1f;
+TCGvcpu_S2f;
+TCGvcpu_CSf;
+
+TCGvcpu_Ef;
+TCGvcpu_IEf;
+TCGvcpu_Vf;
+TCGvcpu_Cf;
+TCGvcpu_Nf;
+TCGvcpu_Zf;
+TCGvcpu_DEf;
+
+TCGvcpu_is_delay_slot_instruction;
+
+TCGvcpu_l1_Ef;
+TCGvcpu_l1_Vf;
+TCGvcpu_l1_Cf;
+TCGvcpu_l1_Nf;
+TCGvcpu_l1_Zf;
+TCGvcpu_l1_DEf;
+
+TCGvcpu_l2_Ef;
+TCGvcpu_l2_Vf;
+TCGvcpu_l2_Cf;
+TCGvcpu_l2_Nf;
+TCGvcpu_l2_Zf;
+TCGvcpu_l2_DEf;
+
+TCGvcpu_er_Ef;
+TCGvcpu_er_Vf;
+TCGvcpu_er_Cf;
+TCGvcpu_er_Nf;
+TCGvcpu_er_Zf;
+TCGvcpu_er_DEf;
+
+TCGvcpu_eret;
+TCGvcpu_erbta;
+TCGvcpu_ecr;
+TCGvcpu_efa;
+
+TCGvcpu_bta;
+TCGvcpu_bta_l1;
+TCGvcpu_bta_l2;
+
+TCGvcpu_pc;
+/* replaced by AUX_REG array */
+TCGvcpu_lps;
+TCGvcpu_lpe;
+
+TCGvcpu_r[64];
+
+TCGvcpu_intvec;
+
+TCGvcpu_lock_lf_var;
+
+/* NOTE: Pseudo register required for comparison with lp_end */
+TCGvcpu_npc;
+
+/* Macros */
+
+#include "exec/gen-icount.h"
+#define REG(x)  (cpu_r[x])
+
+/* macro used to fix middle-endianess. */
+#define ARRANGE_ENDIAN(endianess, buf)  \
+((endianess) ? ror32(buf, 16) : bswap32(buf))
+
+static inline bool use_goto_tb(const DisasContext *dc, target_ulong dest)
+{
+if (unlikely(dc->base.singlestep_enabled)) {
+return false;
+}
+#ifndef CONFIG_USER_ONLY
+return (dc->base.tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK);
+#else
+return true;
+#endif
+}
+
+void gen_goto_tb(const DisasContext *ctx, int n, TCGv dest)
+{
+tcg_gen_mov_tl(cpu_pc, dest);
+tcg_gen_andi_tl(cpu_pcl, dest, ~((target_ulong) 3));
+if (ctx->base.singlestep_enabled) {
+gen_helper_debug(cpu_env);
+} else {
+tcg_gen_exit_tb(NULL, 0);
+}
+}
+
+static void gen_gotoi_tb(const DisasContext *ctx, int n, target_ulong dest)
+{
+if (use_goto_tb(ctx, dest)) {
+tcg_gen_goto_tb(n);
+tcg_gen_movi_tl(cpu_pc, dest);
+tcg_gen_movi_tl(cpu_pcl, dest & (~((target_ulong) 3)));
+tcg_gen_exit_tb(ctx->base.tb, n);
+} else {
+tcg_gen_movi_tl(cpu_pc, dest);
+tcg_gen_movi_tl(cpu_pcl, dest & (~((target_ulong) 3)));
+if (ctx->base.singlestep_enabled) {
+gen_helper_debug(cpu_env);
+}
+tcg_gen_exit_tb(NULL, 0);
+}
+}
+
+void arc_translate_init(void)
+{
+int i;
+#define ARC_REG_OFFS(x) offsetof(CPUARCState, x)
+
+#define NEW_ARC_REG(TCGV, FIELD) \
+{ &TCGV, offsetof(CPUARCState, FIELD), #FIELD },
+
+static const struct { TCGv *ptr; int off; const char *name; } r32[] = {
+NEW_ARC_REG(cpu_S1f, macmod.S1)
+NEW_ARC_REG(cpu_S2f, macmod.S2)
+NEW_ARC_REG(cpu_CSf, macmod.CS)
+
+NEW_ARC_REG(cpu_Zf, stat.Zf)
+NEW_ARC_REG(cpu_Nf, stat.Nf)
+NEW_ARC_REG(cpu_Cf, stat.Cf)
+NEW_ARC_REG(cpu_Vf, stat.Vf)
+NEW_ARC_REG(cpu_DEf, stat.DEf)
+NEW_ARC_REG(cpu_Ef, stat.Ef)
+NEW_ARC_REG(cpu_IEf, stat.IEf)
+
+NEW_ARC_REG(cpu_l1_Zf, stat_l1.Zf)
+NEW_ARC_REG(cpu_l1_Nf, stat_l1.Nf)
+NEW_ARC_REG(cpu_l1_Cf, stat_l1.Cf)
+NEW_ARC_REG(cpu_l1_Vf, stat_l1.Vf)
+NEW_ARC_REG(cpu_l1_DEf, stat_l1.DEf)
+
+NEW_ARC_REG(cpu_er_Zf, stat_er.Zf)
+NEW_ARC_RE

[PATCH 04/27] arc: TCG and decoder glue code and helpers

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

Signed-off-by: Cupertino Miranda 
---
 target/arc/extra_mapping.def   |  63 +
 target/arc/helper.c| 281 +++
 target/arc/helper.h|  39 
 target/arc/op_helper.c | 406 +
 target/arc/semfunc_mapping.def | 321 ++
 5 files changed, 1110 insertions(+)
 create mode 100644 target/arc/extra_mapping.def
 create mode 100644 target/arc/helper.c
 create mode 100644 target/arc/helper.h
 create mode 100644 target/arc/op_helper.c
 create mode 100644 target/arc/semfunc_mapping.def

diff --git a/target/arc/extra_mapping.def b/target/arc/extra_mapping.def
new file mode 100644
index 00..50517f058e
--- /dev/null
+++ b/target/arc/extra_mapping.def
@@ -0,0 +1,63 @@
+/*
+ * QEMU ARC EXTRA MAPPING
+ *
+ * Copyright (c) 2020 Synopsys Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+SEMANTIC_FUNCTION(ENTER, 0)
+SEMANTIC_FUNCTION(LEAVE, 0)
+MAPPING(enter_s, ENTER, 0)
+MAPPING(leave_s, LEAVE, 0)
+
+SEMANTIC_FUNCTION(SR, 2)
+SEMANTIC_FUNCTION(SRL, 2)
+SEMANTIC_FUNCTION(SYNC, 0)
+MAPPING(sr, SR, 2, 1, 0)
+MAPPING(srl, SRL, 2, 1, 0)
+MAPPING(sync, SYNC, 0)
+
+SEMANTIC_FUNCTION(TRAP, 1)
+SEMANTIC_FUNCTION(RTIE, 0)
+SEMANTIC_FUNCTION(SLEEP, 1)
+MAPPING(trap_s, TRAP, 1, 0)
+MAPPING(rtie, RTIE, 0)
+MAPPING(sleep, SLEEP, 1, 0)
+
+SEMANTIC_FUNCTION(SWI, 1)
+CONSTANT(SWI, swi, 0, 0)
+MAPPING(swi, SWI, 1, 0)
+CONSTANT(SWI, swi_s, 0, 0)
+MAPPING(swi_s, SWI, 1, 0)
+
+SEMANTIC_FUNCTION(VADD2, 3)
+SEMANTIC_FUNCTION(VADD2H, 3)
+SEMANTIC_FUNCTION(VADD4H, 3)
+SEMANTIC_FUNCTION(VSUB2, 3)
+SEMANTIC_FUNCTION(VSUB2H, 3)
+SEMANTIC_FUNCTION(VSUB4H, 3)
+SEMANTIC_FUNCTION(MPYD, 3)
+SEMANTIC_FUNCTION(MPYDU, 3)
+
+
+MAPPING(vadd2, VADD2, 3, 0, 1, 2)
+MAPPING(vadd2h, VADD2H, 3, 0, 1, 2)
+MAPPING(vadd4h, VADD4H, 3, 0, 1, 2)
+MAPPING(vsub2, VSUB2, 3, 0, 1, 2)
+MAPPING(vsub2h, VSUB2H, 3, 0, 1, 2)
+MAPPING(vsub4h, VSUB4H, 3, 0, 1, 2)
+MAPPING(mpyd, MPYD, 3, 0, 1, 2)
+MAPPING(mpydu, MPYDU, 3, 0, 1, 2)
diff --git a/target/arc/helper.c b/target/arc/helper.c
new file mode 100644
index 00..e11d21d576
--- /dev/null
+++ b/target/arc/helper.c
@@ -0,0 +1,281 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synppsys Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+
+#include "cpu.h"
+#include "hw/irq.h"
+#include "include/hw/sysbus.h"
+#include "include/sysemu/sysemu.h"
+#include "qemu/qemu-print.h"
+#include "exec/exec-all.h"
+#include "exec/cpu_ldst.h"
+#include "qemu/host-utils.h"
+#include "exec/helper-proto.h"
+#include "irq.h"
+
+void arc_cpu_do_interrupt(CPUState *cs)
+{
+ARCCPU  *cpu= ARC_CPU(cs);
+CPUARCState *env= &cpu->env;
+uint32_t offset = 0;
+uint32_t vectno;
+const char  *name;
+MemTxResult txres;
+
+/*
+ * NOTE: Special LP_END exception. Immediately return code execution to
+ * lp_start.
+ * Now also used for delayslot MissI cases.
+ * This special exception should not execute any of the exception
+ * handling code. Instead it returns immediately after setting PC to the
+ * address passed as exception parameter.
+ */
+if (cs->exception_index == EXCP_LPEND_REACHED
+|| cs->exception_index == EXCP_FAKE) {
+env->pc = env->param;
+CPU_PCL(env) = env->pc & 0xfffe;
+return;
+}
+
+/* If we take an exception within an exception => fatal Machine Check. */
+if (GET_STATUS_BIT(env->stat, AEf) == 1) {
+cs->exception_index = EXCP_MACHINE_CHECK;
+env->causecode = 0;
+env->param = 0;
+arc_mmu_disable(env);
+env->mpu.enabled = false;  

[PATCH 13/27] arc: Add Synopsys ARC emulation boards

2021-04-05 Thread cupertinomiranda
From: Claudiu Zissulescu 

Add the Synopsys ARC boards, arc_sim for testing, sim-hs main emulation
board using standard UART and nsim which includes a Synopsys ARC specific
UART implementation.

Signed-off-by: Claudiu Zissulescu 
---
 hw/arc/Makefile.objs |  21 +
 hw/arc/arc_sim.c | 124 +++
 hw/arc/boot.c| 100 ++
 hw/arc/boot.h|  21 +
 hw/arc/meson.build   |  13 +++
 hw/arc/pic_cpu.c | 113 
 hw/arc/virt.c| 180 +++
 include/hw/arc/cpudevs.h |  30 +++
 8 files changed, 602 insertions(+)
 create mode 100644 hw/arc/Makefile.objs
 create mode 100644 hw/arc/arc_sim.c
 create mode 100644 hw/arc/boot.c
 create mode 100644 hw/arc/boot.h
 create mode 100644 hw/arc/meson.build
 create mode 100644 hw/arc/pic_cpu.c
 create mode 100644 hw/arc/virt.c
 create mode 100644 include/hw/arc/cpudevs.h

diff --git a/hw/arc/Makefile.objs b/hw/arc/Makefile.objs
new file mode 100644
index 00..28d7766cd9
--- /dev/null
+++ b/hw/arc/Makefile.objs
@@ -0,0 +1,21 @@
+#
+#  QEMU ARC CPU
+#
+#  Copyright (c) 2019
+#
+#  This library is free software; you can redistribute it and/or
+#  modify it under the terms of the GNU Lesser General Public
+#  License as published by the Free Software Foundation; either
+#  version 2.1 of the License, or (at your option) any later version.
+#
+#  This library 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
+#  Lesser General Public License for more details.
+#
+#  You should have received a copy of the GNU Lesser General Public
+#  License along with this library; if not, see
+#  http://www.gnu.org/licenses/lgpl-2.1.html
+#
+
+obj-y   = arc_sim.o arc_uart.o sample.o pic_cpu.o boot.o board-hsdk.o sim-hs.o 
nsim.o
diff --git a/hw/arc/arc_sim.c b/hw/arc/arc_sim.c
new file mode 100644
index 00..64db440454
--- /dev/null
+++ b/hw/arc/arc_sim.c
@@ -0,0 +1,124 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synppsys Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "qapi/error.h"
+#include "cpu.h"
+#include "hw/hw.h"
+#include "hw/boards.h"
+#include "elf.h"
+#include "hw/char/serial.h"
+#include "net/net.h"
+#include "hw/loader.h"
+#include "exec/memory.h"
+#include "exec/address-spaces.h"
+#include "sysemu/reset.h"
+#include "sysemu/runstate.h"
+#include "sysemu/sysemu.h"
+#include "hw/sysbus.h"
+#include "hw/arc/cpudevs.h"
+#include "boot.h"
+
+
+static uint64_t arc_io_read(void *opaque, hwaddr addr, unsigned size)
+{
+return 0;
+}
+
+static void arc_io_write(void *opaque, hwaddr addr,
+ uint64_t val, unsigned size)
+{
+switch (addr) {
+case 0x08: /* board reset. */
+qemu_system_reset_request(SHUTDOWN_CAUSE_GUEST_RESET);
+break;
+default:
+break;
+}
+}
+
+static const MemoryRegionOps arc_io_ops = {
+.read = arc_io_read,
+.write = arc_io_write,
+.endianness = DEVICE_NATIVE_ENDIAN,
+};
+
+static void arc_sim_init(MachineState *machine)
+{
+static struct arc_boot_info boot_info;
+unsigned int smp_cpus = machine->smp.cpus;
+ram_addr_t ram_base = 0;
+ram_addr_t ram_size = machine->ram_size;
+ARCCPU *cpu = NULL;
+MemoryRegion *ram, *system_io;
+int n;
+
+boot_info.ram_start = ram_base;
+boot_info.ram_size = ram_size;
+boot_info.kernel_filename = machine->kernel_filename;
+
+for (n = 0; n < smp_cpus; n++) {
+cpu = ARC_CPU(object_new(machine->cpu_type));
+if (cpu == NULL) {
+fprintf(stderr, "Unable to find CPU definition!\n");
+exit(1);
+}
+
+/* Set the initial CPU properties. */
+object_property_set_uint(OBJECT(cpu), "freq_hz", 100, 
&error_fatal);
+object_property_set_bool(OBJECT(cpu), "rtc-opt", true, &error_fatal);
+object_property_set_bool(OBJECT(cpu), "realized", true, &error_fatal);
+
+/* Initialize internal devices. */
+cpu_arc_pic_init(cpu);
+cpu_arc_clock_init(cpu);
+
+qemu_register_reset(arc_cpu_reset, cpu);
+}
+
+ram = g_new(MemoryRegion, 1);
+memo

[PATCH 09/27] arc: Add IRQ and timer subsystem support

2021-04-05 Thread cupertinomiranda
From: Claudiu Zissulescu 

Signed-off-by: Claudiu Zissulescu 
---
 target/arc/irq.c   | 680 +
 target/arc/irq.h   |  37 +++
 target/arc/timer.c | 459 ++
 target/arc/timer.h |  27 ++
 4 files changed, 1203 insertions(+)
 create mode 100644 target/arc/irq.c
 create mode 100644 target/arc/irq.h
 create mode 100644 target/arc/timer.c
 create mode 100644 target/arc/timer.h

diff --git a/target/arc/irq.c b/target/arc/irq.c
new file mode 100644
index 00..75111a87a8
--- /dev/null
+++ b/target/arc/irq.c
@@ -0,0 +1,680 @@
+/*
+ * QEMU ARC CPU - IRQ subsystem
+ *
+ * Copyright (c) 2020 Synopsys Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "qemu/log.h"
+#include "qemu/error-report.h"
+#include "hw/irq.h"
+#include "cpu.h"
+#include "qemu/main-loop.h"
+#include "irq.h"
+#include "exec/cpu_ldst.h"
+#include "translate.h"
+#include "qemu/host-utils.h"
+
+#define CACHE_ENTRY_SIZE (TARGET_LONG_BITS / 8)
+#define TARGET_LONG_LOAD(ENV, ADDR) cpu_ldl_data(ENV, ADDR)
+#define TARGET_LONG_STORE(ENV, ADDR, VALUE) cpu_stl_data(ENV, ADDR, VALUE)
+
+/* Static functions and variables. */
+
+static uint32_t save_reg_pair_32[] = {
+0, 2, 4, 6, 8, 10, 12, 14, 16, 18, 20, 22, 24, 26, 28, 30
+};
+
+static uint32_t save_reg_pair_16[] = {
+0, 2, 10, 12, 14, 26, 28, 30
+};
+
+/* Given a struct STATUS_R, pack it to 32 bit. */
+uint32_t pack_status32(ARCStatus *status_r)
+{
+uint32_t res = 0x0;
+
+res |= status_r->pstate & PSTATE_MASK;
+res |= (status_r->RBf & ((1 << RBf_bS)-1)) << RBf_b;
+res |= (status_r->Zf & ((1 << Zf_bS)-1)) << Zf_b;
+res |= (status_r->Nf & ((1 << Nf_bS)-1)) << Nf_b;
+res |= (status_r->Cf & ((1 << Cf_bS)-1)) << Cf_b;
+res |= (status_r->Vf & ((1 << Vf_bS)-1)) << Vf_b;
+res |= (status_r->DEf & ((1 << DEf_bS)-1)) << DEf_b;
+res |= (status_r->Ef  & ((1 << Ef_bS)-1)) << Ef_b;
+res |= (status_r->IEf & ((1 << IEf_bS)-1)) << IEf_b;
+
+/* For debug purposes only. */
+/*
+ * assert((status_r->pstate & ~PSTATE_MASK) == 0);
+ * assert((status_r->RBf & (~((1 << RBf_bS) - 1))) == 0);
+ * assert((status_r->Zf  & (~((1 << Zf_bS)  - 1))) == 0);
+ * assert((status_r->Nf  & (~((1 << Cf_bS)  - 1))) == 0);
+ * assert((status_r->Cf  & (~((1 << Cf_bS)  - 1))) == 0);
+ * assert((status_r->Vf  & (~((1 << Vf_bS)  - 1))) == 0);
+ * assert((status_r->DEf & (~((1 << DEf_bS) - 1))) == 0);
+ * assert((status_r->Ef  & (~((1 << Ef_bS)  - 1))) == 0);
+ * assert((status_r->IEf & (~((1 << IEf_bS) - 1))) == 0);
+ */
+
+return res;
+}
+
+/* Reverse of the above function. */
+void unpack_status32(ARCStatus *status_r, uint32_t value)
+{
+status_r->pstate = value;
+status_r->RBf = ((value >> RBf_b)&((1 << RBf_bS)-1));
+status_r->Zf  = ((value >> Zf_b)&((1 << Zf_bS)-1));
+status_r->Nf  = ((value >> Nf_b)&((1 << Nf_bS)-1));
+status_r->Cf  = ((value >> Cf_b)&((1 << Cf_bS)-1));
+status_r->Vf  = ((value >> Vf_b)&((1 << Vf_bS)-1));
+status_r->DEf = ((value >> DEf_b)&((1 << DEf_bS)-1));
+status_r->Ef  = ((value >> Ef_b)&((1 << Ef_bS)-1));
+status_r->IEf = ((value >> IEf_b)&((1 << IEf_bS)-1));
+}
+
+/* Return from fast interrupts. */
+
+static void arc_rtie_firq(CPUARCState *env)
+{
+assert(GET_STATUS_BIT(env->stat, AEf) == 0);
+
+qemu_log_mask(CPU_LOG_INT, "[IRQ] exit firq: U=" TARGET_FMT_ld
+  ", AUX_IRQ_ACT.U=%d\n",
+  GET_STATUS_BIT(env->stat, Uf), env->aux_irq_act >> 31);
+
+/* Clear currently active interrupt. */
+env->aux_irq_act &= (~1);
+
+/* Check if we need to restore userland SP. */
+if (((env->aux_irq_act & 0x) == 0) && (env->aux_irq_act & 0x8000)) 
{
+switchSP(env);
+}
+
+env->stat = env->stat_l1; /* FIXME use status32_p0 reg. */
+/* Keep U-bit in sync. */
+env->aux_irq_act &= ~(GET_STATUS_BIT(env->stat, Uf) << 31);
+
+/* FIXME! fix current reg bank if RB bit is changed. */
+
+CPU_PCL(env) = CPU_ILINK(env);
+env->pc = CPU_ILINK(env);
+}
+
+/* Implements a pop operation from the CPU stack. */
+static target_ulong irq_pop(CPUARCState *env, const char *str)
+{
+target_ulong rval;
+rval = TARGET_LONG_LOAD(env, CPU_SP(env));
+
+qemu_log_mask(CPU_LOG_INT, "[IRQ] Pop [SP:0x"

[PATCH 12/27] arc: Add gdbstub and XML for debugging support

2021-04-05 Thread cupertinomiranda
From: Shahab Vahedi 

Register layout for the target and the mechanisms to read and set them.

Signed-off-by: Shahab Vahedi 
---
 gdb-xml/arc-v2-aux.xml   |  32 +++
 gdb-xml/arc-v2-core.xml  |  45 +
 gdb-xml/arc-v2-other.xml | 235 ++
 target/arc/gdbstub.c | 421 +++
 target/arc/gdbstub.h | 157 +++
 5 files changed, 890 insertions(+)
 create mode 100644 gdb-xml/arc-v2-aux.xml
 create mode 100644 gdb-xml/arc-v2-core.xml
 create mode 100644 gdb-xml/arc-v2-other.xml
 create mode 100644 target/arc/gdbstub.c
 create mode 100644 target/arc/gdbstub.h

diff --git a/gdb-xml/arc-v2-aux.xml b/gdb-xml/arc-v2-aux.xml
new file mode 100644
index 00..e18168ad05
--- /dev/null
+++ b/gdb-xml/arc-v2-aux.xml
@@ -0,0 +1,32 @@
+
+
+
+
+
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+
diff --git a/gdb-xml/arc-v2-core.xml b/gdb-xml/arc-v2-core.xml
new file mode 100644
index 00..c925a6994c
--- /dev/null
+++ b/gdb-xml/arc-v2-core.xml
@@ -0,0 +1,45 @@
+
+
+
+
+
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+
diff --git a/gdb-xml/arc-v2-other.xml b/gdb-xml/arc-v2-other.xml
new file mode 100644
index 00..9824f518cc
--- /dev/null
+++ b/gdb-xml/arc-v2-other.xml
@@ -0,0 +1,235 @@
+
+
+
+
+
+  
+
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+
+
+
+
+  
+  
+
+
+
+
+
+
+
+
+  
+  
+
+
+
+  
+  
+
+  
+  
+
+
+
+  
+  
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+
+
+
+  
+  
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+
+
+
+
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+
diff --git a/target/arc/gdbstub.c b/target/arc/gdbstub.c
new file mode 100644
index 00..a09cdb3f45
--- /dev/null
+++ b/target/arc/gdbstub.c
@@ -0,0 +1,421 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synppsys Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "exec/gdbstub.h"
+#include "arc-common.h"
+#include "target/arc/regs.h"
+#include "irq.h"
+#include "gdbstub.h"
+#include "exec/helper-proto.h"
+
+/* gets the register address for a particular processor */
+#define REG_ADDR(reg, processor_type) \
+arc_aux_reg_address_for((reg), (processor_type))
+
+#define GDB_GET_REG gdb_get_reg32
+
+int arc_cpu_gdb_read_register(CPUState *cs, GByteArray *mem_buf, int n)
+{
+ARCCPU *cpu = ARC_CPU(cs);
+CPUARCState *env = &cpu->env;
+target_ulong regval = 0;
+
+switch (n) {
+case 0 ... 31:
+   regval = env->r[n];
+   break;
+case GDB_REG_58:
+   regval = env->r[58];
+   break;
+case GDB_REG_59:
+   regval = env->r[59];
+   break;
+case GDB_REG_60:
+   regval = env->r[60];
+   break;
+case GDB_REG_63:
+   regval = env->r[63];
+   break;
+default:
+   assert(!"Unsupported register is being read.");
+}
+
+return GDB_GET_REG(mem_buf, regval);
+}
+
+int arc_cpu_gdb_write_register(CPUState *cs, uint8_t *mem_buf, int n)
+{
+ARCCPU *cpu = ARC_CPU(cs);
+CPUARCState *env = &cpu->env;
+target_ulong regval = ldl_p(mem_buf);
+
+switch (n) {
+case 0 ... 31:
+env->r[n] = regval;
+break;
+case GDB_REG_58:
+env->r[58] = regval;
+break;
+case GDB_REG_59:
+env->r[59] = regval;
+break;
+case GDB_REG_60:
+  

[PATCH 17/27] arcv3: Core cpu file changes

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 target/arc/arc-common.h | 19 +++
 target/arc/cpu-param.h  | 10 ++
 target/arc/cpu.c| 35 +++
 target/arc/cpu.h| 12 
 target/arc/meson.build  | 19 ---
 5 files changed, 88 insertions(+), 7 deletions(-)

diff --git a/target/arc/arc-common.h b/target/arc/arc-common.h
index ff9f97d457..a01e3c661d 100644
--- a/target/arc/arc-common.h
+++ b/target/arc/arc-common.h
@@ -14,37 +14,48 @@
 
 /* CPU combi. */
 #define ARC_OPCODE_ARCALL  (ARC_OPCODE_ARC600 | ARC_OPCODE_ARC700   \
-| ARC_OPCODE_ARCv2EM | ARC_OPCODE_ARCv2HS)
+| ARC_OPCODE_ARCv2EM | ARC_OPCODE_ARCv2HS   \
+| ARC_OPCODE_V3_ARC32 | ARC_OPCODE_V3_ARC64)
 #define ARC_OPCODE_ARCFPX  (ARC_OPCODE_ARC700 | ARC_OPCODE_ARCv2EM)
 #define ARC_OPCODE_ARCV1   (ARC_OPCODE_ARC700 | ARC_OPCODE_ARC600)
 #define ARC_OPCODE_ARCV2   (ARC_OPCODE_ARCv2EM | ARC_OPCODE_ARCv2HS)
 #define ARC_OPCODE_ARCMPY6E  (ARC_OPCODE_ARC700 | ARC_OPCODE_ARCV2)
 
+#define ARC_OPCODE_V3_ALL   (ARC_OPCODE_V3_ARC64 | ARC_OPCODE_V3_ARC32)
+
+#define ARC_OPCODE_V2_V3(ARC_OPCODE_V3_ALL | ARC_OPCODE_ARCV2)
+#define ARC_OPCODE_ARCv2HS_AND_V3(ARC_OPCODE_V3_ALL | ARC_OPCODE_ARCv2HS)
 
 enum arc_cpu_family {
 ARC_OPCODE_NONE= 0,
+
 ARC_OPCODE_DEFAULT = 1 << 0,
 ARC_OPCODE_ARC600  = 1 << 1,
 ARC_OPCODE_ARC700  = 1 << 2,
 ARC_OPCODE_ARCv2EM = 1 << 3,
-ARC_OPCODE_ARCv2HS = 1 << 4
+ARC_OPCODE_ARCv2HS = 1 << 4,
+ARC_OPCODE_V3_ARC32  = 1 << 5,
+ARC_OPCODE_V3_ARC64  = 1 << 6
 };
 
 typedef struct {
-uint32_t value;
+uint64_t value;
 uint32_t type;
 } operand_t;
 
 typedef struct {
 uint32_t class;
-uint32_t limm;
+uint64_t limm;
 uint8_t len;
 bool limm_p;
+#define unsigned_limm_p limm_p
+bool signed_limm_p;
 operand_t operands[3];
 uint8_t n_ops;
 uint8_t cc;
 uint8_t aa;
 uint8_t zz;
+#define zz_as_data_size zz
 bool d;
 bool f;
 bool di;
diff --git a/target/arc/cpu-param.h b/target/arc/cpu-param.h
index 512f4c8b75..9ad28fa693 100644
--- a/target/arc/cpu-param.h
+++ b/target/arc/cpu-param.h
@@ -20,11 +20,21 @@
 #ifndef ARC_CPU_PARAM_H
 #define ARC_CPU_PARAM_H 1
 
+#ifdef TARGET_ARCV2
 #define TARGET_LONG_BITS32
 #define TARGET_PAGE_BITS13
 #define TARGET_PHYS_ADDR_SPACE_BITS 32
 #define TARGET_VIRT_ADDR_SPACE_BITS 32
 #define NB_MMU_MODES2
+#endif
+
+#ifdef TARGET_ARCV3
+#define TARGET_LONG_BITS64
+#define TARGET_PAGE_BITS12
+#define TARGET_PHYS_ADDR_SPACE_BITS 48
+#define TARGET_VIRT_ADDR_SPACE_BITS 64
+#define NB_MMU_MODES3
+#endif
 
 #endif
 
diff --git a/target/arc/cpu.c b/target/arc/cpu.c
index f1a5b2a7c1..da394f015a 100644
--- a/target/arc/cpu.c
+++ b/target/arc/cpu.c
@@ -193,6 +193,9 @@ static void arc_cpu_disas_set_info(CPUState *cs, 
disassemble_info *info)
 case ARC_OPCODE_ARCv2HS:
 info->mach = bfd_mach_arc_arcv2hs;
 break;
+case ARC_OPCODE_V3_ARC64:
+info->mach = bfd_mach_arcv3_64;
+break;
 default:
 info->mach = bfd_mach_arc_arcv2;
 break;
@@ -226,6 +229,7 @@ static void arc_cpu_realizefn(DeviceState *dev, Error 
**errp)
  */
 cpu->freq_hz = cpu->cfg.freq_hz;
 
+#ifdef TARGET_ARCV2
 cpu->isa_config = 0x02;
 switch (cpu->cfg.pc_size) {
 case 16:
@@ -291,6 +295,18 @@ static void arc_cpu_realizefn(DeviceState *dev, Error 
**errp)
   | (cpu->cfg.dmp_unaligned ? BIT(22) : 0) | BIT(23)
   | (cpu->cfg.code_density ? (2 << 24) : 0) | BIT(28);
 
+#elif TARGET_ARCV3
+cpu->isa_config = 0x03/* ver */
+  | (1 << 8)  /* va_size: 48-bit */
+  | (1 << 16) /* pa_size: 48-bit */
+  | ((cpu->cfg.byte_order ? 1 : 0) << 20) /* endian */
+  | (1 << 21) /* atomic=1: LLOCK, LLOCKL, WLFC */
+  | ((cpu->cfg.dmp_unaligned ? 1 : 0) << 23) /* unaliged 
access */
+  | (0 << 24) /* 128-bit load/store TBD */
+  | (3 << 26) /* Code density instructions */
+  | (0 << 28); /* 64-bit DIV/REM TBD */
+#endif
+
 arc_initializeTIMER(cpu);
 arc_initializeIRQ(cpu);
 
@@ -379,7 +395,11 @@ static void arc_cpu_class_init(ObjectClass *oc, void *data)
 cc->gdb_write_register = arc_cpu_gdb_write_register;
 
 /* Core GDB support */
+#ifdef TARGET_ARCV2
 cc->gdb_core_xml_file = "arc-v2-core.xml";
+#else
+cc->gdb_core_xml_file = "arc-core-v3.xml";
+#endif
 cc->gdb_num_core_regs = GDB_REG_LAST;
 cc->gdb_arch_name = arc_gdb_arch_name;
 
@@ -395,6 +415,7 @@ static void arc_any_initfn(Object *obj)
 cpu->family = ARC_OPCODE_ARC700;
 }
 
+#ifdef TARGET_ARCV2
 static void arc600_initfn(Object *obj)
 {
 ARCCPU *cpu = ARC_CPU(obj);
@@ -418,6 +439,15 @@ stat

[PATCH 10/27] arc: Add memory management unit (MMU) support

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

Add Synopsys ARC MMU version 4 support. The implementation is
restricted to 8K page size support.

Signed-off-by: Cupertino Miranda 
---
 target/arc/mmu.c | 805 +++
 target/arc/mmu.h | 148 +
 2 files changed, 953 insertions(+)
 create mode 100644 target/arc/mmu.c
 create mode 100644 target/arc/mmu.h

diff --git a/target/arc/mmu.c b/target/arc/mmu.c
new file mode 100644
index 00..f79c910d80
--- /dev/null
+++ b/target/arc/mmu.c
@@ -0,0 +1,805 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synppsys Inc.
+ * Contributed by Cupertino Miranda 
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "mmu.h"
+#include "target/arc/regs.h"
+#include "qemu/osdep.h"
+#include "cpu.h"
+#include "exec/exec-all.h"
+
+target_ulong
+arc_mmu_aux_get(const struct arc_aux_reg_detail *aux_reg_detail, void *data)
+{
+CPUARCState *env = (CPUARCState *) data;
+struct arc_mmu *mmu = &env->mmu;
+uint32_t reg = 0;
+
+switch (aux_reg_detail->id) {
+case AUX_ID_mmu_build:
+/*
+ * For now hardcode the TLB geometry and canonical page sizes
+ * MMUv4: 2M Super Page, 8k Page, 4 way set associative,
+ *1K entries (256x4), 4 uITLB, 8 uDTLB
+ */
+reg = 0x04e21a4a;
+break;
+case AUX_ID_tlbindex:
+reg = mmu->tlbindex;
+break;
+case AUX_ID_tlbpd0:
+reg = mmu->tlbpd0;
+break;
+case AUX_ID_tlbpd1:
+reg = mmu->tlbpd1;
+break;
+case AUX_ID_tlbpd1_hi:
+reg = mmu->tlbpd1_hi;
+break;
+case AUX_ID_scratch_data0:
+reg = mmu->scratch_data0;
+break;
+case AUX_ID_tlbcommand:
+reg = mmu->tlbcmd;
+break;
+case AUX_ID_pid:
+reg = (mmu->enabled << 31) | mmu->pid_asid;
+break;
+case AUX_ID_sasid0:
+reg = mmu->sasid0;
+break;
+case AUX_ID_sasid1:
+reg = mmu->sasid1;
+break;
+default:
+break;
+}
+
+return reg;
+}
+
+void
+arc_mmu_aux_set(const struct arc_aux_reg_detail *aux_reg_detail,
+target_ulong val, void *data)
+{
+CPUARCState *env = (CPUARCState *) data;
+CPUState *cs = env_cpu(env);
+struct arc_mmu *mmu = &env->mmu;
+
+switch (aux_reg_detail->id) {
+/* AUX_ID_tlbcommand is more involved and handled seperately */
+case AUX_ID_tlbindex:
+mmu->tlbindex = val;
+break;
+case AUX_ID_tlbpd0:
+mmu->tlbpd0 = val;
+break;
+case AUX_ID_tlbpd1:
+mmu->tlbpd1 = val;
+break;
+case AUX_ID_tlbpd1_hi:
+mmu->tlbpd1_hi = val;
+break;
+case AUX_ID_scratch_data0:
+mmu->scratch_data0 = val;
+break;
+case AUX_ID_pid:
+qemu_log_mask(CPU_LOG_MMU,
+  "[MMU] Writing PID_ASID with value 0x" TARGET_FMT_lx
+  " at 0x" TARGET_FMT_lx "\n",
+  val, env->pc);
+mmu->enabled = (val >> 31);
+mmu->pid_asid = val & 0xff;
+tlb_flush(cs);
+break;
+case AUX_ID_sasid0:
+mmu->sasid0 = val;
+break;
+case AUX_ID_sasid1:
+mmu->sasid1 = val;
+break;
+default:
+break;
+}
+}
+
+/* vaddr can't have top bit */
+#define VPN(addr) ((addr) & (PAGE_MASK & (~0x8000)))
+#define PFN(addr) ((addr) & PAGE_MASK)
+
+static void
+arc_mmu_debug_tlb_for_set(CPUARCState *env, int set)
+{
+int j;
+bool set_printed = false;
+
+for (j = 0; j < N_WAYS; j++) {
+struct arc_tlb_e *tlb = &env->mmu.nTLB[set][j];
+
+if ((tlb->pd0 & PD0_V) != 0) {
+if (set_printed == false) {
+printf("set %d\n", set);
+set_printed = true;
+}
+if (set_printed == true) {
+printf(" way %d\n", j);
+}
+printf("  tlppd0: %08x: vaddr=\t%08x %s %s%s asid=%02x\n",
+   tlb->pd0, VPN(tlb->pd0),
+   (char *) ((tlb->pd0 & PD0_SZ) != 0 ? "sz1" : "sz0"),
+   (char *) ((tlb->pd0 & PD0_V) != 0 ? "V" : ""),
+   (char *) ((tlb->pd0 & PD0_G) != 0 ? "g" : ""),
+   tlb->pd0 & PD0_ASID);
+
+printf("  tlppd1: %08x: padd

[PATCH 14/27] arc: Add support for ARCv2

2021-04-05 Thread cupertinomiranda
From: Shahab Vahedi 

Add remaining bits of the Synopsys ARCv2 (EM/HS) support into QEMU,
configure bits, arch_init and configuration files for softmmu (hardware
emulation).

Signed-off-by: Shahab Vahedi 
Signed-off-by: Cupertino Miranda 
---
 configure   |  2 ++
 default-configs/arc-softmmu.mak |  5 +
 default-configs/devices/arc-softmmu.mak |  7 +++
 default-configs/targets/arc-softmmu.mak |  3 +++
 disas.c |  2 ++
 disas/meson.build   |  1 +
 hw/Kconfig  |  1 +
 hw/arc/Kconfig  |  9 +
 hw/arc/Makefile.objs| 21 -
 hw/arc/meson.build  |  6 +-
 hw/meson.build  |  1 +
 include/disas/dis-asm.h | 10 +-
 include/elf.h   |  5 +
 include/exec/poison.h   |  2 ++
 include/sysemu/arch_init.h  |  1 +
 meson.build |  5 +++--
 softmmu/arch_init.c |  2 ++
 target/meson.build  |  1 +
 18 files changed, 55 insertions(+), 29 deletions(-)
 create mode 100644 default-configs/arc-softmmu.mak
 create mode 100644 default-configs/devices/arc-softmmu.mak
 create mode 100644 default-configs/targets/arc-softmmu.mak
 create mode 100644 hw/arc/Kconfig
 delete mode 100644 hw/arc/Makefile.objs

diff --git a/configure b/configure
index 535e6a9269..80d993fac7 100755
--- a/configure
+++ b/configure
@@ -680,6 +680,8 @@ elif check_define __arm__ ; then
   cpu="arm"
 elif check_define __aarch64__ ; then
   cpu="aarch64"
+elif check_define __arc__ ; then
+  cpu="arc"
 else
   cpu=$(uname -m)
 fi
diff --git a/default-configs/arc-softmmu.mak b/default-configs/arc-softmmu.mak
new file mode 100644
index 00..4300a90c93
--- /dev/null
+++ b/default-configs/arc-softmmu.mak
@@ -0,0 +1,5 @@
+# Default configuration for arc-softmmu
+
+CONFIG_VIRTIO_MMIO=y
+CONFIG_SERIAL=y
+CONFIG_OPENCORES_ETH=y
diff --git a/default-configs/devices/arc-softmmu.mak 
b/default-configs/devices/arc-softmmu.mak
new file mode 100644
index 00..0ce4176b2d
--- /dev/null
+++ b/default-configs/devices/arc-softmmu.mak
@@ -0,0 +1,7 @@
+# Default configuration for arc-softmmu
+
+CONFIG_SEMIHOSTING=n
+
+# Boards:
+#
+CONFIG_ARC_VIRT=y
diff --git a/default-configs/targets/arc-softmmu.mak 
b/default-configs/targets/arc-softmmu.mak
new file mode 100644
index 00..a50b090b97
--- /dev/null
+++ b/default-configs/targets/arc-softmmu.mak
@@ -0,0 +1,3 @@
+TARGET_ARCH=arcv2
+TARGET_BASE_ARCH=arc
+TARGET_XML_FILES= gdb-xml/arc-v2-core.xml gdb-xml/arc-v2-aux.xml 
gdb-xml/arc-v2-other.xml
diff --git a/disas.c b/disas.c
index a61f95b580..a10fa41330 100644
--- a/disas.c
+++ b/disas.c
@@ -208,6 +208,8 @@ static void initialize_debug_host(CPUDebug *s)
 s->info.cap_insn_split = 6;
 #elif defined(__hppa__)
 s->info.print_insn = print_insn_hppa;
+#elif defined(__arc__)
+s->info.print_insn = print_insn_arc;
 #endif
 }
 
diff --git a/disas/meson.build b/disas/meson.build
index 4c8da01877..c35836fa9f 100644
--- a/disas/meson.build
+++ b/disas/meson.build
@@ -4,6 +4,7 @@ subdir('libvixl')
 common_ss.add(when: 'CONFIG_ALPHA_DIS', if_true: files('alpha.c'))
 common_ss.add(when: 'CONFIG_ARM_A64_DIS', if_true: files('arm-a64.cc'))
 common_ss.add_all(when: 'CONFIG_ARM_A64_DIS', if_true: libvixl_ss)
+common_ss.add(when: 'CONFIG_ARC_DIS', if_true: files('arc.c'))
 common_ss.add(when: 'CONFIG_ARM_DIS', if_true: files('arm.c'))
 common_ss.add(when: 'CONFIG_CRIS_DIS', if_true: files('cris.c'))
 common_ss.add(when: 'CONFIG_HEXAGON_DIS', if_true: files('hexagon.c'))
diff --git a/hw/Kconfig b/hw/Kconfig
index ff40bd3f7b..cdc0d380a3 100644
--- a/hw/Kconfig
+++ b/hw/Kconfig
@@ -41,6 +41,7 @@ source vfio/Kconfig
 source watchdog/Kconfig
 
 # arch Kconfig
+source arc/Kconfig
 source arm/Kconfig
 source alpha/Kconfig
 source avr/Kconfig
diff --git a/hw/arc/Kconfig b/hw/arc/Kconfig
new file mode 100644
index 00..b47afbcdf2
--- /dev/null
+++ b/hw/arc/Kconfig
@@ -0,0 +1,9 @@
+config ARC_VIRT
+bool
+select SERIAL
+select VIRTIO_MMIO
+select PCI_EXPRESS_GENERIC_BRIDGE
+select PCI_DEVICES
+
+config ARC
+bool
diff --git a/hw/arc/Makefile.objs b/hw/arc/Makefile.objs
deleted file mode 100644
index 28d7766cd9..00
--- a/hw/arc/Makefile.objs
+++ /dev/null
@@ -1,21 +0,0 @@
-#
-#  QEMU ARC CPU
-#
-#  Copyright (c) 2019
-#
-#  This library is free software; you can redistribute it and/or
-#  modify it under the terms of the GNU Lesser General Public
-#  License as published by the Free Software Foundation; either
-#  version 2.1 of the License, or (at your option) any later version.
-#
-#  This library 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 th

[PATCH 11/27] arc: Add memory protection unit (MPU) support

2021-04-05 Thread cupertinomiranda
From: Shahab Vahedi 

Add memory implementation for Synopsys MPU unit version 3.
Synopsys MPU allows to create memory regions against unauthorized
execution/read/writes accesses.

Signed-off-by: Shahab Vahedi 
---
 target/arc/mpu.c | 656 +++
 target/arc/mpu.h | 133 ++
 2 files changed, 789 insertions(+)
 create mode 100644 target/arc/mpu.c
 create mode 100644 target/arc/mpu.h

diff --git a/target/arc/mpu.c b/target/arc/mpu.c
new file mode 100644
index 00..256ff12bfc
--- /dev/null
+++ b/target/arc/mpu.c
@@ -0,0 +1,656 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Synppsys Inc.
+ * Contributed by Shahab Vahedi (Synopsys)
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "mpu.h"
+#include "cpu.h"
+#include "exec/exec-all.h"
+#include "mmu.h"
+
+/*
+ * In case of exception, this signals the effective region
+ * was the default one
+ */
+#define MPU_DEFAULT_REGION_NR 0xff
+
+/* Defines used by in-house functions */
+#define MPU_EN_EN_BIT   30
+#define MPU_EN_KR_BIT8
+#define MPU_EN_KW_BIT7
+#define MPU_EN_KE_BIT6
+#define MPU_EN_UR_BIT5
+#define MPU_EN_UW_BIT4
+#define MPU_EN_UE_BIT3
+
+#define MPU_ECR_EC_CODE_BIT 16
+#define MPU_ECR_VT_BIT   8
+
+#define MPU_BASE_ADDR_MASK  0xffe0  /* ignore least 5 bits */
+#define MPU_BASE_VALID_MASK 0x0001  /* bit #0 */
+
+/*
+ * Given a number of bits as width, calc the mask to
+ * "and" with. e.g.: 3 bits --> 8 - 1 --> 7 (111b)
+ */
+#define MPU_WIDTH_TO_MASK(w) ((1 << (w)) - 1)
+#define MPU_PERMS_REG_LOWER_SIZE_WIDTH  2
+#define MPU_PERMS_REG_HIGHER_SIZE_WIDTH 3
+#define MPU_PERMS_REG_HIGHER_SIZE_POS   9
+
+/*
+ * After knowing the operating mode (user/kernel),
+ * this struct represents the effective permissions.
+ */
+typedef struct MPUEffectPerm {
+bool read;
+bool write;
+bool exec;
+} MPUEffectPerm;
+
+/* Packer and unpackers (local to this translation unit) */
+static inline uint32_t pack_enable(const bool ena)
+{
+return ena << MPU_EN_EN_BIT;
+}
+
+static inline void unpack_enable(bool *enabled, uint32_t value)
+{
+*enabled = (value >> MPU_EN_EN_BIT) & 1;
+}
+
+static inline uint32_t pack_permissions(const MPUPermissions *perms)
+{
+return perms->KR << MPU_EN_KR_BIT |
+   perms->KW << MPU_EN_KW_BIT |
+   perms->KE << MPU_EN_KE_BIT |
+   perms->UR << MPU_EN_UR_BIT |
+   perms->UW << MPU_EN_UW_BIT |
+   perms->UE << MPU_EN_UE_BIT;
+}
+
+static inline void unpack_permissions(MPUPermissions *perms, uint32_t value)
+{
+perms->KR = (value >> MPU_EN_KR_BIT) & 1;
+perms->KW = (value >> MPU_EN_KW_BIT) & 1;
+perms->KE = (value >> MPU_EN_KE_BIT) & 1;
+perms->UR = (value >> MPU_EN_UR_BIT) & 1;
+perms->UW = (value >> MPU_EN_UW_BIT) & 1;
+perms->UE = (value >> MPU_EN_UE_BIT) & 1;
+}
+
+static inline uint32_t pack_enable_reg(const MPUEnableReg *mpuen)
+{
+return pack_enable(mpuen->enabled) |
+   pack_permissions(&mpuen->permission);
+}
+
+static inline void unpack_enable_reg(MPUEnableReg *mpuen, uint32_t value)
+{
+unpack_enable(&mpuen->enabled, value);
+unpack_permissions(&mpuen->permission, value);
+}
+
+static inline uint32_t pack_ecr(const MPUECR *mpuecr)
+{
+return ARC_MPU_ECR_VEC_NUM << MPU_ECR_EC_CODE_BIT |
+   (mpuecr->violation & 3) << MPU_ECR_VT_BIT  |
+   mpuecr->region;
+}
+
+static inline uint32_t pack_base_reg(const MPUBaseReg *mpurdb)
+{
+return mpurdb->addr | mpurdb->valid;
+}
+
+static inline void unpack_base_reg(MPUBaseReg *mpurdb, uint32_t value)
+{
+mpurdb->addr  = value & MPU_BASE_ADDR_MASK;
+mpurdb->valid = value & MPU_BASE_VALID_MASK;
+}
+
+
+/*
+ * Break the "size" field into "higher" and "lower" parts
+ * e.g.: a b c d e --> a b c . . . d e
+ * higher lower
+ */
+static uint32_t pack_region_size_bits(uint8_t size_bits)
+{
+uint32_t lower =
+size_bits & MPU_WIDTH_TO_MASK(MPU_PERMS_REG_LOWER_SIZE_WIDTH);
+uint32_t higher = size_bits >> MPU_PERMS_REG_LOWER_SIZE_WIDTH;
+higher &= MPU_WIDTH_TO_MASK(MPU_PERMS_REG_HIGHER_SIZE_WIDTH);
+return (higher << MPU_PERMS_REG_HIGHER_SIZE_POS) | lower;
+}
+
+/*
+ * Put the higher and lower parts of "size" field together
+ * e.g.: a b c . . . d e ---> abcd

[PATCH 16/27] tests/acceptance: ARC: Add linux boot testing.

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

Just an acceptance test with ARC Linux booting.

Signed-off-by: Cupertino Miranda 
---
 tests/acceptance/boot_linux_console.py | 55 ++
 1 file changed, 55 insertions(+)

diff --git a/tests/acceptance/boot_linux_console.py 
b/tests/acceptance/boot_linux_console.py
index 1ca32ecf25..b5a781b6b4 100644
--- a/tests/acceptance/boot_linux_console.py
+++ b/tests/acceptance/boot_linux_console.py
@@ -138,6 +138,26 @@ def test_mips_malta(self):
 console_pattern = 'Kernel command line: %s' % kernel_command_line
 self.wait_for_console_pattern(console_pattern)
 
+def test_mips_malta(self):
+"""
+:avocado: tags=arch:arc
+"""
+deb_url = ('http://snapshot.debian.org/archive/debian/'
+   '20130217T032700Z/pool/main/l/linux-2.6/'
+   'linux-image-2.6.32-5-4kc-malta_2.6.32-48_mips.deb')
+deb_hash = 'a8cfc28ad8f45f54811fc6cf74fc43ffcfe0ba04'
+deb_path = self.fetch_asset(deb_url, asset_hash=deb_hash)
+kernel_path = self.extract_from_deb(deb_path,
+'/boot/vmlinux-archs')
+
+self.vm.set_console()
+kernel_command_line = self.KERNEL_COMMON_COMMAND_LINE + 'console=ttyS0'
+self.vm.add_args('-kernel', kernel_path,
+ '-append', kernel_command_line)
+self.vm.launch()
+console_pattern = 'Kernel command line: %s' % kernel_command_line
+self.wait_for_console_pattern(console_pattern)
+
 def test_mips64el_malta(self):
 """
 This test requires the ar tool to extract "data.tar.gz" from
@@ -966,6 +986,17 @@ def test_alpha_clipper(self):
 console_pattern = 'Kernel command line: %s' % kernel_command_line
 self.wait_for_console_pattern(console_pattern)
 
+def do_test_arc(self, kernel_name, console=0):
+tar_url = 
('https://github.com/cupertinomiranda/arc-qemu-resources/archive/master.tar.gz')
+file_path = self.fetch_asset(tar_url)
+archive.extract(file_path, self.workdir)
+
+self.vm.set_console(console_index=console)
+self.vm.add_args('-kernel',
+ self.workdir + '/' + kernel_name)
+self.vm.launch()
+self.wait_for_console_pattern('QEMU advent calendar')
+
 def test_m68k_q800(self):
 """
 :avocado: tags=arch:m68k
@@ -1086,3 +1117,27 @@ def test_xtensa_lx60(self):
 tar_hash = '49e88d9933742f0164b60839886c9739cb7a0d34'
 self.vm.add_args('-cpu', 'dc233c')
 self.do_test_advcal_2018('02', tar_hash, 'santas-sleigh-ride.elf')
+
+timeout = 240
+def test_arc_virt(self):
+"""
+:avocado: tags=arch:arc
+:avocado: tags=machine:virt
+"""
+
+tar_url = ('https://github.com/cupertinomiranda/'
+   'arc-qemu-resources/archive/master.tar.gz')
+file_path = self.fetch_asset(tar_url)
+archive.extract(file_path, self.workdir)
+
+kernel_path = self.workdir + '/arc-qemu-resources-master/vmlinux_archs'
+
+self.vm.set_console()
+kernel_command_line = (self.KERNEL_COMMON_COMMAND_LINE)
+self.vm.add_args('-kernel', kernel_path)
+self.vm.add_args('-device', 'virtio-net-device,netdev=net0')
+self.vm.add_args('-netdev', 
'user,id=net0,hostfwd=tcp::5558-:21,hostfwd=tcp::5557-:23')
+self.vm.launch()
+
+console_pattern = 'Welcome to Buildroot'
+self.wait_for_console_pattern(console_pattern)
-- 
2.20.1


___
linux-snps-arc mailing list
linux-snps-arc@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-snps-arc


[PATCH 21/27] arcv3: TCG instruction generator changes

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 target/arc/translate.c | 180 +
 1 file changed, 180 insertions(+)

diff --git a/target/arc/translate.c b/target/arc/translate.c
index 1712fcc9c3..6b2102394f 100644
--- a/target/arc/translate.c
+++ b/target/arc/translate.c
@@ -303,6 +303,15 @@ static bool read_and_decode_context(DisasContext *ctx,
 cpu_ldl_code(ctx->env,
 ctx->cpc + length));
 length += 4;
+#ifdef TARGET_ARCV3
+} else if(ctx->insn.signed_limm_p) {
+ctx->insn.limm = ARRANGE_ENDIAN(true,
+cpu_ldl_code (ctx->env,
+ctx->cpc + length));
+if(ctx->insn.limm & 0x8000)
+  ctx->insn.limm += 0x;
+length += 4;
+#endif
 } else {
 ctx->insn.limm = 0;
 }
@@ -747,7 +756,14 @@ arc_gen_SR(DisasCtxt *ctx, TCGv src2, TCGv src1)
 {
 int ret = DISAS_NEXT;
 
+#ifdef TARGET_ARCV2
+writeAuxReg(src2, src1);
+#elif TARGET_ARCV3
+TCGv temp = tcg_temp_local_new();
+tcg_gen_andi_tl(temp, src1, 0x);
 writeAuxReg(src2, src1);
+tcg_temp_free(temp);
+#endif
 return ret;
 }
 int
@@ -770,6 +786,169 @@ arc_gen_SYNC(DisasCtxt *ctx)
 }
 
 
+#ifdef TARGET_ARCV3
+/*
+ * The mpyl instruction is a 64x64 signed multipler that produces
+ * a 64-bit product (the lower 64-bit of the actual prodcut).
+ */
+int
+arc_gen_MPYL(DisasCtxt *ctx, TCGv a, TCGv b, TCGv c)
+{
+if ((getFFlag () == true)) {
+arc_gen_excp(ctx, EXCP_INST_ERROR, 0, 0);
+return DISAS_NEXT;
+}
+
+TCGLabel *done = gen_new_label();
+
+if (ctx->insn.cc) {
+TCGv cc = tcg_temp_local_new();
+arc_gen_verifyCCFlag(ctx, cc);
+tcg_gen_brcondi_tl(TCG_COND_NE, cc, 1, done);
+tcg_temp_free(cc);
+}
+
+TCGv_i64 lo = tcg_temp_local_new_i64();
+TCGv_i64 hi = tcg_temp_local_new_i64();
+
+tcg_gen_muls2_i64(lo, hi, b, c);
+tcg_gen_mov_tl(a, lo);
+
+tcg_temp_free_i64(hi);
+tcg_temp_free_i64(lo);
+gen_set_label(done);
+
+return DISAS_NEXT;
+}
+
+/*
+ * The mpyml instruction is a 64x64 signed multipler that produces
+ * a 64-bit product (the higher 64-bit of the actual prodcut).
+ */
+int
+arc_gen_MPYML(DisasCtxt *ctx, TCGv a, TCGv b, TCGv c)
+{
+if ((getFFlag () == true)) {
+arc_gen_excp(ctx, EXCP_INST_ERROR, 0, 0);
+return DISAS_NEXT;
+}
+
+TCGLabel *done = gen_new_label();
+
+if (ctx->insn.cc) {
+TCGv cc = tcg_temp_local_new();
+arc_gen_verifyCCFlag(ctx, cc);
+tcg_gen_brcondi_tl(TCG_COND_NE, cc, 1, done);
+tcg_temp_free(cc);
+}
+
+TCGv lo = tcg_temp_local_new();
+TCGv hi = tcg_temp_local_new();
+tcg_gen_muls2_i64(lo, hi, b, c);
+tcg_gen_mov_tl(a, hi);
+
+tcg_temp_free(hi);
+tcg_temp_free(lo);
+gen_set_label(done);
+
+return DISAS_NEXT;
+}
+
+/*
+ * The mpymul instruction is a 64x64 unsigned multipler that produces
+ * a 64-bit product (the higher 64-bit of the actual prodcut).
+ */
+int
+arc_gen_MPYMUL(DisasCtxt *ctx, TCGv a, TCGv b, TCGv c)
+{
+if ((getFFlag () == true)) {
+arc_gen_excp(ctx, EXCP_INST_ERROR, 0, 0);
+return DISAS_NEXT;
+}
+
+TCGLabel *done = gen_new_label();
+
+if (ctx->insn.cc) {
+TCGv cc = tcg_temp_local_new();
+arc_gen_verifyCCFlag(ctx, cc);
+tcg_gen_brcondi_tl(TCG_COND_NE, cc, 1, done);
+tcg_temp_free(cc);
+}
+
+TCGv lo = tcg_temp_local_new();
+TCGv hi = tcg_temp_local_new();
+
+tcg_gen_mulu2_i64(lo, hi, b, c);
+tcg_gen_mov_tl(a, hi);
+
+tcg_temp_free(hi);
+tcg_temp_free(lo);
+gen_set_label(done);
+
+return DISAS_NEXT;
+}
+
+/*
+ * The mpymsul instruction is a 64x64 signedxunsigned multipler that
+ * produces * a 64-bit product (the higher 64-bit of the actual prodcut).
+ */
+int
+arc_gen_MPYMSUL(DisasCtxt *ctx, TCGv a, TCGv b, TCGv c)
+{
+if ((getFFlag () == true)) {
+arc_gen_excp(ctx, EXCP_INST_ERROR, 0, 0);
+return DISAS_NEXT;
+}
+
+TCGLabel *done = gen_new_label();
+
+if (ctx->insn.cc) {
+TCGv cc = tcg_temp_local_new();
+arc_gen_verifyCCFlag(ctx, cc);
+tcg_gen_brcondi_tl(TCG_COND_NE, cc, 1, done);
+tcg_temp_free(cc);
+}
+
+TCGv lo = tcg_temp_local_new();
+TCGv hi = tcg_temp_local_new();
+tcg_gen_mulsu2_tl(lo, hi, b, c);
+tcg_gen_mov_tl(a, hi);
+
+tcg_temp_free(hi);
+tcg_temp_free(lo);
+gen_set_label(done);
+
+return DISAS_NEXT;
+}
+
+/*
+ * a = b + (c << 32)
+ */
+int
+arc_gen_ADDHL(DisasCtxt *ctx, TCGv a, TCGv b, TCGv c)
+{
+TCGLabel *done = gen_new_label();
+
+if (ctx->insn.cc) {
+TCGv cc = tcg_temp_local_new();
+arc_gen_verifyCCFlag(ctx, cc);
+tcg_gen_brcondi_tl(TCG_COND_NE, cc, 1, done);
+tcg_temp_free(cc);
+}
+
+TCGv shifted = tcg_

[PATCH 23/27] arcv3: BCR and AUX register changes

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 target/arc/regs-detail.def | 40 ++
 target/arc/regs-impl.c |  5 +
 target/arc/regs.def| 20 +++
 3 files changed, 65 insertions(+)

diff --git a/target/arc/regs-detail.def b/target/arc/regs-detail.def
index 6f0cc94809..48b26d6cb0 100644
--- a/target/arc/regs-detail.def
+++ b/target/arc/regs-detail.def
@@ -39,8 +39,10 @@ DEF(0xa,   ARC_OPCODE_ARCALL,  NONE, status32)
 DEF(0xb,   ARC_OPCODE_ARCV2,   NONE, status32_p0)
 DEF(0xc,   ARC_OPCODE_ARCv2EM, NONE, sec_extra)
 DEF(0xd,   ARC_OPCODE_ARCV2,   NONE, aux_user_sp)
+DEF(0xd,   ARC_OPCODE_V3_ALL,  NONE, aux_user_sp)
 DEF(0xe,   ARC_OPCODE_ARC700,  NONE, clk_enable)
 DEF(0xe,   ARC_OPCODE_ARCV2,   NONE, aux_irq_ctrl)
+DEF(0xe,   ARC_OPCODE_V3_ALL,  NONE, aux_irq_ctrl)
 DEF(0xf,   ARC_OPCODE_ARC700,  NONE, bpu_flush)
 DEF(0xf,   ARC_OPCODE_ARCv2HS, NONE, debugi)
 DEF(0x10,  ARC_OPCODE_ARCV1,   NONE, ivic)
@@ -75,6 +77,7 @@ DEF(0x23,  ARC_OPCODE_ARCALL,  NONE, limit0)
 DEF(0x24,  ARC_OPCODE_ARCV1,   NONE, pcport)
 DEF(0x25,  ARC_OPCODE_ARC700,  NONE, int_vector_base)
 DEF(0x25,  ARC_OPCODE_ARCV2,   NONE, int_vector_base)
+DEF(0x25,  ARC_OPCODE_V3_ALL,  NONE, int_vector_base)
 DEF(0x26,  ARC_OPCODE_ARC600,  NONE, aux_vbfdw_mode)
 DEF(0x27,  ARC_OPCODE_ARC600,  NONE, aux_vbfdw_bm0)
 DEF(0x28,  ARC_OPCODE_ARC600,  NONE, aux_vbfdw_bm1)
@@ -116,6 +119,7 @@ DEF(0x41,  ARC_OPCODE_ARCV1,   NONE, aux_macmode)
 DEF(0x42,  ARC_OPCODE_ARC600,  NONE, lsp_newval)
 DEF(0x43,  ARC_OPCODE_ARCV1,   NONE, aux_irq_lv12)
 DEF(0x43,  ARC_OPCODE_ARCV2,   NONE, aux_irq_act)
+DEF(0x43,  ARC_OPCODE_V3_ALL,  NONE, aux_irq_act)
 DEF(0x44,  ARC_OPCODE_ARCV1,   NONE, aux_xmac0)
 DEF(0x45,  ARC_OPCODE_ARCV1,   NONE, aux_xmac1)
 DEF(0x46,  ARC_OPCODE_ARCV1,   NONE, aux_xmac2)
@@ -126,7 +130,9 @@ DEF(0x4a,  ARC_OPCODE_ARCALL,  NONE, dc_ivdl)
 DEF(0x4b,  ARC_OPCODE_ARCALL,  NONE, dc_flsh)
 DEF(0x4c,  ARC_OPCODE_ARCALL,  NONE, dc_fldl)
 DEF(0x4d,  ARC_OPCODE_ARCV2,   NONE, dc_startr)
+DEF(0x4d,  ARC_OPCODE_V3_ALL,  NONE, dc_startr)
 DEF(0x4e,  ARC_OPCODE_ARCV2,   NONE, dc_endr)
+DEF(0x4e,  ARC_OPCODE_V3_ALL,  NONE, dc_endr)
 DEF(0x50,  ARC_OPCODE_NONE,NONE, hexdata)
 DEF(0x51,  ARC_OPCODE_NONE,NONE, hexctrl)
 DEF(0x52,  ARC_OPCODE_NONE,NONE, led)
@@ -191,13 +197,17 @@ DEF(0x100, ARC_OPCODE_ARCALL,  NONE, count1)
 DEF(0x101, ARC_OPCODE_ARCALL,  NONE, control1)
 DEF(0x102, ARC_OPCODE_ARCALL,  NONE, limit1)
 DEF(0x103, ARC_OPCODE_ARCV2,   NONE, aux_rtc_ctrl)
+DEF(0x103, ARC_OPCODE_V3_ALL,  NONE, aux_rtc_ctrl)
 DEF(0x104, ARC_OPCODE_ARCV2,   NONE, aux_rtc_low)
+DEF(0x104, ARC_OPCODE_V3_ALL,  NONE, aux_rtc_low)
 DEF(0x105, ARC_OPCODE_ARCV2,   NONE, aux_rtc_high)
+DEF(0x105, ARC_OPCODE_V3_ALL,  NONE, aux_rtc_high)
 DEF(0x200, ARC_OPCODE_ARCV1,   NONE, aux_irq_lev)
 DEF(0x200, ARC_OPCODE_ARCV2,   NONE, irq_priority_pending)
 DEF(0x201, ARC_OPCODE_ARCALL,  NONE, aux_irq_hint)
 DEF(0x202, ARC_OPCODE_ARC600,  NONE, aux_inter_core_interrupt)
 DEF(0x206, ARC_OPCODE_ARCV2,   NONE, irq_priority)
+DEF(0x206, ARC_OPCODE_V3_ALL,  NONE, irq_priority)
 DEF(0x210, ARC_OPCODE_ARC700,  NONE, aes_aux_0)
 DEF(0x211, ARC_OPCODE_ARC700,  NONE, aes_aux_1)
 DEF(0x212, ARC_OPCODE_ARC700,  NONE, aes_aux_2)
@@ -273,10 +283,15 @@ DEF(0x408, ARC_OPCODE_ARC700,  NONE, tlbcommand)
 DEF(0x409, ARC_OPCODE_ARC700,  NONE, pid)
 DEF(0x409, ARC_OPCODE_ARCALL,  NONE, mpuen)
 DEF(0x40a, ARC_OPCODE_ARCV2,   NONE, icause)
+DEF(0x40a, ARC_OPCODE_V3_ALL,  NONE, icause)
 DEF(0x40b, ARC_OPCODE_ARCV2,   NONE, irq_select)
+DEF(0x40b, ARC_OPCODE_V3_ALL,  NONE, irq_select)
 DEF(0x40c, ARC_OPCODE_ARCV2,   NONE, irq_enable)
+DEF(0x40c, ARC_OPCODE_V3_ALL,  NONE, irq_enable)
 DEF(0x40d, ARC_OPCODE_ARCV2,   NONE, irq_trigger)
+DEF(0x40d, ARC_OPCODE_V3_ALL,  NONE, irq_trigger)
 DEF(0x40f, ARC_OPCODE_ARCV2,   NONE, irq_status)
+DEF(0x40f, ARC_OPCODE_V3_ALL,  NONE, irq_status)
 DEF(0x410, ARC_OPCODE_ARCALL,  NONE, xpu)
 DEF(0x412, ARC_OPCODE_ARCALL,  NONE, bta)
 DEF(0x413, ARC_OPCODE_ARC700,  NONE, bta_l1)
@@ -497,12 +512,17 @@ DEF(0xff, ARC_OPCODE_DEFAULT,  NONE, unimp_bcr)
 /* Actual BCR implementations */
 
 DEF(0x6d, ARC_OPCODE_ARCv2HS, NONE, mpu_build)
+DEF(0x6d, ARC_OPCODE_V3_ALL,  NONE, mpu_build)
 DEF(0x6f, ARC_OPCODE_ARCv2HS, NONE, mmu_build)
 DEF(0x75, ARC_OPCODE_ARCALL, NONE, timer_build)
 DEF(0xf3, ARC_OPCODE_ARCV2,  NONE, irq_build)
+DEF(0xf3, ARC_OPCODE_V3_ALL, NONE, irq_build)
 DEF(0x72, ARC_OPCODE_ARCV2,  NONE, d_cache_build)
+DEF(0x72, ARC_OPCODE_V3_ALL, NONE, d_cache_build)
 DEF(0x77, ARC_OPCODE_ARCV2,  NONE, i_cache_build)
+DEF(0x77, ARC_OPCODE_V3_ALL, NONE, i_cache_build)
 DEF(0x7b, ARC_OPCODE_ARCV2,  NONE, mpy_build)
+DEF(0x7b, ARC_OPCODE_V3_ALL, NONE, mpy_build)
 
 /* OLD BCR definitions */
 /*
@@ -538,3 +558,23 @@ DEF (0xfc,  ARC_OPCODE_ARCALL,  NONE, vlc_build)
 DEF (0xfd,  ARC_OPCODE_ARCALL,  NONE, simd_dma_build)
 DEF (0xfe,  ARC_OPCODE_ARCALL,  NONE, ifetch_queue_build)
 */
+
+/* ARCV3 definitions. */
+
+DEF (0x7,   ARC_

[PATCH 24/27] arcv3: IRQ changes and new MMUv6 WIP

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 target/arc/irq.c|  11 +
 target/arc/irq.h|   7 +
 target/arc/mmu-v6.c | 640 
 target/arc/mmu-v6.h |  36 +++
 4 files changed, 694 insertions(+)
 create mode 100644 target/arc/mmu-v6.c
 create mode 100644 target/arc/mmu-v6.h

diff --git a/target/arc/irq.c b/target/arc/irq.c
index 75111a87a8..7fe537d847 100644
--- a/target/arc/irq.c
+++ b/target/arc/irq.c
@@ -30,8 +30,15 @@
 #include "qemu/host-utils.h"
 
 #define CACHE_ENTRY_SIZE (TARGET_LONG_BITS / 8)
+#ifdef TARGET_ARCV2
 #define TARGET_LONG_LOAD(ENV, ADDR) cpu_ldl_data(ENV, ADDR)
 #define TARGET_LONG_STORE(ENV, ADDR, VALUE) cpu_stl_data(ENV, ADDR, VALUE)
+#elif TARGET_ARCV3
+#define TARGET_LONG_LOAD(ENV, ADDR) cpu_ldq_data(ENV, ADDR)
+#define TARGET_LONG_STORE(ENV, ADDR, VALUE) cpu_stq_data(ENV, ADDR, VALUE)
+#else
+#error "This should never happen "
+#endif
 
 /* Static functions and variables. */
 
@@ -181,12 +188,14 @@ static void arc_rtie_irq(CPUARCState *env)
 CPU_BLINK(env) = irq_pop(env, "blink");
 }
 
+#ifdef TARGET_ARCV2
 /* Pop lp_end, lp_start, lp_count if aux_irq_ctrl.l bit is set. */
 if (env->aux_irq_ctrl & (1 << 10)) {
 env->lpe = irq_pop(env, "LP_END");
 env->lps = irq_pop(env, "LP_START");
 CPU_LP(env) = irq_pop(env, "lp");
 }
+#endif
 
 /*
  * Pop EI_BASE, JLI_BASE, LDI_BASE if LP bit is set and Code
@@ -313,12 +322,14 @@ static void arc_enter_irq(ARCCPU *cpu, uint32_t vector)
 irq_push(env, 0xdeadbeef, "dummy EI_BASE");
 }
 
+#ifdef TARGET_ARCV2
 /* Push LP_COUNT, LP_START, LP_END registers if required. */
 if (env->aux_irq_ctrl & (1 << 10)) {
 irq_push(env, CPU_LP(env), "lp");
 irq_push(env, env->lps, "LP_START");
 irq_push(env, env->lpe, "LP_END");
 }
+#endif
 
 /* Push BLINK register if required */
 if (env->aux_irq_ctrl & (1 << 9) && ((env->aux_irq_ctrl & 0x1F) != 16)) {
diff --git a/target/arc/irq.h b/target/arc/irq.h
index d450126b76..770f2f3522 100644
--- a/target/arc/irq.h
+++ b/target/arc/irq.h
@@ -32,6 +32,13 @@ void arc_resetIRQ(ARCCPU *);
 uint32_t pack_status32(ARCStatus *);
 void unpack_status32(ARCStatus *, uint32_t);
 
+#ifdef TARGET_ARCV2
 #define OFFSET_FOR_VECTOR(VECNO) (VECNO << 2)
+#elif TARGET_ARCV3
+#define OFFSET_FOR_VECTOR(VECNO) (VECNO << 3)
+#else
+#error Should never be reached
+#endif
+
 
 #endif
diff --git a/target/arc/mmu-v6.c b/target/arc/mmu-v6.c
new file mode 100644
index 00..525ef640d6
--- /dev/null
+++ b/target/arc/mmu-v6.c
@@ -0,0 +1,640 @@
+/*
+ * QEMU ARC CPU
+ *
+ * Copyright (c) 2020 Cupertino Miranda (cmira...@synopsys.com)
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, see
+ * http://www.gnu.org/licenses/lgpl-2.1.html
+ */
+
+#include "qemu/osdep.h"
+#include "mmu-v6.h"
+#include "target/arc/regs.h"
+#include "qemu/osdep.h"
+#include "cpu.h"
+#include "exec/exec-all.h"
+
+#define LOAD_DATA_IN(ADDR) (address_space_ldq(((CPUState *) cpu)->as, ADDR, 
MEMTXATTRS_UNSPECIFIED, NULL))
+
+#define SET_MMU_EXCEPTION(ENV, N, C, P) { \
+  ENV->mmu.exception.number = N; \
+  ENV->mmu.exception.causecode = C; \
+  ENV->mmu.exception.parameter = P; \
+}
+
+uint32_t mmu_ctrl;
+
+static void disable_mmuv6(void)
+{
+mmu_ctrl &= 0xFFFE;
+}
+
+#define MMU_ENABLED ((mmu_ctrl & 1) != 0)
+#define MMU_IN_USER_KERNEL_MODE ((mmu_ctrl >> 1) & 1)
+
+int mmuv6_enabled(void)
+{
+return MMU_ENABLED;
+}
+
+
+uint32_t mmu_ttbcr;
+
+#define MMU_TTBCR_TNSZ(I) ((mmu_ttbcr>> (I * 16)) & 0x1f)
+#define MMU_TTBCR_TNSH(I) (((mmu_ttbcr >> 4) >> (I * 16)) & 0x3)
+
+#define MMU_TTBCR_A1  ((mmu_ttbcr >> 15) & 0x1)
+
+/*
+static void init_mmu_ttbcr(void)
+{
+// TODO BE DONE
+}
+*/
+
+uint64_t mmu_rtp0;
+uint64_t mmu_rtp1;
+
+uint64_t mmu_fault_status;
+
+#define MASK_FOR_ROOT_ADDRESS(X) \
+  (0x & (~((1 << X) - 1)))
+
+/* TODO: This is for MMU48 only. */
+#define X_FOR_BCR_ZR(I) \
+  (12)
+
+// Grab Root Table Address for RTPN
+#define MMU_RTPN_ROOT_ADDRESS(VADDR, N) \
+(mmu_rtp##N & MASK_FOR_ROOT_ADDRESS(X_FOR_BCR_ZR(1)))
+
+#define MMU_RTP0_ROOT_ADDRESS(VADDR) MMU_RTPN_ROOT_ADDRESS(VADDR, 0)
+#define MMU_RTP1_ROOT_ADDRESS(VADDR) MMU_RTPN_ROOT_ADDRESS(VADDR, 1)
+
+/* TODO: This is for MMU48/52 only. */
+#define MMU_RTPN_ASID(VADDR, N) \
+  ((mmu_rtp##N >> 48) & 0x)
+
+/* Table descriptors accessor

[PATCH 25/27] arcv3: gdbstub changes and new XML files

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 gdb-xml/arc-core-v3.xml   |  45 +
 gdb-xml/arc64-aux-minimal.xml |  32 ++
 gdb-xml/arc64-aux-other.xml   | 177 ++
 target/arc/gdbstub.c  |  23 +
 target/arc/gdbstub.h  |  10 ++
 5 files changed, 287 insertions(+)
 create mode 100644 gdb-xml/arc-core-v3.xml
 create mode 100644 gdb-xml/arc64-aux-minimal.xml
 create mode 100644 gdb-xml/arc64-aux-other.xml

diff --git a/gdb-xml/arc-core-v3.xml b/gdb-xml/arc-core-v3.xml
new file mode 100644
index 00..fdca31b4c3
--- /dev/null
+++ b/gdb-xml/arc-core-v3.xml
@@ -0,0 +1,45 @@
+
+
+
+
+
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+
diff --git a/gdb-xml/arc64-aux-minimal.xml b/gdb-xml/arc64-aux-minimal.xml
new file mode 100644
index 00..56c3f2f698
--- /dev/null
+++ b/gdb-xml/arc64-aux-minimal.xml
@@ -0,0 +1,32 @@
+
+
+
+
+
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+
diff --git a/gdb-xml/arc64-aux-other.xml b/gdb-xml/arc64-aux-other.xml
new file mode 100644
index 00..75a120b894
--- /dev/null
+++ b/gdb-xml/arc64-aux-other.xml
@@ -0,0 +1,177 @@
+
+
+
+
+
+  
+
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+
+
+  
+  
+
+
+
+  
+  
+
+  
+  
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+
+
+
+  
+  
+
+
+
+  
+  
+
+
+  
+  
+
+
+
+
+
+
+
+
+  
+  
+
+
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+  
+
diff --git a/target/arc/gdbstub.c b/target/arc/gdbstub.c
index a09cdb3f45..84e31b02cc 100644
--- a/target/arc/gdbstub.c
+++ b/target/arc/gdbstub.c
@@ -30,7 +30,13 @@
 #define REG_ADDR(reg, processor_type) \
 arc_aux_reg_address_for((reg), (processor_type))
 
+#ifdef TARGET_ARCV2
 #define GDB_GET_REG gdb_get_reg32
+#elif TARGET_ARCV3
+#define GDB_GET_REG gdb_get_reg64
+#else
+#error No target is selected.
+#endif
 
 int arc_cpu_gdb_read_register(CPUState *cs, GByteArray *mem_buf, int n)
 {
@@ -272,6 +278,18 @@ arc_aux_other_gdb_get_reg(CPUARCState *env, GByteArray 
*mem_buf, int regnum)
 case GDB_AUX_OTHER_REG_BTA:
 regval = helper_lr(env, REG_ADDR(AUX_ID_bta, cpu->family));
 break;
+#ifdef TARGET_ARCV3
+/* MMUv6 */
+case GDB_AUX_OTHER_REG_MMU_CTRL:
+regval = helper_lr(env, REG_ADDR(AUX_ID_mmu_ctrl, cpu->family));
+break;
+case GDB_AUX_OTHER_REG_RTP0:
+regval = helper_lr(env, REG_ADDR(AUX_ID_mmu_rtp0, cpu->family));
+break;
+case GDB_AUX_OTHER_REG_RTP1:
+regval = helper_lr(env, REG_ADDR(AUX_ID_mmu_rtp1, cpu->family));
+break;
+#endif
 default:
 assert(!"Unsupported other auxiliary register is being read.");
 }
@@ -395,8 +413,13 @@ arc_aux_other_gdb_set_reg(CPUARCState *env, uint8_t 
*mem_buf, int regnum)
 return 4;
 }
 
+#ifdef TARGET_ARCV2
 #define GDB_TARGET_MINIMAL_XML "arc-v2-aux.xml"
 #define GDB_TARGET_AUX_XML "arc-v2-other.xml"
+#else
+#define GDB_TARGET_MINIMAL_XML "arc64-aux-minimal.xml"
+#define GDB_TARGET_AUX_XML "arc64-aux-other.xml"
+#endif
 
 void arc_cpu_register_gdb_regs_for_features(ARCCPU *cpu)
 {
diff --git a/target/arc/gdbstub.h b/target/arc/gdbstub.h
index 2ced52ee57..ff00c592e1 100644
--- a/target/arc/gdbstub.h
+++ b/target/arc/gdbstub.h
@@ -20,7 +20,11 @@
 #ifndef ARC_GDBSTUB_H
 #define ARC_GDBSTUB_H
 
+#ifdef TARGET_ARCV2
 #define GDB_TARGET_STRING "arc:ARCv2"
+#else
+#define GDB_TARGET_STRING "arc:ARCv3_64"
+#endif
 
 enum gdb_regs {
 GDB_REG_0 = 0,
@@ -147,6 +151,12 @@ enum gdb_aux_other_regs {
 GDB_AUX_OTHER_REG_TLBPD1,   /* page descriptor 1 */
 GDB_AUX_OTHER_REG_TLB_INDEX,/* tlb index */
 GDB_AUX_OTHER_REG_TLB_CMD,  /* tlb command   */
+#ifdef TARGET_ARCV3
+/* mmuv6 */
+GDB_AUX_OTHER_REG_MMU_CTRL, /* mmuv6 control */
+GDB_AUX_OTHER_REG_RTP0, /* region 0 ptr  */
+GDB_AUX_OTHER_REG_RTP1, /* region 1 ptr  */
+#endif
 
 GDB_AUX_OTHER_REG_LAST
 };
-- 
2.20.1


___
linux-snps-arc mailing list
linux-snps-arc@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-snps-arc


[PATCH 27/27] arcv3: Add support for ARCv3

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 configure | 2 ++
 default-configs/devices/arcv3-softmmu.mak | 7 +++
 default-configs/targets/arcv3-softmmu.mak | 3 +++
 include/disas/dis-asm.h   | 2 ++
 include/elf.h | 1 +
 meson.build   | 3 ++-
 6 files changed, 17 insertions(+), 1 deletion(-)
 create mode 100644 default-configs/devices/arcv3-softmmu.mak
 create mode 100644 default-configs/targets/arcv3-softmmu.mak

diff --git a/configure b/configure
index 80d993fac7..cec3199434 100755
--- a/configure
+++ b/configure
@@ -682,6 +682,8 @@ elif check_define __aarch64__ ; then
   cpu="aarch64"
 elif check_define __arc__ ; then
   cpu="arc"
+elif check_define __arc64__ ; then
+  cpu="arc64"
 else
   cpu=$(uname -m)
 fi
diff --git a/default-configs/devices/arcv3-softmmu.mak 
b/default-configs/devices/arcv3-softmmu.mak
new file mode 100644
index 00..0ce4176b2d
--- /dev/null
+++ b/default-configs/devices/arcv3-softmmu.mak
@@ -0,0 +1,7 @@
+# Default configuration for arc-softmmu
+
+CONFIG_SEMIHOSTING=n
+
+# Boards:
+#
+CONFIG_ARC_VIRT=y
diff --git a/default-configs/targets/arcv3-softmmu.mak 
b/default-configs/targets/arcv3-softmmu.mak
new file mode 100644
index 00..af39b7c34d
--- /dev/null
+++ b/default-configs/targets/arcv3-softmmu.mak
@@ -0,0 +1,3 @@
+TARGET_ARCH=arcv3
+TARGET_BASE_ARCH=arc
+TARGET_XML_FILES= gdb-xml/arc-core-v3.xml gdb-xml/arc64-aux-minimal.xml 
gdb-xml/arc64-aux-other.xml
diff --git a/include/disas/dis-asm.h b/include/disas/dis-asm.h
index 8a0aa19bc2..15ec34c185 100644
--- a/include/disas/dis-asm.h
+++ b/include/disas/dis-asm.h
@@ -214,6 +214,8 @@ enum bfd_architecture
 #define bfd_mach_arc_arcv2 5
 #define bfd_mach_arc_arcv2em   6
 #define bfd_mach_arc_arcv2hs   7
+#define bfd_mach_arcv3_64  0x10
+#define bfd_mach_arcv3_32  0x20
   bfd_arch_m32r,   /* Mitsubishi M32R/D */
 #define bfd_mach_m32r  0  /* backwards compatibility */
   bfd_arch_mn10200,/* Matsushita MN10200 */
diff --git a/include/elf.h b/include/elf.h
index 8c7c4ab8a9..14643f4c17 100644
--- a/include/elf.h
+++ b/include/elf.h
@@ -210,6 +210,7 @@ typedef struct mips_elf_abiflags_v0 {
 
 #define EM_ARC_COMPACT  93  /* Synopsys ARCompact */
 #define EM_ARC_COMPACT2 195 /* Synopsys ARCompact V2 */
+#define EM_ARC_COMPACT3_64 253 /* Synopsys ARCompact V3 ARC64 */
 
 #define EM_MOXIE   223 /* Moxie processor family */
 #define EM_MOXIE_OLD   0xFEED
diff --git a/meson.build b/meson.build
index a25425022e..5290ad9939 100644
--- a/meson.build
+++ b/meson.build
@@ -57,7 +57,7 @@ python = import('python').find_installation()
 
 supported_oses = ['windows', 'freebsd', 'netbsd', 'openbsd', 'darwin', 
'sunos', 'linux']
 supported_cpus = ['ppc', 'ppc64', 's390x', 'sparc64', 'riscv32', 'riscv64', 
'x86', 'x86_64',
-  'arc', 'arm', 'aarch64', 'mips', 'mips64', 'sparc', 'sparc64']
+  'arc', 'arc64', 'arm', 'aarch64', 'mips', 'mips64', 'sparc', 'sparc64']
 
 cpu = host_machine.cpu_family()
 targetos = host_machine.system()
@@ -1191,6 +1191,7 @@ config_target_mak = {}
 disassemblers = {
   'alpha' : ['CONFIG_ALPHA_DIS'],
   'arc' : ['CONFIG_ARC_DIS'],
+  'arc64' : ['CONFIG_ARC_DIS'],
   'arm' : ['CONFIG_ARM_DIS'],
   'avr' : ['CONFIG_AVR_DIS'],
   'cris' : ['CONFIG_CRIS_DIS'],
-- 
2.20.1


___
linux-snps-arc mailing list
linux-snps-arc@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-snps-arc


[PATCH 18/27] arcv3: Decoder code

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 disas/arc.c|   51 +-
 target/arc/decoder-v3.c| 1547 
 target/arc/decoder-v3.h|  322 
 target/arc/flags-v3.def|  103 +++
 target/arc/operands-v3.def |  133 
 5 files changed, 2147 insertions(+), 9 deletions(-)
 create mode 100644 target/arc/decoder-v3.c
 create mode 100644 target/arc/decoder-v3.h
 create mode 100644 target/arc/flags-v3.def
 create mode 100644 target/arc/operands-v3.def

diff --git a/disas/arc.c b/disas/arc.c
index f8b2e31be9..9a9c289948 100644
--- a/disas/arc.c
+++ b/disas/arc.c
@@ -308,8 +308,15 @@ static int arc_read_mem(bfd_vma memaddr,
 case bfd_mach_arc_arcv2hs:
 *isa_mask = ARC_OPCODE_ARCv2HS;
 break;
+case bfd_mach_arcv3_64:
+*isa_mask = ARC_OPCODE_V3_ARC64;
+break;
+case bfd_mach_arcv3_32:
+*isa_mask = ARC_OPCODE_V3_ARC32;
+break;
+
 default:
-*isa_mask = ARC_OPCODE_ARCv2EM;
+*isa_mask = ARC_OPCODE_NONE;
 break;
 }
 
@@ -390,15 +397,41 @@ int print_insn_arc(bfd_vma memaddr, struct 
disassemble_info *info)
 opcode = arc_find_format(&dis_insn, insn, insn_len, isa_mask);
 
 /* If limm is required, read it. */
-if (dis_insn.limm_p) {
-bfd_byte buffer[4];
-int status = (*info->read_memory_func)(memaddr + insn_len, buffer,
-   4, info);
-if (status != 0) {
-return -1;
+if((isa_mask & ARC_OPCODE_V3_ALL) != 0) {
+if (dis_insn.unsigned_limm_p) {
+bfd_byte buffer[4];
+int status = (*info->read_memory_func)(memaddr + insn_len, buffer,
+   4, info);
+if (status != 0) {
+return -1;
+}
+dis_insn.limm = ARRANGE_ENDIAN (info, buffer);
+insn_len += 4;
+}
+else if (dis_insn.signed_limm_p) {
+bfd_byte buffer[4];
+int status = (*info->read_memory_func)(memaddr + insn_len, buffer,
+   4, info);
+if (status != 0) {
+return -1;
+}
+dis_insn.limm = ARRANGE_ENDIAN (info, buffer);
+if(dis_insn.limm & 0x8000)
+  dis_insn.limm += 0x;
+insn_len += 4;
+}
+
+} else {
+if (dis_insn.limm_p) {
+bfd_byte buffer[4];
+int status = (*info->read_memory_func)(memaddr + insn_len, buffer,
+   4, info);
+if (status != 0) {
+return -1;
+}
+dis_insn.limm = ARRANGE_ENDIAN(info, buffer);
+insn_len += 4;
 }
-dis_insn.limm = ARRANGE_ENDIAN(info, buffer);
-insn_len += 4;
 }
 
 /* Print the mnemonic. */
diff --git a/target/arc/decoder-v3.c b/target/arc/decoder-v3.c
new file mode 100644
index 00..ae058c706d
--- /dev/null
+++ b/target/arc/decoder-v3.c
@@ -0,0 +1,1547 @@
+/*
+ * Decoder for the ARC.
+ * Copyright (C) 2017 Free Software Foundation, Inc.
+
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public License
+ * as published by the Free Software Foundation; either version 2.1 of
+ * the License, or (at your option) any later version.
+
+ * This library 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
+ * Lesser General Public License for more details.
+
+ * You should have received a copy of the GNU General Public License
+ * along with GAS or GDB; see the file COPYING3.  If not, write to
+ * the Free Software Foundation, 51 Franklin Street - Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
+#include "qemu/osdep.h"
+#include "target/arc/decoder.h"
+#include "qemu/osdep.h"
+#include "qemu/bswap.h"
+#include "cpu.h"
+
+/* Register names. */
+static const char * const regnames[64] = {
+"r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
+"r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
+"r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
+"r24", "r25",
+"gp",
+"fp", "sp", "ilink", "r30", "blink",
+
+"r32", "r33", "r34", "r35", "r36", "r37", "r38", "r39",
+"r40", "r41", "r42", "r43", "r44", "r45", "r46", "r47",
+"r48", "r49", "r50", "r51", "r52", "r53", "r54", "r55",
+"r56", "r57", "r58", "r59", "lp_count", "rezerved", "LIMM", "pcl"
+};
+const char *get_register_name(int value)
+{
+return regnames[value];
+}
+
+extern bool special_flag_p(const char *opname, const char *flgname);
+
+static long long int
+extract_rb (unsigned long long insn ATTRIBUTE_UNUSED,
+   bfd_boolean * invalid ATTRIBUTE_UNUSED)
+{
+  int value = (((insn >> 12) & 0x07) << 3) | (

[PATCH 20/27] arcv3: TCG, decoder glue code and helper changes

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 target/arc/extra_mapping.def  |  16 +
 target/arc/helper.c   |  11 +
 target/arc/helper.h   |  16 +
 target/arc/op_helper.c| 110 ++-
 target/arc/semfunc-v2_mapping.def | 321 
 target/arc/semfunc-v3_mapping.def | 468 ++
 target/arc/semfunc_mapping.def| 308 +---
 7 files changed, 937 insertions(+), 313 deletions(-)
 create mode 100644 target/arc/semfunc-v2_mapping.def
 create mode 100644 target/arc/semfunc-v3_mapping.def

diff --git a/target/arc/extra_mapping.def b/target/arc/extra_mapping.def
index 50517f058e..527a70f304 100644
--- a/target/arc/extra_mapping.def
+++ b/target/arc/extra_mapping.def
@@ -43,6 +43,7 @@ MAPPING(swi, SWI, 1, 0)
 CONSTANT(SWI, swi_s, 0, 0)
 MAPPING(swi_s, SWI, 1, 0)
 
+#ifdef TARGET_ARCV2
 SEMANTIC_FUNCTION(VADD2, 3)
 SEMANTIC_FUNCTION(VADD2H, 3)
 SEMANTIC_FUNCTION(VADD4H, 3)
@@ -61,3 +62,18 @@ MAPPING(vsub2h, VSUB2H, 3, 0, 1, 2)
 MAPPING(vsub4h, VSUB4H, 3, 0, 1, 2)
 MAPPING(mpyd, MPYD, 3, 0, 1, 2)
 MAPPING(mpydu, MPYDU, 3, 0, 1, 2)
+#endif
+
+#ifdef TARGET_ARCV3
+SEMANTIC_FUNCTION(MPYL, 3)
+SEMANTIC_FUNCTION(MPYML, 3)
+SEMANTIC_FUNCTION(MPYMUL, 3)
+SEMANTIC_FUNCTION(MPYMSUL, 3)
+SEMANTIC_FUNCTION(ADDHL, 3)
+
+MAPPING(mpyl, MPYL, 3, 0, 1, 2)
+MAPPING(mpyml, MPYML, 3, 0, 1, 2)
+MAPPING(mpymul, MPYMUL, 3, 0, 1, 2)
+MAPPING(mpymsul, MPYMSUL, 3, 0, 1, 2)
+MAPPING(addhl, ADDHL, 3, 0, 1, 2)
+#endif
diff --git a/target/arc/helper.c b/target/arc/helper.c
index e11d21d576..10c46cbee4 100644
--- a/target/arc/helper.c
+++ b/target/arc/helper.c
@@ -80,12 +80,23 @@ void arc_cpu_do_interrupt(CPUState *cs)
 case EXCP_MACHINE_CHECK:
 name = "Machine Check";
 break;
+#ifdef TARGET_ARCV2
 case EXCP_TLB_MISS_I:
 name = "TLB Miss Instruction";
 break;
 case EXCP_TLB_MISS_D:
 name = "TLB Miss Data";
 break;
+#elif TARGET_ARCV3
+case EXCP_IMMU_FAULT:
+name = "Instruction MMU Fault";
+break;
+case EXCP_DMMU_FAULT:
+name = "Data MMU Fault";
+break;
+#else
+#error
+#endif
 case EXCP_PROTV:
 name = "Protection Violation";
 break;
diff --git a/target/arc/helper.h b/target/arc/helper.h
index 1929c1682f..2d93fc3a96 100644
--- a/target/arc/helper.h
+++ b/target/arc/helper.h
@@ -37,3 +37,19 @@ DEF_HELPER_FLAGS_3(overflow_sub_flag, TCG_CALL_NO_RWG_SE, 
tl, tl, tl, tl)
 DEF_HELPER_FLAGS_3(mpymu, TCG_CALL_NO_RWG_SE, tl, env, tl, tl)
 DEF_HELPER_FLAGS_3(mpym, TCG_CALL_NO_RWG_SE, tl, env, tl, tl)
 DEF_HELPER_FLAGS_3(repl_mask, TCG_CALL_NO_RWG_SE, tl, tl, tl, tl)
+
+/* ARCV3 helpers */
+#ifdef TARGET_ARCV3
+DEF_HELPER_FLAGS_2(ffs32, TCG_CALL_NO_RWG_SE, tl, env, tl)
+
+DEF_HELPER_FLAGS_3(carry_add_flag32, TCG_CALL_NO_RWG_SE, tl, tl, tl, tl)
+DEF_HELPER_FLAGS_3(carry_sub_flag32, TCG_CALL_NO_RWG_SE, tl, tl, tl, tl)
+DEF_HELPER_FLAGS_3(overflow_add_flag32, TCG_CALL_NO_RWG_SE, tl, tl, tl, tl)
+DEF_HELPER_FLAGS_3(overflow_sub_flag32, TCG_CALL_NO_RWG_SE, tl, tl, tl, tl)
+
+DEF_HELPER_FLAGS_2(rotate_left32, TCG_CALL_NO_RWG_SE, i64, i64, i64)
+DEF_HELPER_FLAGS_2(rotate_right32, TCG_CALL_NO_RWG_SE, i64, i64, i64)
+DEF_HELPER_FLAGS_2(asr_32, TCG_CALL_NO_RWG_SE, i64, i64, i64)
+
+DEF_HELPER_2(norml, i64, env, i64)
+#endif
diff --git a/target/arc/op_helper.c b/target/arc/op_helper.c
index 1124541993..6d68018334 100644
--- a/target/arc/op_helper.c
+++ b/target/arc/op_helper.c
@@ -188,7 +188,9 @@ void helper_rtie(CPUARCState *env)
   (target_ulong) pack_status32(&env->stat));
 }
 
+#ifdef TARGET_ARCV2
 helper_zol_verify(env, env->pc);
+#endif
 }
 
 void helper_flush(CPUARCState *env)
@@ -390,17 +392,103 @@ arc_status_regs_set(const struct arc_aux_reg_detail 
*aux_reg_detail,
 }
 }
 
-/*
- * uint32_t lf_variable = 0;
- * uint32_t helper_get_lf(void)
- * {
- *   return lf_variable;
- * }
- * void helper_set_lf(uint32_t v)
- * {
- *   lf_variable = v;
- * }
- */
+#ifdef TARGET_ARCV3
+uint64_t helper_carry_add_flag32(uint64_t dest, uint64_t b, uint64_t c) {
+return carry_add_flag(dest, b, c, 32);
+}
+
+target_ulong helper_overflow_add_flag32(target_ulong dest, target_ulong b, 
target_ulong c) {
+return overflow_add_flag(dest, b, c, 32);
+}
+
+target_ulong helper_overflow_sub_flag32(target_ulong dest, target_ulong b, 
target_ulong c) {
+dest = dest & 0x;
+b = b & 0x;
+c = c & 0x;
+return overflow_sub_flag(dest, b, c, 32);
+}
+
+uint64_t helper_carry_sub_flag32(uint64_t dest, uint64_t b, uint64_t c)
+{
+uint32_t t1, t2, t3;
+
+t1 = ~b;
+t2 = t1 & c;
+t3 = (t1 | c) & dest;
+
+t2 = t2 | t3;
+return (t2 >> 31) & 1;
+}
+
+uint64_t helper_rotate_left32(uint64_t orig, uint64_t n)
+{
+uint64_t t;
+uint64_t dest = (orig << n) & ((0x << n) & 0x);
+
+t = (orig >> (32 - n)) & ((1 << n) - 1);
+dest |= t;
+
+return dest;
+}
+
+uint64_t helper_rotate_right3

[PATCH 26/27] arcv3: board changes

2021-04-05 Thread cupertinomiranda
From: Cupertino Miranda 

---
 hw/arc/boot.c | 1 +
 hw/arc/virt.c | 4 
 2 files changed, 5 insertions(+)

diff --git a/hw/arc/boot.c b/hw/arc/boot.c
index 962fc03b03..0af559e44b 100644
--- a/hw/arc/boot.c
+++ b/hw/arc/boot.c
@@ -69,6 +69,7 @@ void arc_load_kernel(ARCCPU *cpu, struct arc_boot_info *info)
 }
 
 elf_machine = cpu->family > 2 ? EM_ARC_COMPACT2 : EM_ARC_COMPACT;
+elf_machine = (cpu->family & ARC_OPCODE_V3_ALL) != 0 ? EM_ARC_COMPACT3_64 
: elf_machine;
 kernel_size = load_elf(info->kernel_filename, NULL, NULL, NULL,
&entry, NULL, NULL, NULL, ARC_ENDIANNESS_LE,
elf_machine, 1, 0);
diff --git a/hw/arc/virt.c b/hw/arc/virt.c
index 8f7d7cbd5d..e07fa5c123 100644
--- a/hw/arc/virt.c
+++ b/hw/arc/virt.c
@@ -120,7 +120,11 @@ static void virt_init(MachineState *machine)
 boot_info.kernel_cmdline = machine->kernel_cmdline;
 
 for (n = 0; n < smp_cpus; n++) {
+#ifdef TARGET_ARCV2
 cpu = ARC_CPU(cpu_create("archs-" TYPE_ARC_CPU));
+#else
+cpu = ARC_CPU(cpu_create("arc64-" TYPE_ARC_CPU));
+#endif
 if (cpu == NULL) {
 fprintf(stderr, "Unable to find CPU definition!\n");
 exit(1);
-- 
2.20.1


___
linux-snps-arc mailing list
linux-snps-arc@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-snps-arc