diff --git a/sim/testsuite/configure b/sim/testsuite/configure
index bbc3bea48d..e37bdbd8d8 100755
--- a/sim/testsuite/configure
+++ b/sim/testsuite/configure
@@ -1888,6 +1888,10 @@ case "${target}" in
    msp430*-*-*)
        sim_arch=msp430
        ;;
+   or1k-*-* | or1knd-*-*)
+       sim_arch=or1k
+       sim_testsuite=yes
+       ;;
    rl78-*-*)
        sim_arch=rl78
        ;;
diff --git a/sim/testsuite/sim/or1k/add.S b/sim/testsuite/sim/or1k/add.S
new file mode 100644
index 0000000000..c9d65e67b6
--- /dev/null
+++ b/sim/testsuite/sim/or1k/add.S
@@ -0,0 +1,639 @@
+/* Tests instructions l.add, l.addc, l.addi and l.addic.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000001);\n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x3fffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x40000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xc0000000);\n
+# output: report(0xc0000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xbfffffff);\n
+# output: report(0xbfffffff);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x40000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xbfffffff);\n
+# output: report(0xbfffffff);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x3fffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x3fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x40000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xc0000000);\n
+# output: report(0xc0000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xc0000000);\n
+# output: report(0xbfffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xbfffffff);\n
+# output: report(0xbfffffff);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x40000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x3fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xbfffffff);\n
+# output: report(0xbfffffff);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x0000fffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fff8000);\n
+# output: report(0x00007fff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fffc000);\n
+# output: report(0x00004000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80008000);\n
+# output: report(0x00008000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80007fff);\n
+# output: report(0x00008000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fffc000);\n
+# output: report(0x00004000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x0000fffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80007fff);\n
+# output: report(0x00008000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x0000fffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fff8000);\n
+# output: report(0x00007fff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fff8000);\n
+# output: report(0x00007fff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fffc000);\n
+# output: report(0x00004000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x0000ffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80008000);\n
+# output: report(0x00008000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80007fff);\n
+# output: report(0x00008000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80007fff);\n
+# output: report(0x00008000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fffc000);\n
+# output: report(0x00004000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x7fffc000);\n
+# output: report(0x00003fff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x0000fffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x0000ffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80007fff);\n
+# output: report(0x00008000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .exception_vectors
+
+	/* Range exception.  */
+	.org	0xb00
+
+	/* The handling is a bit dubious at present.  We just patch the
+	   instruction with l.nop and restart.  This will go wrong in branch
+	   delay slots.  But we don't have those in this test.  */
+	l.addi r1, r1, -EXCEPTION_STACK_SKIP_SIZE
+	PUSH r2
+	PUSH r3
+	/* Save the address of the instruction that caused the problem.  */
+	MOVE_FROM_SPR r2, SPR_EPCR_BASE
+	LOAD_IMMEDIATE r3, 0x15000000 /* Opcode for l.nop  */
+	l.sw	0(r2), r3
+	POP r3
+	POP r2
+	l.addi r1, r1, EXCEPTION_STACK_SKIP_SIZE
+	l.rfe
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test l.add  */
+
+	/* Add two small positive numbers  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, 1, 2
+
+	/* The carry flag should be ignored.  */
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.add, 1, 2
+
+	/* Add two small negative numbers, which should set the carry flag
+	   but not the overflow flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, -1, -2
+
+	/* Add two quite large positive numbers.  Should set neither the
+	   overflow nor the carry flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, 0x40000000, \
+	  0x3fffffff
+
+	/* Add two large positive numbers.  Should set the overflow, but
+	   not the carry flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, 0x40000000, \
+	  0x40000000
+
+	/* Add two quite large negative numbers.  Should set the carry, but
+	   not the overflow flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, -1073741824, \
+	  -1073741824 /* -1073741824 = 0xC0000000  */
+
+	/* Add two large negative numbers.  Should set both the overflow
+	   and carry flags.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, 0xbfffffff, \
+	  0xbfffffff
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that an overflow alone causes a RANGE Exception.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, 0x40000000, \
+	  0x40000000
+
+	/* Check that a carry alone does not cause a RANGE Exception.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, 0xffffffff, \
+	  0xfffffffe
+
+	/* Check that carry and overflow together cause an exception.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.add, 0xbfffffff, \
+	  0xbfffffff
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test l.addc  */
+
+	/* Add two small positive numbers  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV,  l.addc, 1, 2
+
+	/* Add two small negative numbers.  Sets the carry flag but not the
+	   overflow flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, -1, -2
+
+	/* Add two quite large positive numbers.  Should set neither the
+	   overflow nor the carry flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, 0x40000000, \
+	  0x3fffffff
+
+	/* Add two quite large positive numbers with a carry in.  Should
+	   set the overflow but not the carry flag.  */
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.addc, 0x40000000, \
+	  0x3fffffff
+
+	/* Add two large positive numbers.  Should set the overflow, but
+	   not the carry flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, 0x40000000, \
+	  0x40000000
+
+	/* Add the largest unsigned value to zero with a carry.  This
+	   potentially can break a simplistic test for carry that does not
+	   consider the carry flag properly.  Do it both ways around.  */
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.addc, -1,  0
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.addc,  0, -1
+
+	/* Add two quite large negative numbers.  Should set the carry, but
+	   not the overflow flag.  Here -1073741824 is 0xC0000000.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, -1073741824, \
+	  -1073741824
+
+	/* Add two quite large negative numbers that would overflow, with a
+	   carry that just avoids the overflow.  Should set the carry, but
+	   not the overflow flag.  Here -1073741824 is 0xC0000000 and
+	   -1073741825 is 0xBFFFFFFF.  */
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.addc, -1073741824, \
+	  -1073741825
+
+	/* Add two large negative numbers.  Should set both the overflow
+	   and carry flags.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, -1073741825, \
+	  -1073741825
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that an overflow alone causes a RANGE Exception, even when
+	   it is the carry that causes the overflow.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, 0x40000000, \
+	  0x40000000
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.addc, 0x40000000, \
+	  0x3fffffff
+
+	/* Check that a carry alone does not cause a RANGE Exception, even
+	   when it is the carry that causes the overflow.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, 0xffffffff, \
+	  0xfffffffe
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.addc, 0x00000000, \
+	  0xffffffff
+
+	/* Check that carry and overflow together cause an exception.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.addc, 0xbfffffff, \
+	  0xbfffffff
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test l.addi  */
+
+	/* Add two small positive numbers  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 1, 2
+
+	/* Check carry in is ignored.  */
+	TEST_INST_FF_I32_I16 SPR_SR_CY, SPR_SR_OV, l.addi, 1, 2
+
+	/* Add two small negative numbers.  Sets the carry flag but not the
+	   overflow flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0xffffffff, \
+	  0xfffe
+
+	/* Add two quite large positive numbers.  Should set neither the
+	   overflow nor the carry flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0x7fff8000, \
+	  0x7fff
+
+	/* Add two large positive numbers.  Should set the overflow, but
+	   not the carry flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0x7fffc000, \
+	  0x4000
+
+	/* Add two quite large negative numbers.  Should set the carry, but
+	   not the overflow flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0x80008000, \
+	  0x8000
+
+	/* Add two large negative numbers.  Should set both the overflow
+	   and carry flags.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0x80007fff, \
+	  0x8000
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that an overflow alone causes a RANGE Exception.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0x7fffc000, \
+	  0x4000
+
+	/* Check that a carry alone does not cause a RANGE Exception.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0xffffffff, \
+	  0xfffe
+
+	/* Check that carry and overflow together cause an exception.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addi, 0x80007fff, \
+	  0x8000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test l.addi */
+
+	/* Add two small positive numbers  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 1, 2
+
+	/* Add two small negative numbers.  Sets the carry flag but not the
+	   overflow flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0xffffffff, \
+	  0xfffe
+
+	/* Add two quite large positive numbers.  Should set neither the
+	   overflow nor the carry flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0x7fff8000, \
+	  0x7fff
+
+	/* Add two quite large positive numbers with a carry in.  Should
+	   set the overflow but not the carry flag.  */
+	TEST_INST_FF_I32_I16 SPR_SR_CY, SPR_SR_OV, l.addic, 0x7fff8000, 0x7fff
+
+	/* Add two large positive numbers.  Should set the overflow, but
+	   not the carry flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0x7fffc000, \
+	  0x4000
+
+	/* Add the largest unsigned value to zero with a carry.  This
+	   potentially can break a simplistic test for carry that does not
+	   consider the carry flag properly.  Do it both ways around.  */
+	TEST_INST_FF_I32_I16 SPR_SR_CY, SPR_SR_OV, l.addic, 0xffffffff, 0x0000
+	TEST_INST_FF_I32_I16 SPR_SR_CY, SPR_SR_OV, l.addic, 0x00000000, 0xffff
+
+	/* Add two quite large negative numbers.  Should set the carry, but
+	   not the overflow flag.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0x80008000, \
+	  0x8000
+
+	/* Add two quite large negative numbers that would overflow, with a
+	   carry that just avoids the overflow.  This should set the carry,
+	   but not the overflow flag.  */
+	TEST_INST_FF_I32_I16 SPR_SR_CY, SPR_SR_OV, l.addic, 0x80007fff, 0x8000
+
+	/* Add two large negative numbers.  Should set both the overflow
+	   and carry flags.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0x80007fff, \
+	  0x8000
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that an overflow alone causes a RANGE Exception, even when
+	   it is the carry that causes the overflow.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0x7fffc000, \
+	  0x4000
+	TEST_INST_FF_I32_I16 SPR_SR_CY, SPR_SR_OV, l.addic, 0x7fffc000, 0x3fff
+
+	/* Check that a carry alone does not cause a RANGE Exception, even
+	   when it is the carry that causes the overflow.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0xffffffff, \
+	  0xfffe
+	TEST_INST_FF_I32_I16 SPR_SR_CY, SPR_SR_OV, l.addic, 0x00000000, 0xffff
+
+	/* Check that carry and overflow together cause an exception.  */
+	TEST_INST_FF_I32_I16 0, SPR_SR_CY | SPR_SR_OV, l.addic, 0x80007fff, \
+	  0x8000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/alltests.exp b/sim/testsuite/sim/or1k/alltests.exp
new file mode 100644
index 0000000000..4480590050
--- /dev/null
+++ b/sim/testsuite/sim/or1k/alltests.exp
@@ -0,0 +1,34 @@
+# OR1K simulator testsuite.
+#
+# Copyright 2017 Free Software Foundation, Inc.
+#
+# 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 3 of the License, 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 <http://www.gnu.org/licenses/>.
+
+if [istarget or1k*-*-*] {
+
+    set all_machs "or1k"
+
+    global global_ld_options
+    set global_ld_options "-T $srcdir/$subdir/or1k-test.ld"
+
+    foreach src [lsort [glob -nocomplain $srcdir/$subdir/*.S]] {
+
+	if ![runtest_file_p $runtests $src] {
+	    continue
+	}
+
+	run_sim_test $src $all_machs
+    }
+
+}
diff --git a/sim/testsuite/sim/or1k/and.S b/sim/testsuite/sim/or1k/and.S
new file mode 100644
index 0000000000..c692fb6c76
--- /dev/null
+++ b/sim/testsuite/sim/or1k/and.S
@@ -0,0 +1,198 @@
+/* Tests instructions l.and, l.andi.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x55555555);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xc4c70f07);\n
+# output: report(0x44400004);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x38f0f83b);\n
+# output: report(0x30800803);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x0000ffff);\n
+# output: report(0x0000ffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x0000aaaa);\n
+# output: report(0x0000aaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00005555);\n
+# output: report(0x00005555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00005555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000f83);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000f07);\n
+# output: report(0x00000004);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000f83b);\n
+# output: report(0x00000803);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Always set OVE.  We should never trigger an exception, even if
+	   this bit is set.  */
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test the l.and instruction with a range of operands.  */
+	TEST_INST_I32_I32 l.and, 0x00000000, 0x00000000
+	TEST_INST_I32_I32 l.and, 0xffffffff, 0xffffffff
+	TEST_INST_I32_I32 l.and, 0xaaaaaaaa, 0x00000000
+	TEST_INST_I32_I32 l.and, 0xaaaaaaaa, 0xaaaaaaaa
+	TEST_INST_I32_I32 l.and, 0x55555555, 0x00000000
+	TEST_INST_I32_I32 l.and, 0x55555555, 0x55555555
+	TEST_INST_I32_I32 l.and, 0xaaaaaaaa, 0x55555555
+	TEST_INST_I32_I32 l.and, 0x4c70f07c, 0xb38f0f83
+	TEST_INST_I32_I32 l.and, 0x4c70f07c, 0xc4c70f07
+	TEST_INST_I32_I32 l.and, 0xb38f0f83, 0x38f0f83b
+
+	/* Test the l.andi instruction with a range of operands.  */
+	TEST_INST_I32_I16 l.andi, 0x00000000, 0x0000
+	TEST_INST_I32_I16 l.andi, 0xffffffff, 0xffff
+	TEST_INST_I32_I16 l.andi, 0xaaaaaaaa, 0x0000
+	TEST_INST_I32_I16 l.andi, 0xaaaaaaaa, 0xaaaa
+	TEST_INST_I32_I16 l.andi, 0x55555555, 0x0000
+	TEST_INST_I32_I16 l.andi, 0x55555555, 0x5555
+	TEST_INST_I32_I16 l.andi, 0xaaaaaaaa, 0x5555
+	TEST_INST_I32_I16 l.andi, 0x4c70f07c, 0x0f83
+	TEST_INST_I32_I16 l.andi, 0x4c70f07c, 0x0f07
+	TEST_INST_I32_I16 l.andi, 0xb38f0f83, 0xf83b
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/basic.S b/sim/testsuite/sim/or1k/basic.S
new file mode 100644
index 0000000000..5aaa55c362
--- /dev/null
+++ b/sim/testsuite/sim/or1k/basic.S
@@ -0,0 +1,522 @@
+/* Tests some basic CPU instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0xffff0012);\n
+# output: report(0x12352af7);\n
+# output: report(0x7ffffffe);\n
+# output: report(0xffffa5a7);\n
+# output: report(0x000fffff);\n
+# output: report(0x00002800);\n
+# output: report(0x00000009);\n
+# output: report(0xdeaddead);\n
+# output: report(0xffff0000);\n
+# output: report(0x12345678);\n
+# output: report(0xabcdf0bd);\n
+# output: exit(0)\n
+
+#include "or1k-asm-test-env.h"
+
+#define FIRST_RAM_ADDR 0x00000000
+
+	STANDARD_TEST_HEADER
+
+	/* Early test begin.  */
+
+	/* Do this test upfront, as it modifies STACK_POINTER_R1.  */
+
+	l.addi  r1 , r0 , 0x1
+	l.addi  r2 , r1 , 0x2
+	l.addi  r3 , r2 , 0x4
+	l.addi  r4 , r3 , 0x8
+	l.addi  r5 , r4 , 0x10
+	l.addi  r6 , r5 , 0x20
+	l.addi  r7 , r6 , 0x40
+	l.addi  r8 , r7 , 0x80
+	l.addi  r9 , r8 , 0x100
+	l.addi  r10, r9 , 0x200
+	l.addi  r11, r10, 0x400
+	l.addi  r12, r11, 0x800
+	l.addi  r13, r12, 0x1000
+	l.addi  r14, r13, 0x2000
+	l.addi  r15, r14, 0x4000
+	l.addi  r16, r15, 0x8000
+
+	l.sub   r31, r0 , r1
+	l.sub   r30, r31, r2
+	l.sub   r29, r30, r3
+	l.sub   r28, r29, r4
+	l.sub   r27, r28, r5
+	l.sub   r26, r27, r6
+	l.sub   r25, r26, r7
+	l.sub   r24, r25, r8
+	l.sub   r23, r24, r9
+	l.sub   r22, r23, r10
+	l.sub   r21, r22, r11
+	l.sub   r20, r21, r12
+	l.sub   r19, r20, r13
+	l.sub   r18, r19, r14
+	l.sub   r17, r18, r15
+	l.sub   r16, r17, r16
+
+	/* We cannot use REPORT_REG_TO_CONSOLE here, as the stack is not
+	   set up yet.  */
+	MOVE_REG NOP_REPORT_R3, r16
+	REPORT_TO_CONSOLE /* Should be 0xffff0012  */
+
+	/* Early test end.  */
+
+	STANDARD_TEST_BODY
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Read and write from RAM.  */
+
+	LOAD_IMMEDIATE r31, FIRST_RAM_ADDR
+	l.sw    0(r31), r16
+
+	l.movhi r3,0x1234
+	l.ori   r3,r3,0x5678
+
+	l.sw    4(r31),r3
+
+	l.lbz   r4,4(r31)
+	l.add   r8,r8,r4
+	l.sb    11(r31),r4
+	l.lbz   r4,5(r31)
+	l.add   r8,r8,r4
+	l.sb    10(r31),r4
+	l.lbz   r4,6(r31)
+	l.add   r8,r8,r4
+	l.sb    9(r31),r4
+	l.lbz   r4,7(r31)
+	l.add   r8,r8,r4
+	l.sb    8(r31),r4
+
+	l.lbs   r4,8(r31)
+	l.add   r8,r8,r4
+	l.sb    7(r31),r4
+	l.lbs   r4,9(r31)
+	l.add   r8,r8,r4
+	l.sb    6(r31),r4
+	l.lbs   r4,10(r31)
+	l.add   r8,r8,r4
+	l.sb    5(r31),r4
+	l.lbs   r4,11(r31)
+	l.add   r8,r8,r4
+	l.sb    4(r31),r4
+
+	l.lhz   r4,4(r31)
+	l.add   r8,r8,r4
+	l.sh    10(r31),r4
+	l.lhz   r4,6(r31)
+	l.add   r8,r8,r4
+	l.sh    8(r31),r4
+
+	l.lhs   r4,8(r31)
+	l.add   r8,r8,r4
+	l.sh    6(r31),r4
+	l.lhs   r4,10(r31)
+	l.add   r8,r8,r4
+	l.sh    4(r31),r4
+
+	l.lwz   r4,4(r31)
+	l.add   r8,r8,r4
+
+	REPORT_REG_TO_CONSOLE r8 /* Should be 0x12352af7  */
+
+	l.lwz   r9,0(r31)
+	l.add   r8,r9,r8
+	l.sw    0(r31),r8
+
+	/* Test arithmetic operations.  */
+
+	l.addi  r3,r0,1
+	l.addi  r4,r0,2
+	l.addi  r5,r0,-1
+	l.addi  r6,r0,-1
+	l.addi  r8,r0,0
+
+	l.sub   r7,r5,r3
+	l.sub   r8,r3,r5
+	l.add   r8,r8,r7
+
+	l.div   r7,r7,r4
+	l.add   r9,r3,r4
+	l.mul   r7,r9,r7
+	l.divu  r7,r7,r4
+	l.add   r8,r8,r7
+
+	REPORT_REG_TO_CONSOLE r8 /* Should be 0x7ffffffe  */
+
+	l.lwz   r9,0(r31)
+	l.add   r8,r9,r8
+	l.sw    0(r31),r8
+
+	/* Test logical operations.  */
+
+	l.addi  r3,r0,1
+	l.addi  r4,r0,2
+	l.addi  r5,r0,-1
+	l.addi  r6,r0,-1
+	l.addi  r8,r0,0
+
+	l.andi  r8,r8,1
+	l.and   r8,r8,r3
+
+	l.xori  r8,r5,0xa5a5
+	l.xor   r8,r8,r5
+
+	l.ori   r8,r8,2
+	l.or    r8,r8,r4
+
+	REPORT_REG_TO_CONSOLE r8 /* Should be 0xffffa5a7  */
+
+	l.lwz   r9,0(r31)
+	l.add   r8,r9,r8
+	l.sw    0(r31),r8
+
+	/* Test shifting operations.  */
+
+	l.addi  r3,r0,1
+	l.addi  r4,r0,2
+	l.addi  r5,r0,-1
+	l.addi  r6,r0,-1
+	l.addi  r8,r0,0
+
+	l.slli  r8,r5,6
+	l.sll   r8,r8,r4
+
+	l.srli  r8,r8,6
+	l.srl   r8,r8,r4
+
+	l.srai  r8,r8,2
+	l.sra   r8,r8,r4
+
+	REPORT_REG_TO_CONSOLE r8 /* Should be 0x000fffff  */
+
+	l.lwz   r9,0(r31)
+	l.add   r8,r9,r8
+	l.sw    0(r31),r8
+
+	/* Test the CPU flag. */
+
+	l.addi  r3,r0,1
+	l.addi  r4,r0,-2
+	l.addi  r8,r0,0
+
+	l.sfeq  r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfeq  r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfeqi r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfeqi r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfne  r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfne  r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfnei r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfnei r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgtu r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgtu r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgtui    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgtui    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgeu r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgeu r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgeui    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgeui    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfltu r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfltu r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfltui    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfltui    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfleu r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfleu r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfleui    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfleui    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgts r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgts r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgtsi    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgtsi    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfges r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfges r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgesi    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfgesi    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sflts r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sflts r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfltsi    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfltsi    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfles r3,r3
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sfles r3,r4
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sflesi    r3,1
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	l.sflesi    r3,-2
+	l.mfspr r5,r0,17
+	l.andi  r4,r5,0x200
+	l.add   r8,r8,r4
+
+	REPORT_REG_TO_CONSOLE r8 /* Should be 0x00002800  */
+
+	l.lwz   r9,0(r31)
+	l.add   r8,r9,r8
+	l.sw    0(r31),r8
+
+	/* Test the jump instructions.  */
+
+	l.addi  r8,r0,0
+
+	OR1K_DELAYED (
+	OR1K_INST (l.addi  r8,r8,1),
+	OR1K_INST (l.j _T1)
+	)
+
+_T2:	OR1K_DELAYED (
+	OR1K_INST (l.addi  r8,r8,1),
+	OR1K_INST (l.jr    r9)
+	)
+
+_T1:	OR1K_DELAYED (
+	OR1K_INST (l.addi  r8,r8,1),
+	OR1K_INST (l.jal   _T2)
+	)
+
+	l.sfeqi r0,0
+	OR1K_DELAYED (
+	OR1K_INST (l.addi  r8,r8,1),
+	OR1K_INST (l.bf    _T3)
+	)
+
+_T3:	l.sfeqi r0,1
+	OR1K_DELAYED (
+	OR1K_INST (l.addi  r8,r8,1),
+	OR1K_INST (l.bf    _T4)
+	)
+
+	l.addi  r8,r8,1
+
+_T4:	l.sfeqi r0,0
+	OR1K_DELAYED (
+	OR1K_INST (l.addi  r8,r8,1),
+	OR1K_INST (l.bnf    _T5)
+	)
+
+	l.addi  r8,r8,1
+
+_T5:	l.sfeqi r0,1
+	OR1K_DELAYED (
+	OR1K_INST (l.addi  r8,r8,1),
+	OR1K_INST (l.bnf    _T6)
+	)
+
+	l.addi  r8,r8,1
+
+_T6:	l.movhi r3,hi (_T7)
+	l.ori  r3,r3,lo (_T7)
+	l.mtspr r0,r3,32
+	l.mfspr r5,r0,17
+	l.mtspr r0,r5,64
+	l.rfe
+	l.addi  r8,r8,1 /* l.rfe should not have a delay slot  */
+
+	l.addi  r8,r8,1
+
+_T7:    REPORT_REG_TO_CONSOLE r8 /* Should be 0x000000009  */
+
+	l.lwz   r9,0(r31)
+	l.add   r8,r9,r8
+	l.sw    0(r31),r8
+
+	l.lwz   r9,0(r31)
+	l.movhi r3,0x4c69
+	l.ori   r3,r3,0xe5f7
+	l.add   r8,r8,r3
+
+	REPORT_REG_TO_CONSOLE r8 /* Should be 0xdeaddead  */
+
+	/* Test l.movhi, on 32-bit implementations it should not
+	   sign-extend anything.  */
+
+	l.movhi r3, -1
+	REPORT_REG_TO_CONSOLE r3
+
+	/* Test l.cmov  */
+
+	LOAD_IMMEDIATE r14, 0x12345678
+	LOAD_IMMEDIATE r15, 0xABCDF0BD
+
+	SET_SPR_SR_FLAGS  SPR_SR_F, r6, r7
+	l.cmov r10, r14, r15
+	CLEAR_SPR_SR_FLAGS SPR_SR_F, r6, r7
+	l.cmov r11, r14, r15
+
+	REPORT_REG_TO_CONSOLE r10
+	REPORT_REG_TO_CONSOLE r11
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/div.S b/sim/testsuite/sim/or1k/div.S
new file mode 100644
index 0000000000..7e154c2b89
--- /dev/null
+++ b/sim/testsuite/sim/or1k/div.S
@@ -0,0 +1,291 @@
+/* Tests the divide instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x0000000c);\n
+# output: report(0x00000003);\n
+# output: report(0x00000004);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000b);\n
+# output: report(0x00000003);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000004);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff5);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0x00000003);\n
+# output: report(0xfffffffc);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff5);\n
+# output: report(0x00000003);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000c);\n
+# output: report(0xfffffffd);\n
+# output: report(0xfffffffc);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000b);\n
+# output: report(0xfffffffd);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000c);\n
+# output: report(0x00000000);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0x00000000);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000c);\n
+# output: report(0x00000000);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0x00000000);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x0000000c);\n
+# output: report(0x00000003);\n
+# output: report(0x00000004);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000b);\n
+# output: report(0x00000003);\n
+# output: report(0x00000003);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff5);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0x00000003);\n
+# output: report(0x55555551);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff5);\n
+# output: report(0x00000003);\n
+# output: report(0x55555551);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000c);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000b);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000c);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x0000000c);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xfffffff4);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .exception_vectors
+
+	/* Range exception.  */
+	.org	0xb00
+
+	l.addi r1, r1, -EXCEPTION_STACK_SKIP_SIZE
+	PUSH r2
+	PUSH r3
+	/* Save the address of the instruction that caused the problem.  */
+	MOVE_FROM_SPR r2, SPR_EPCR_BASE
+	LOAD_IMMEDIATE r3, 0x15000000 /* Opcode for l.nop  */
+	l.sw	0(r2), r3
+	POP r3
+	POP r2
+	l.addi r1, r1, EXCEPTION_STACK_SKIP_SIZE
+	l.rfe
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test l.div  */
+
+	/* Divide two positive numbers and check rounding.  Should set no
+	   flags.  */
+	TEST_INST_I32_I32 l.div, 0x0000000c, 0x00000003 /* 12 / 3 = 4  */
+	TEST_INST_I32_I32 l.div, 0x0000000b, 0x00000003 /* 11 / 3 = 3  */
+
+	/* Divide two negative numbers and check rounding.  Should set no
+	   flags.  */
+	TEST_INST_I32_I32 l.div, 0xfffffff4, 0xfffffffd
+	TEST_INST_I32_I32 l.div, 0xfffffff5, 0xfffffffd
+
+	/* Divide a negative number by a positive number and check
+	   rounding.  Should set no flags.  */
+	TEST_INST_I32_I32 l.div, 0xfffffff4, 0x00000003
+	TEST_INST_I32_I32 l.div, 0xfffffff5, 0x00000003
+
+	/* Divide a positive number by a negative number and check
+	   rounding.  Should set no flags.  */
+	TEST_INST_I32_I32 l.div, 0x0000000c, 0xfffffffd
+	TEST_INST_I32_I32 l.div, 0x0000000b, 0xfffffffd
+
+	/* Divide by zero.  This will set the carry flag.  */
+	TEST_INST_I32_I32 l.div, 0x0000000c, 0x00000000
+	TEST_INST_I32_I32 l.div, 0xfffffff4, 0x00000000
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Divide by zero.  This will set the carry flag and trigger an
+	   exception.  */
+	TEST_INST_I32_I32 l.div, 0x0000000c, 0x00000000
+	TEST_INST_I32_I32 l.div, 0xfffffff4, 0x00000000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test l.divu  */
+
+	/* Divide two positive numbers and check rounding.  Should set no
+	   flags.  */
+	TEST_INST_I32_I32 l.divu, 0x0000000c, 0x00000003
+	TEST_INST_I32_I32 l.divu, 0x0000000b, 0x00000003
+
+	/* Divide two numbers that would be negative under 2's complement
+	   and check rounding.  Should set no flags.  */
+	TEST_INST_I32_I32 l.divu, 0xfffffff4, 0xfffffffd
+	TEST_INST_I32_I32 l.divu, 0xfffffff5, 0xfffffffd
+
+	/* Divide a number that would be negative under 2's complement by a
+	   number that would be positive under 2's complement and check
+	   rounding.  This should set no flags.  */
+	TEST_INST_I32_I32 l.divu, 0xfffffff4, 0x00000003
+	TEST_INST_I32_I32 l.divu, 0xfffffff5, 0x00000003
+
+	/* Divide a number that would be positive under 2's complement by a
+	   number that would be negative under 2's complement and check
+	   rounding.  This should set no flags.  */
+	TEST_INST_I32_I32 l.divu, 0x0000000c, 0xfffffffd
+	TEST_INST_I32_I32 l.divu, 0x0000000b, 0xfffffffd
+
+	/* Divide by zero.  This will set the carry flag.  */
+	TEST_INST_I32_I32 l.divu, 0x0000000c, 0x00000000
+	TEST_INST_I32_I32 l.divu, 0xfffffff4, 0x00000000
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Divide by zero.  This will set the carry flag and trigger an
+	   exception.  */
+	TEST_INST_I32_I32 l.divu, 0x0000000c, 0x00000000
+	TEST_INST_I32_I32 l.divu, 0xfffffff4, 0x00000000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/ext.S b/sim/testsuite/sim/or1k/ext.S
new file mode 100644
index 0000000000..652c2b05f4
--- /dev/null
+++ b/sim/testsuite/sim/or1k/ext.S
@@ -0,0 +1,236 @@
+/* Tests the l.ext{b,h}{s,z} instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x0000007f);\n
+# output: report(0x0000007f);\n
+# output: report(0x00000053);\n
+# output: report(0x00000053);\n
+# output: report(0x0000ff53);\n
+# output: report(0x00000053);\n
+# output: report(0x00001234);\n
+# output: report(0x00000034);\n
+# output: report(0x000000ff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000080);\n
+# output: report(0xffffff80);\n
+# output: report(0x0000ff80);\n
+# output: report(0xffffff80);\n
+# output: report(0x00007f80);\n
+# output: report(0xffffff80);\n
+# output: report(0x00007fff);\n
+# output: report(0xffffffff);\n
+# output: report(0x0000007f);\n
+# output: report(0x0000007f);\n
+# output: report(0x00000053);\n
+# output: report(0x00000053);\n
+# output: report(0x0000ff53);\n
+# output: report(0x00000053);\n
+# output: report(0x00001234);\n
+# output: report(0x00000034);\n
+# output: report(0x000000ff);\n
+# output: report(0x000000ff);\n
+# output: report(0x00000080);\n
+# output: report(0x00000080);\n
+# output: report(0x0000ff80);\n
+# output: report(0x00000080);\n
+# output: report(0x00007f80);\n
+# output: report(0x00000080);\n
+# output: report(0x00007fff);\n
+# output: report(0x000000ff);\n
+# output: report(0x00007fff);\n
+# output: report(0x00007fff);\n
+# output: report(0x00005233);\n
+# output: report(0x00005233);\n
+# output: report(0xffff2f53);\n
+# output: report(0x00002f53);\n
+# output: report(0x12345678);\n
+# output: report(0x00005678);\n
+# output: report(0x0000ffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00008000);\n
+# output: report(0xffff8000);\n
+# output: report(0x0000ff80);\n
+# output: report(0xffffff80);\n
+# output: report(0x80008000);\n
+# output: report(0xffff8000);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00007fff);\n
+# output: report(0x00007fff);\n
+# output: report(0x00005233);\n
+# output: report(0x00005233);\n
+# output: report(0xffff2f53);\n
+# output: report(0x00002f53);\n
+# output: report(0x12345678);\n
+# output: report(0x00005678);\n
+# output: report(0x0000ffff);\n
+# output: report(0x0000ffff);\n
+# output: report(0x00008000);\n
+# output: report(0x00008000);\n
+# output: report(0x0000ff80);\n
+# output: report(0x0000ff80);\n
+# output: report(0x80008000);\n
+# output: report(0x00008000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x0000ffff);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x7fff7fff);\n
+# output: report(0x7fff7fff);\n
+# output: report(0xffff7f7f);\n
+# output: report(0xffff7f7f);\n
+# output: report(0xffffff7f);\n
+# output: report(0xffffff7f);\n
+# output: report(0xffff7fff);\n
+# output: report(0xffff7fff);\n
+# output: report(0x7fff7f7f);\n
+# output: report(0x7fff7f7f);\n
+# output: report(0x12345678);\n
+# output: report(0x12345678);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x7fff7fff);\n
+# output: report(0x7fff7fff);\n
+# output: report(0xffff7f7f);\n
+# output: report(0xffff7f7f);\n
+# output: report(0xffffff7f);\n
+# output: report(0xffffff7f);\n
+# output: report(0xffff7fff);\n
+# output: report(0xffff7fff);\n
+# output: report(0x7fff7f7f);\n
+# output: report(0x7fff7f7f);\n
+# output: report(0x12345678);\n
+# output: report(0x12345678);\n
+# output: exit(0)\n
+
+#include "or1k-asm-test-env.h"
+
+	.macro CHECK_EXT insn, val, mask, high_mask
+	LOAD_IMMEDIATE r4, \val
+	REPORT_REG_TO_CONSOLE r4
+	\insn   r5, r4
+	REPORT_REG_TO_CONSOLE r5
+	LOAD_IMMEDIATE r6, \mask
+	l.xori  r7, r6, -1
+	l.and   r8, r4, r6
+	l.and   r9, r5, r6
+	l.sfne  r8, r9
+	OR1K_DELAYED_NOP (l.bf    ext_fail)
+	l.and   r8, r5, r7
+	LOAD_IMMEDIATE r7, \high_mask
+	l.sfne  r8, r7
+	OR1K_DELAYED_NOP (l.bf    ext_fail)
+	.endm
+
+#define CHECK_HIGH3_CLEAR(insn, val) CHECK_EXT insn, val, 0x000000ff, 0
+#define CHECK_HIGH3_SET(val) CHECK_EXT l.extbs, val, 0x000000ff, 0xffffff00
+#define CHECK_HIGH2_CLEAR(insn, val) CHECK_EXT insn, val, 0x0000ffff, 0
+#define CHECK_HIGH2_SET(val) CHECK_EXT l.exths, val, 0x0000ffff, 0xffff0000
+
+	.macro CHECK_MOVE insn, val
+	LOAD_IMMEDIATE r4, \val
+	REPORT_REG_TO_CONSOLE r4
+	\insn   r5, r4
+	REPORT_REG_TO_CONSOLE r5
+	l.sfne  r5, r4
+	OR1K_DELAYED_NOP (l.bf    ext_fail)
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test l.extbs  */
+	CHECK_HIGH3_CLEAR ( l.extbs, 0x7f   )
+	CHECK_HIGH3_CLEAR ( l.extbs, 0x53   )
+	CHECK_HIGH3_CLEAR ( l.extbs, 0xff53 )
+	CHECK_HIGH3_CLEAR ( l.extbs, 0x1234 )
+
+	CHECK_HIGH3_SET (0xff)
+	CHECK_HIGH3_SET (0x80)
+	CHECK_HIGH3_SET (0xff80)
+	CHECK_HIGH3_SET (0x7f80)
+	CHECK_HIGH3_SET (0x7fff)
+
+	/* Test l.extbz  */
+	CHECK_HIGH3_CLEAR (l.extbz, 0x7f)
+	CHECK_HIGH3_CLEAR (l.extbz, 0x53)
+	CHECK_HIGH3_CLEAR (l.extbz, 0xff53)
+	CHECK_HIGH3_CLEAR (l.extbz, 0x1234)
+
+	CHECK_HIGH3_CLEAR (l.extbz, 0xff)
+	CHECK_HIGH3_CLEAR (l.extbz, 0x80)
+	CHECK_HIGH3_CLEAR (l.extbz, 0xff80)
+	CHECK_HIGH3_CLEAR (l.extbz, 0x7f80)
+	CHECK_HIGH3_CLEAR (l.extbz, 0x7fff)
+
+	/* Test l.exths  */
+	CHECK_HIGH2_CLEAR (l.exths, 0x7fff)
+	CHECK_HIGH2_CLEAR (l.exths, 0x5233)
+	CHECK_HIGH2_CLEAR (l.exths, 0xffff2f53)
+	CHECK_HIGH2_CLEAR (l.exths, 0x12345678)
+
+	CHECK_HIGH2_SET (0xffff)
+	CHECK_HIGH2_SET (0x8000)
+	CHECK_HIGH2_SET (0xff80)
+	CHECK_HIGH2_SET (0x80008000)
+	CHECK_HIGH2_SET (0x7fffffff)
+
+	/* Test l.exthz  */
+	CHECK_HIGH2_CLEAR (l.exthz, 0x7fff)
+	CHECK_HIGH2_CLEAR (l.exthz, 0x5233)
+	CHECK_HIGH2_CLEAR (l.exthz, 0xffff2f53)
+	CHECK_HIGH2_CLEAR (l.exthz, 0x12345678)
+
+	CHECK_HIGH2_CLEAR (l.exthz, 0xffff)
+	CHECK_HIGH2_CLEAR (l.exthz, 0x8000)
+	CHECK_HIGH2_CLEAR (l.exthz, 0xff80)
+	CHECK_HIGH2_CLEAR (l.exthz, 0x80008000)
+	CHECK_HIGH2_CLEAR (l.exthz, 0x7fffffff)
+
+	/* Test l.extws  */
+	CHECK_MOVE l.extws, 0xffffffff
+	CHECK_MOVE l.extws, 0x7fffffff
+	CHECK_MOVE l.extws, 0x7fff7fff
+	CHECK_MOVE l.extws, 0xffff7f7f
+	CHECK_MOVE l.extws, 0xffffff7f
+	CHECK_MOVE l.extws, 0xffff7fff
+	CHECK_MOVE l.extws, 0x7fff7f7f
+	CHECK_MOVE l.extws, 0x12345678
+
+	/* Test l.extwz  */
+	CHECK_MOVE l.extwz, 0xffffffff
+	CHECK_MOVE l.extwz, 0x7fffffff
+	CHECK_MOVE l.extwz, 0x7fff7fff
+	CHECK_MOVE l.extwz, 0xffff7f7f
+	CHECK_MOVE l.extwz, 0xffffff7f
+	CHECK_MOVE l.extwz, 0xffff7fff
+	CHECK_MOVE l.extwz, 0x7fff7f7f
+	CHECK_MOVE l.extwz, 0x12345678
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
+
+ext_fail:
+	EXIT_SIMULATION_WITH_IMMEDIATE_EXIT_CODE SEC_GENERIC_ERROR
diff --git a/sim/testsuite/sim/or1k/find.S b/sim/testsuite/sim/or1k/find.S
new file mode 100644
index 0000000000..6279276961
--- /dev/null
+++ b/sim/testsuite/sim/or1k/find.S
@@ -0,0 +1,100 @@
+/* Tests the find instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x80000000);\n
+# output: report(0x00000020);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000002);\n
+# output: \n
+# output: report(0x00018000);\n
+# output: report(0x00000010);\n
+# output: \n
+# output: report(0xc0000000);\n
+# output: report(0x0000001f);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x80000000);\n
+# output: report(0x00000020);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x0000001f);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000020);\n
+# output: \n
+# output: report(0x00018000);\n
+# output: report(0x00000011);\n
+# output: \n
+# output: report(0xc0000000);\n
+# output: report(0x00000020);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	.macro TEST_FIND opcode, operand
+	LOAD_IMMEDIATE r5, \operand
+	REPORT_REG_TO_CONSOLE r5
+	\opcode r4, r5
+	REPORT_REG_TO_CONSOLE r4
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test l.ff1  */
+
+	TEST_FIND l.ff1, 0x00000001
+	TEST_FIND l.ff1, 0x80000000
+	TEST_FIND l.ff1, 0x55555555
+	TEST_FIND l.ff1, 0xaaaaaaaa
+	TEST_FIND l.ff1, 0x00018000
+	TEST_FIND l.ff1, 0xc0000000
+	TEST_FIND l.ff1, 0x00000000
+
+	/* Test l.fl1  */
+
+	TEST_FIND l.fl1, 0x00000001
+	TEST_FIND l.fl1, 0x80000000
+	TEST_FIND l.fl1, 0x55555555
+	TEST_FIND l.fl1, 0xaaaaaaaa
+	TEST_FIND l.fl1, 0x00018000
+	TEST_FIND l.fl1, 0xc0000000
+	TEST_FIND l.fl1, 0x00000000
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/flag.S b/sim/testsuite/sim/or1k/flag.S
new file mode 100644
index 0000000000..d9e2429ad1
--- /dev/null
+++ b/sim/testsuite/sim/or1k/flag.S
@@ -0,0 +1,386 @@
+/* Tests the set flag (l.sf*) instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+#define INT_MAX		2147483647 /* 0x7fffffff  */
+#define INT_MAX_MIN1	2147483646 /* 0x7ffffffe  */
+#define NEG_INT_MAX	-2147483648 /* 0x80000000  */
+#define NEG_INT_MAX_PL1	-2147483647 /* 0x80000001  */
+#define MIN1		-1 /* 0xffffffff  */
+
+#define SHRT_MIN	(-32768)
+#define SHRT_MAX	32767
+
+#define UINT_MAX	4294967295 /* 0xffffffff  */
+#define UINT_MAX_MIN1	4294967294 /* 0xfffffffe  */
+
+#define USHRT_MAX	65535
+
+	.macro MOVE_TO_R4_R5_AND_REPORT a, b
+	LOAD_IMMEDIATE r4, \a
+	LOAD_IMMEDIATE r5, \b
+
+	/* During development, add REPORT_xxx statements here to see the
+	   operands.  */
+	.endm
+
+	.macro MOVE_TO_R4_AND_REPORT_I a, b
+	LOAD_IMMEDIATE r4, \a
+
+	/* During development, add REPORT_xxx statements here to see the
+	   operands.  */
+	.endm
+
+	.macro SHOULD_BE_SET
+	OR1K_DELAYED_NOP (l.bnf  failed)
+	.endm
+
+	.macro SHOULDNT_BE_SET
+	OR1K_DELAYED_NOP (l.bf    failed)
+	.endm
+
+	.macro SHOULD_BE_LESS_THAN_SIGNED a, b
+	MOVE_TO_R4_R5_AND_REPORT \a , \b
+
+	l.sfeq  r4, r5
+	SHOULDNT_BE_SET
+	l.sfne  r4, r5
+	SHOULD_BE_SET
+	l.sfgts r4, r5
+	SHOULDNT_BE_SET
+	l.sfges r4, r5
+	SHOULDNT_BE_SET
+	l.sfles r4, r5
+	SHOULD_BE_SET
+	l.sflts r4, r5
+	SHOULD_BE_SET
+	.endm
+
+	.macro SHOULD_BE_GREATER_THAN_SIGNED a, b
+	MOVE_TO_R4_R5_AND_REPORT \a , \b
+
+	l.sfeq  r4, r5
+	SHOULDNT_BE_SET
+	l.sfne  r4, r5
+	SHOULD_BE_SET
+	l.sfgts r4, r5
+	SHOULD_BE_SET
+	l.sfges r4, r5
+	SHOULD_BE_SET
+	l.sfles r4, r5
+	SHOULDNT_BE_SET
+	l.sflts r4, r5
+	SHOULDNT_BE_SET
+	.endm
+
+	.macro SHOULD_BE_LESS_THAN_UNSIGNED a, b
+	MOVE_TO_R4_R5_AND_REPORT \a , \b
+
+	l.sfeq  r4, r5
+	SHOULDNT_BE_SET
+	l.sfne  r4, r5
+	SHOULD_BE_SET
+	l.sfgtu r4, r5
+	SHOULDNT_BE_SET
+	l.sfgeu r4, r5
+	SHOULDNT_BE_SET
+	l.sfleu r4, r5
+	SHOULD_BE_SET
+	l.sfltu r4, r5
+	SHOULD_BE_SET
+	.endm
+
+	.macro SHOULD_BE_GREATER_THAN_UNSIGNED a, b
+	MOVE_TO_R4_R5_AND_REPORT \a , \b
+
+	l.sfeq  r4, r5
+	SHOULDNT_BE_SET
+	l.sfne  r4, r5
+	SHOULD_BE_SET
+	l.sfgtu r4, r5
+	SHOULD_BE_SET
+	l.sfgeu r4, r5
+	SHOULD_BE_SET
+	l.sfleu r4, r5
+	SHOULDNT_BE_SET
+	l.sfltu r4, r5
+	SHOULDNT_BE_SET
+	.endm
+
+	.macro SHOULD_BE_EQUAL a, b
+	MOVE_TO_R4_R5_AND_REPORT \a , \b
+
+	l.sfeq  r4, r5
+	SHOULD_BE_SET
+	l.sfne  r4, r5
+	SHOULDNT_BE_SET
+
+	/* Signed tests.  */
+	l.sfgts r4, r5
+	SHOULDNT_BE_SET
+	l.sfges r4, r5
+	SHOULD_BE_SET
+	l.sfles r4, r5
+	SHOULD_BE_SET
+	l.sflts r4, r5
+	SHOULDNT_BE_SET
+
+	/* Unsigned tests.  */
+	l.sfgtu r4, r5
+	SHOULDNT_BE_SET
+	l.sfgeu r4, r5
+	SHOULD_BE_SET
+	l.sfleu r4, r5
+	SHOULD_BE_SET
+	l.sfltu r4, r5
+	SHOULDNT_BE_SET
+	.endm
+
+	.macro SHOULDNT_BE_EQUAL a, b
+	MOVE_TO_R4_R5_AND_REPORT \a , \b
+
+	l.sfeq  r4, r5
+	SHOULDNT_BE_SET
+	l.sfne  r4, r5
+	SHOULD_BE_SET
+	.endm
+
+	.macro SHOULD_BE_EQUAL_I a, b
+	MOVE_TO_R4_AND_REPORT_I \a, \b
+
+	l.sfeqi  r4, \b
+	SHOULD_BE_SET
+	l.sfnei  r4, \b
+	SHOULDNT_BE_SET
+
+	/* Signed tests.  */
+	l.sfgtsi r4, \b
+	SHOULDNT_BE_SET
+	l.sfgesi r4, \b
+	SHOULD_BE_SET
+	l.sflesi r4, \b
+	SHOULD_BE_SET
+	l.sfltsi r4, \b
+	SHOULDNT_BE_SET
+
+	/* Unsigned tests.  */
+	l.sfgtui r4, \b
+	SHOULDNT_BE_SET
+	l.sfgeui r4, \b
+	SHOULD_BE_SET
+	l.sfleui r4, \b
+	SHOULD_BE_SET
+	l.sfltui r4, \b
+	SHOULDNT_BE_SET
+	.endm
+
+	.macro SHOULDNT_BE_EQUAL_I a, b
+	MOVE_TO_R4_AND_REPORT_I \a, \b
+
+	l.sfeqi  r4, \b
+	SHOULDNT_BE_SET
+	l.sfnei  r4, \b
+	SHOULD_BE_SET
+	.endm
+
+	.macro SHOULD_BE_LESS_THAN_SIGNED_I a, b
+	MOVE_TO_R4_AND_REPORT_I \a, \b
+
+	l.sfeqi  r4, \b
+	SHOULDNT_BE_SET
+	l.sfnei  r4, \b
+	SHOULD_BE_SET
+	l.sfgtsi r4, \b
+	SHOULDNT_BE_SET
+	l.sfgesi r4, \b
+	SHOULDNT_BE_SET
+	l.sflesi r4, \b
+	SHOULD_BE_SET
+	l.sfltsi r4, \b
+	SHOULD_BE_SET
+	.endm
+
+	.macro SHOULD_BE_GREATER_THAN_SIGNED_I a, b
+	MOVE_TO_R4_AND_REPORT_I \a, \b
+
+	l.sfeqi  r4, \b
+	SHOULDNT_BE_SET
+	l.sfnei  r4, \b
+	SHOULD_BE_SET
+	l.sfgtsi r4, \b
+	SHOULD_BE_SET
+	l.sfgesi r4, \b
+	SHOULD_BE_SET
+	l.sflesi r4, \b
+	SHOULDNT_BE_SET
+	l.sfltsi r4, \b
+	SHOULDNT_BE_SET
+	.endm
+
+	.macro SHOULD_BE_LESS_THAN_UNSIGNED_I a, b
+	MOVE_TO_R4_AND_REPORT_I \a, \b
+
+	l.sfeqi  r4, \b
+	SHOULDNT_BE_SET
+	l.sfnei  r4, \b
+	SHOULD_BE_SET
+	l.sfgtui r4, \b
+	SHOULDNT_BE_SET
+	l.sfgeui r4, \b
+	SHOULDNT_BE_SET
+	l.sfleui r4, \b
+	SHOULD_BE_SET
+	l.sfltui r4, \b
+	SHOULD_BE_SET
+	.endm
+
+	.macro SHOULD_BE_GREATER_THAN_UNSIGNED_I a, b
+	MOVE_TO_R4_AND_REPORT_I \a, \b
+
+	l.sfeqi  r4, \b
+	SHOULDNT_BE_SET
+	l.sfnei  r4, \b
+	SHOULD_BE_SET
+	l.sfgtui r4, \b
+	SHOULD_BE_SET
+	l.sfgeui r4, \b
+	SHOULD_BE_SET
+	l.sfleui r4, \b
+	SHOULDNT_BE_SET
+	l.sfltui r4, \b
+	SHOULDNT_BE_SET
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Signed tests  */
+
+	SHOULD_BE_LESS_THAN_SIGNED 0, 1
+	SHOULD_BE_LESS_THAN_SIGNED MIN1, 0
+	SHOULD_BE_LESS_THAN_SIGNED INT_MAX_MIN1, INT_MAX
+	SHOULD_BE_LESS_THAN_SIGNED NEG_INT_MAX, INT_MAX
+	SHOULD_BE_LESS_THAN_SIGNED NEG_INT_MAX, INT_MAX_MIN1
+	SHOULD_BE_LESS_THAN_SIGNED NEG_INT_MAX_PL1, INT_MAX
+	SHOULD_BE_LESS_THAN_SIGNED NEG_INT_MAX_PL1, INT_MAX_MIN1
+	SHOULD_BE_LESS_THAN_SIGNED -7, -6
+	SHOULD_BE_LESS_THAN_SIGNED NEG_INT_MAX, NEG_INT_MAX_PL1
+	SHOULD_BE_LESS_THAN_SIGNED NEG_INT_MAX, MIN1
+	SHOULD_BE_LESS_THAN_SIGNED NEG_INT_MAX, 0
+
+	SHOULD_BE_GREATER_THAN_SIGNED 1, 0
+	SHOULD_BE_GREATER_THAN_SIGNED 0, MIN1
+	SHOULD_BE_GREATER_THAN_SIGNED INT_MAX, INT_MAX_MIN1
+	SHOULD_BE_GREATER_THAN_SIGNED INT_MAX, NEG_INT_MAX
+	SHOULD_BE_GREATER_THAN_SIGNED INT_MAX_MIN1, NEG_INT_MAX
+	SHOULD_BE_GREATER_THAN_SIGNED INT_MAX, NEG_INT_MAX_PL1
+	SHOULD_BE_GREATER_THAN_SIGNED INT_MAX_MIN1, NEG_INT_MAX_PL1
+	SHOULD_BE_GREATER_THAN_SIGNED -6, -7
+	SHOULD_BE_GREATER_THAN_SIGNED NEG_INT_MAX_PL1, NEG_INT_MAX
+	SHOULD_BE_GREATER_THAN_SIGNED MIN1, NEG_INT_MAX
+	SHOULD_BE_GREATER_THAN_SIGNED 0, NEG_INT_MAX
+
+	/* See the immediate tests below.  */
+	SHOULD_BE_LESS_THAN_SIGNED 0xFFFF7FFF, 0xFFFF8000
+	/* See the immediate tests below.  */
+	SHOULD_BE_GREATER_THAN_SIGNED 0xFFFF8001, 0xFFFF8000
+
+	/* Signed tests, immediate  */
+
+	SHOULD_BE_LESS_THAN_SIGNED_I	0,  1
+	SHOULD_BE_LESS_THAN_SIGNED_I  -1,  0
+	SHOULD_BE_LESS_THAN_SIGNED_I  -7, -6
+
+	SHOULD_BE_GREATER_THAN_SIGNED_I 0x00008000, 0x7FFF
+	SHOULD_BE_LESS_THAN_SIGNED_I 0xFFFFFFFF, 0x7FFF
+	/* 0x8000 gets sign-extended to 0xFFFF8000.  */
+	SHOULD_BE_LESS_THAN_SIGNED_I 0xFFFF7FFF, 0x8000
+	/* 0x8000 gets sign-extended to 0xFFFF8000.  */
+	SHOULD_BE_GREATER_THAN_SIGNED_I 0xFFFF8001, 0x8000
+	/* 0x8000 gets sign-extended to 0xFFFF8000.  */
+	SHOULD_BE_GREATER_THAN_SIGNED_I 0x00008000, 0x8000
+
+	/* Unsigned tests  */
+
+	SHOULD_BE_LESS_THAN_UNSIGNED 0, 1
+	SHOULD_BE_LESS_THAN_UNSIGNED UINT_MAX_MIN1, UINT_MAX
+	SHOULD_BE_GREATER_THAN_UNSIGNED 1, 0
+	SHOULD_BE_GREATER_THAN_UNSIGNED UINT_MAX, UINT_MAX_MIN1
+	SHOULD_BE_GREATER_THAN_UNSIGNED UINT_MAX, 0
+	SHOULD_BE_GREATER_THAN_UNSIGNED 0x80000001,  0x80000000
+	SHOULD_BE_LESS_THAN_UNSIGNED 0x80000000,  0x80000001
+	SHOULD_BE_GREATER_THAN_UNSIGNED 0x80000000, 0x7fffffff
+	SHOULD_BE_LESS_THAN_UNSIGNED 0x7fffffff,  0x80000000
+	SHOULD_BE_GREATER_THAN_UNSIGNED 0x7fffffff,  0x7ffffffe
+	SHOULD_BE_LESS_THAN_UNSIGNED 0x7ffffffe,  0x7fffffff
+	SHOULD_BE_LESS_THAN_UNSIGNED 0x2024fae0,  0xfef03220
+
+	/* Unsigned tests, immediate  */
+
+	SHOULD_BE_LESS_THAN_UNSIGNED_I 0, 1
+	SHOULD_BE_GREATER_THAN_UNSIGNED_I 1, 0
+	SHOULD_BE_LESS_THAN_UNSIGNED_I	 SHRT_MAX - 1, SHRT_MAX
+	SHOULD_BE_GREATER_THAN_UNSIGNED_I SHRT_MAX	 , SHRT_MAX - 1
+
+	/* The sign extension produces unexpected results here.  */
+
+	/* 0xFFFF gets sign-extended to 0xFFFFFFFF.  */
+	SHOULD_BE_LESS_THAN_UNSIGNED_I 0xFFFFFFFF - 1, 0xFFFF
+	/* 0x8000 gets sign-extended to 0xFFFF8000.  */
+	SHOULD_BE_LESS_THAN_UNSIGNED_I 0xFFFF7FFF, 0x8000
+
+	/* Equal tests.  */
+
+	SHOULD_BE_EQUAL 0, 0
+	SHOULD_BE_EQUAL UINT_MAX, UINT_MAX
+	SHOULD_BE_EQUAL MIN1, UINT_MAX
+	SHOULD_BE_EQUAL INT_MAX, INT_MAX
+	SHOULD_BE_EQUAL NEG_INT_MAX, NEG_INT_MAX
+
+	/* Equal tests, immediate.  Test the 16-to-32-bit sign extension.  */
+
+	SHOULD_BE_EQUAL_I 0, 0
+	SHOULD_BE_EQUAL_I 0x00007FFF, 0x7FFF
+	SHOULD_BE_EQUAL_I 0xFFFF8000, 0x8000
+	SHOULD_BE_EQUAL_I 0xFFFFFFFF, 0xFFFF
+
+	/* Non-equal tests.  */
+
+	SHOULDNT_BE_EQUAL 0, 1
+	SHOULDNT_BE_EQUAL UINT_MAX, INT_MAX
+	SHOULDNT_BE_EQUAL UINT_MAX, NEG_INT_MAX
+	SHOULDNT_BE_EQUAL MIN1, NEG_INT_MAX_PL1
+	SHOULDNT_BE_EQUAL INT_MAX, NEG_INT_MAX
+	SHOULDNT_BE_EQUAL NEG_INT_MAX_PL1, UINT_MAX_MIN1
+
+	/* Non-equal tests, immediate.  Test the 16-to-32-bit sign
+	   extension.  */
+
+	SHOULDNT_BE_EQUAL_I 0x00008000, 0x8000
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
+
+failed:
+	EXIT_SIMULATION_WITH_IMMEDIATE_EXIT_CODE SEC_GENERIC_ERROR
diff --git a/sim/testsuite/sim/or1k/fpu.S b/sim/testsuite/sim/or1k/fpu.S
new file mode 100644
index 0000000000..bfbb755e64
--- /dev/null
+++ b/sim/testsuite/sim/or1k/fpu.S
@@ -0,0 +1,129 @@
+/* Tests some basic fpu instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00007ab7);\n
+# output: report(0xffffd8f0);\n
+# output: report(0x46f56e00);\n
+# output: report(0xc61c4000);\n
+# output: report(0x00007ab7);\n
+# output: report(0xffffd8f0);\n
+# output: \n
+# output: report(0xc0490e56);\n
+# output: report(0xfffffffd);\n
+# output: \n
+# output: report(0x4e6b4bbb);\n
+# output: \n
+# output: report(0xbdc0be40);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: \n
+# output: WARNING: ignoring fpu error caught in fast mode.\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .exception_vectors
+
+	/* Floating point exception.  */
+	.org	0xd00
+
+	/* The handling is a bit dubious at present.  We just patch the
+	   instruction with l.nop and restart.  This will go wrong in branch
+	   delay slots.  But we don't have those in this test.  */
+	l.addi r1, r1, -EXCEPTION_STACK_SKIP_SIZE
+	PUSH r2
+	PUSH r3
+	/* Save the address of the instruction that caused the problem.  */
+	MOVE_FROM_SPR r2, SPR_EPCR_BASE
+	LOAD_IMMEDIATE r3, 0x15000000 /* Opcode for l.nop  */
+	l.sw	-4(r2), r3
+	POP r3
+	POP r2
+	l.addi r1, r1, EXCEPTION_STACK_SKIP_SIZE
+	l.rfe
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test lf.itof.s int to float conversion.  Setting up:
+	 *  r10  31415.0f
+	 *  r12	-10000.0f
+	 */
+	l.ori	r11, r0, 31415
+	l.ori	r13, r0, -10000
+	l.movhi	r15, 0xffff
+	l.or	r13, r13, r15
+
+	REPORT_REG_TO_CONSOLE r11
+	REPORT_REG_TO_CONSOLE r13
+	lf.itof.s r10, r11
+	lf.itof.s r12, r13
+	REPORT_REG_TO_CONSOLE r10
+	REPORT_REG_TO_CONSOLE r12
+
+	/* Test lf.ftoi.s float to int conversion.  */
+	lf.ftoi.s r11, r10
+	lf.ftoi.s r13, r12
+	REPORT_REG_TO_CONSOLE r11
+	REPORT_REG_TO_CONSOLE r13
+	PRINT_NEWLINE_TO_CONSOLE
+
+	/* Test lf.div.s divide 31415 by -1000 to get -pi.  Setting up:
+	 *  r8	-3.1415f
+	 */
+	lf.div.s r8, r10, r12
+	REPORT_REG_TO_CONSOLE r8
+
+	lf.ftoi.s r11, r8
+	REPORT_REG_TO_CONSOLE r11
+	PRINT_NEWLINE_TO_CONSOLE
+
+	/* Test lf.mul.s multiply -pi x -10000 x 31415.  Setting up:
+	 *  r6	 986902225
+	 */
+	lf.mul.s r6, r8, r12
+	lf.mul.s r6, r6, r10
+	REPORT_REG_TO_CONSOLE r6
+	PRINT_NEWLINE_TO_CONSOLE
+
+	/* Test lf.rem.s remainder of 986902225 / -pi.  */
+	lf.rem.s r2, r6, r8
+	REPORT_REG_TO_CONSOLE r2
+	PRINT_NEWLINE_TO_CONSOLE
+
+	/* Test lf.sfge.s set flag if r6 >= r10.  */
+	lf.sfge.s r6, r10
+	MOVE_FROM_SPR r2, SPR_SR
+	REPORT_BIT_TO_CONSOLE r2, SPR_SR_F
+	PRINT_NEWLINE_TO_CONSOLE
+
+	/* Test raising an exception by dividing by 0.  */
+	MOVE_FROM_SPR r2, SPR_FPCSR
+	l.ori	r2, r2, 0x1
+	MOVE_TO_SPR SPR_FPCSR, r2
+div0:	lf.div.s r2, r8, r0
+	REPORT_EXCEPTION div0
+	PRINT_NEWLINE_TO_CONSOLE
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/jump.S b/sim/testsuite/sim/or1k/jump.S
new file mode 100644
index 0000000000..ffcc7a13cc
--- /dev/null
+++ b/sim/testsuite/sim/or1k/jump.S
@@ -0,0 +1,105 @@
+/* Tests the jump instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x48000000);\n
+# output: report(0x00000005);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x48000000);\n
+# output: report(0x00000009);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x44000000);\n
+# output: report(0x00000005);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x44000000);\n
+# output: report(0x00000009);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+/* Tests a jump instruction using a register destination.
+   Checks whether the jump succeeds, or whether an exception is triggered
+   (but not if the right exception was triggered yet).
+
+   We manually construct the opcode, to allow us to force R9 into the
+   destination field, to test exception handling.  Usually the assembler
+   would prevent this.
+
+   Do not specify R31 as the register to use for the jump, as it's used
+   internally.  */
+
+	.macro TEST_JUMP  opcode_value  dest_register_number  alignment_offset
+	REPORT_IMMEDIATE_TO_CONSOLE \opcode_value
+	REPORT_IMMEDIATE_TO_CONSOLE \dest_register_number
+	REPORT_IMMEDIATE_TO_CONSOLE \alignment_offset
+	LOAD_IMMEDIATE r\dest_register_number, 51f + \alignment_offset
+	/* Generate the jump opcode.  */
+\@1$:	OR1K_DELAYED_NOP \
+	  (.word  ( \opcode_value | (\dest_register_number << 11) ))
+	/* If the jump failed, we land here.  */
+	REPORT_IMMEDIATE_TO_CONSOLE 1
+	OR1K_DELAYED_NOP (l.j 52f)
+	/* If the jump succeeds, we land here.  */
+51:	REPORT_IMMEDIATE_TO_CONSOLE 0
+52:	REPORT_EXCEPTION \@1$
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test l.jalr (jump and link register)  */
+	TEST_JUMP 0x48000000, 5, 0
+	/* TODO: The sim does not support unaligned memory access yet.
+	TEST_JUMP 0x48000000, 5, 1
+	TEST_JUMP 0x48000000, 5, 2
+	TEST_JUMP 0x48000000, 5, 3
+	*/
+
+	/* Test with link register as the destination.  This is not
+	   allowed.  */
+	TEST_JUMP 0x48000000, 9, 0
+
+	/* Test l.jr (jump register)  */
+	TEST_JUMP 0x44000000, 5, 0
+	/* TODO: The sim does not support unaligned memory access yet.
+	TEST_JUMP 0x44000000, 5, 1
+	TEST_JUMP 0x44000000, 5, 2
+	TEST_JUMP 0x44000000, 5, 3
+	*/
+
+	/* Test with link register as the destination.   */
+	TEST_JUMP 0x44000000, 9, 0
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/load.S b/sim/testsuite/sim/or1k/load.S
new file mode 100644
index 0000000000..aabbcc5358
--- /dev/null
+++ b/sim/testsuite/sim/or1k/load.S
@@ -0,0 +1,358 @@
+/* Tests the load and store instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0xdeadbeef);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0xdeadbeef);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xdeadbeef);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0xdeadbeef);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x000000de);\n
+# output: report(0x000000ad);\n
+# output: report(0x000000be);\n
+# output: report(0x000000ef);\n
+# output: report(0x000000ef);\n
+# output: report(0x000000be);\n
+# output: report(0x000000ad);\n
+# output: report(0x000000de);\n
+# output: report(0xffffffde);\n
+# output: report(0xffffffad);\n
+# output: report(0xffffffbe);\n
+# output: report(0xffffffef);\n
+# output: report(0xffffffef);\n
+# output: report(0xffffffbe);\n
+# output: report(0xffffffad);\n
+# output: report(0xffffffde);\n
+# output: report(0x0000dead);\n
+# output: report(0x0000beef);\n
+# output: report(0x0000beef);\n
+# output: report(0x0000dead);\n
+# output: report(0xffffdead);\n
+# output: report(0xffffbeef);\n
+# output: report(0xffffbeef);\n
+# output: report(0xffffdead);\n
+# output: report(0xa1a2a3a4);\n
+# output: report(0xb4b3b2b1);\n
+# output: report(0x81828384);\n
+# output: report(0x53545152);\n
+# output: report(0xa0b0c0d0);\n
+# output: report(0xa1b1c1d1);\n
+# output: report(0xa3b3c3d3);\n
+# output: report(0xa2b2c2d2);\n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	.macro TEST_LW  opcode, label, offset
+	LOAD_IMMEDIATE r5, \label
+	\opcode  r4, \offset(r5)
+	REPORT_REG_TO_CONSOLE r4
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .rodata
+	.balign 4
+
+50:     .word   0xdeadbeef
+51:     .word   0x00000000
+52:     .word   0x7fffffff
+53:     .word   0x80000000
+54:     .word   0xffffffff
+
+	.section .data
+	.balign 4
+
+buffer1:  .word 0x00000000
+buffer2:  .word 0x00000000
+buffer3:  .word 0x00000000
+buffer4:  .word 0x00000000
+buffer5:
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test instruction l.lws  */
+
+	/* Load with zero offset.  */
+	TEST_LW l.lws 50b, 0
+	TEST_LW l.lws 51b, 0
+	TEST_LW l.lws 52b, 0
+	TEST_LW l.lws 53b, 0
+	TEST_LW l.lws 54b, 0
+
+	/* Load with positive offset.  */
+	TEST_LW l.lws 50b,  4
+	TEST_LW l.lws 50b,  8
+	TEST_LW l.lws 50b, 12
+	TEST_LW l.lws 50b, 16
+
+	/* Load with negative offset.  */
+	TEST_LW l.lws 54b, -16
+	TEST_LW l.lws 54b, -12
+	TEST_LW l.lws 54b,  -8
+	TEST_LW l.lws 54b,  -4
+
+	/* TODO: add here test cases to cover unaligned memory accesses
+	   with l.lws.  */
+
+	/* Test instruction l.lwz */
+
+	/* Load with zero offset.  */
+	TEST_LW l.lwz 50b, 0
+	TEST_LW l.lwz 51b, 0
+	TEST_LW l.lwz 52b, 0
+	TEST_LW l.lwz 53b, 0
+	TEST_LW l.lwz 54b, 0
+
+	/* Load with positive offset.  */
+	TEST_LW l.lwz 50b,  4
+	TEST_LW l.lwz 50b,  8
+	TEST_LW l.lwz 50b, 12
+	TEST_LW l.lwz 50b, 16
+
+	/* Load with negative offset.  */
+	TEST_LW l.lwz 54b, -16
+	TEST_LW l.lwz 54b, -12
+	TEST_LW l.lwz 54b,  -8
+	TEST_LW l.lwz 54b,  -4
+
+	/* TODO: add here test cases to cover unaligned memory accesses
+	   with l.lwz.  */
+
+	/* Test instruction l.lbz  */
+
+	/* Read data at label 50, forwards, byte by byte.  */
+	LOAD_IMMEDIATE r5, 50b
+
+	l.lbz r4, 0(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lbz r4, 1(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lbz r4, 2(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lbz r4, 3(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	/* Read data at label 50, backwards, byte by byte.  */
+	LOAD_IMMEDIATE r31, 51b
+
+	l.lbz r3, -1(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lbz r3, -2(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lbz r3, -3(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lbz r3, -4(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* Test instruction l.lbs  */
+
+	/* Read data at label 50, forwards, byte by byte.  */
+	LOAD_IMMEDIATE r5, 50b
+
+	l.lbs r4, 0(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lbs r4, 1(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lbs r4, 2(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lbs r4, 3(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	/* Read data at label 50, backwards, byte by byte.  */
+	LOAD_IMMEDIATE r31, 51b
+
+	l.lbs r3, -1(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lbs r3, -2(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lbs r3, -3(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lbs r3, -4(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* Test instruction l.lhz  */
+
+	/* Read data at label 50, forwards, half-word by half-word.  */
+	LOAD_IMMEDIATE r5, 50b
+
+	l.lhz r4, 0(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lhz r4, 2(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	/* Read data at label 50, backwards, half-word by half-word.  */
+	LOAD_IMMEDIATE r31, 51b
+
+	l.lhz r3, -2(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lhz r3, -4(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* TODO: add here test cases to cover unaligned memory accesses
+	   with l.lhz.  */
+
+	/* Test instruction l.lhs  */
+
+	/* Read data at label 50, forwards, half-word by half-word.  */
+	LOAD_IMMEDIATE r5, 50b
+
+	l.lhs r4, 0(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	l.lhs r4, 2(r5)
+	REPORT_REG_TO_CONSOLE r4
+
+	/* Read data at label 50, backwards, half-word by half-word.  */
+	LOAD_IMMEDIATE r31, 51b
+
+	l.lhs r3, -2(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	l.lhs r3, -4(r31)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* TODO: add here test cases to cover unaligned memory accesses
+	   with l.lhs.  */
+
+	/* Test instruction l.sb  */
+
+	/* Write 32-bits forwards, byte-to-byte.  */
+	LOAD_IMMEDIATE r5, buffer1
+
+	LOAD_IMMEDIATE r10, 0xA1
+	LOAD_IMMEDIATE r11, 0xA2
+	LOAD_IMMEDIATE r12, 0xA3
+	LOAD_IMMEDIATE r13, 0xA4
+
+	l.sb 0(r5), r10
+	l.sb 1(r5), r11
+	l.sb 2(r5), r12
+	l.sb 3(r5), r13
+
+	l.lwz r3, 0(r5)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* Write 32-bits backwards, byte-to-byte.  */
+	LOAD_IMMEDIATE r6, buffer2
+
+	LOAD_IMMEDIATE r10, 0xB1
+	LOAD_IMMEDIATE r11, 0xB2
+	LOAD_IMMEDIATE r12, 0xB3
+	LOAD_IMMEDIATE r13, 0xB4
+
+	l.sb -1(r6), r10
+	l.sb -2(r6), r11
+	l.sb -3(r6), r12
+	l.sb -4(r6), r13
+
+	l.lwz r3, 0(r5)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* TODO: add here test cases to cover unaligned memory accesses
+	   with l.sb.  */
+
+	/* Test instruction l.sh  */
+
+	/* Write 32-bits forwards, one half-word at a time.  */
+	LOAD_IMMEDIATE r5, buffer1
+
+	LOAD_IMMEDIATE r10, 0x8182
+	LOAD_IMMEDIATE r11, 0x8384
+
+	l.sh 0(r5), r10
+	l.sh 2(r5), r11
+
+	l.lwz r3, 0(r5)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* Write 32-bits backwards, one half-word at a time.  */
+	LOAD_IMMEDIATE r6, buffer2
+
+	LOAD_IMMEDIATE r10, 0x5152
+	LOAD_IMMEDIATE r11, 0x5354
+
+	l.sh -2(r6), r10
+	l.sh -4(r6), r11
+
+	l.lwz r3, 0(r5)
+	REPORT_REG_TO_CONSOLE r3
+
+	/* TODO: add here test cases to cover unaligned memory accesses
+	   with l.sh.  */
+
+	/* Test instruction l.sw  */
+	LOAD_IMMEDIATE r5, buffer1
+	LOAD_IMMEDIATE r6, buffer5
+
+	LOAD_IMMEDIATE r10, 0xA0B0C0D0
+	LOAD_IMMEDIATE r11, 0xA1B1C1D1
+	LOAD_IMMEDIATE r12, 0xA2B2C2D2
+	LOAD_IMMEDIATE r13, 0xA3B3C3D3
+
+	l.sw  0(r5), r10
+	l.sw  4(r5), r11
+	l.sw -4(r6), r12
+	l.sw -8(r6), r13
+
+	TEST_LW l.lwz buffer1, 0
+	TEST_LW l.lwz buffer2, 0
+	TEST_LW l.lwz buffer3, 0
+	TEST_LW l.lwz buffer4, 0
+
+	/* TODO: add here test cases to cover unaligned memory accesses
+	   with l.sw.  */
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/mac.S b/sim/testsuite/sim/or1k/mac.S
new file mode 100644
index 0000000000..f540b0b532
--- /dev/null
+++ b/sim/testsuite/sim/or1k/mac.S
@@ -0,0 +1,778 @@
+/* Tests the MAC instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x0000000c);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x40000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000006);\n
+# output: report(0x80000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x7ffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x0000000c);\n
+# output: report(0x00000000);\n
+# output: report(0x00000005);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0xfffffff9);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffff9);\n
+# output: report(0xfffffffe);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000006);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0xfffffffe);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x0000000c);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x40000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000006);\n
+# output: report(0x80000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x7ffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x0000000c);\n
+# output: report(0x00000000);\n
+# output: report(0x00000005);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0xfffffff9);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffff9);\n
+# output: report(0xfffffffe);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000006);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0xfffffffe);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x0000000c);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000006);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x7ffffffd);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x0000000c);\n
+# output: report(0x00000005);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000006);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffff9);\n
+# output: report(0xfffffff9);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x80000000);\n
+# output: report(0x80000006);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0xfffffffa);\n
+# output: report(0x3fffffff);\n
+# output: report(0xfffffffa);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffff4);\n
+# output: report(0xfffffffe);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000002);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000004);\n
+# output: report(0x00000000);\n
+# output: report(0x00000004);\n
+# output: report(0x7ffffffe);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000001);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000004);\n
+# output: report(0xfffffffe);\n
+# output: report(0x00000004);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0xffffffff);\n
+# output: report(0xfffffff9);\n
+# output: report(0x00000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x0000000c);\n
+# output: report(0x00000001);\n
+# output: report(0x00000005);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000005);\n
+# output: report(0x80000000);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x80000006);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0x80000000);\n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	.macro TEST_MACRC mac_hi, mac_lo, op1, op2
+	LOAD_IMMEDIATE r2, \mac_hi
+	MOVE_TO_SPR SPR_MACHI, r2
+	LOAD_IMMEDIATE r2, \mac_lo
+	MOVE_TO_SPR SPR_MACLO, r2
+	LOAD_IMMEDIATE r5, \op1
+	LOAD_IMMEDIATE r6, \op2
+	l.mac   r5, r6
+	l.macrc r3
+	REPORT_REG_TO_CONSOLE r3
+	.endm
+
+	.macro TEST_MAC mac_hi, mac_lo, op1, op2
+	LOAD_IMMEDIATE r2, \mac_hi
+	MOVE_TO_SPR SPR_MACHI, r2
+	LOAD_IMMEDIATE r2, \mac_lo
+	MOVE_TO_SPR SPR_MACLO, r2
+	LOAD_IMMEDIATE r5, \op1
+	LOAD_IMMEDIATE r6, \op2
+	l.mac r5, r6
+	MOVE_FROM_SPR r3, SPR_MACHI
+	REPORT_REG_TO_CONSOLE r3
+	MOVE_FROM_SPR r3, SPR_MACLO
+	REPORT_REG_TO_CONSOLE r3
+	.endm
+
+	.macro TEST_MACI mac_hi, mac_lo, op1, op2_immediate
+	LOAD_IMMEDIATE r2, \mac_hi
+	MOVE_TO_SPR SPR_MACHI, r2
+	LOAD_IMMEDIATE r2, \mac_lo
+	MOVE_TO_SPR SPR_MACLO, r2
+	LOAD_IMMEDIATE r5, \op1
+	l.maci r5, \op2_immediate
+	MOVE_FROM_SPR r3, SPR_MACHI
+	REPORT_REG_TO_CONSOLE r3
+	MOVE_FROM_SPR r3, SPR_MACLO
+	REPORT_REG_TO_CONSOLE r3
+	.endm
+
+	.macro TEST_MSB mac_hi, mac_lo, op1, op2
+	LOAD_IMMEDIATE r2, \mac_hi
+	MOVE_TO_SPR SPR_MACHI, r2
+	LOAD_IMMEDIATE r2, \mac_lo
+	MOVE_TO_SPR SPR_MACLO, r2
+	LOAD_IMMEDIATE r5, \op1
+	LOAD_IMMEDIATE r6, \op2
+	l.msb r5, r6
+	MOVE_FROM_SPR r3, SPR_MACHI
+	REPORT_REG_TO_CONSOLE r3
+	MOVE_FROM_SPR r3, SPR_MACLO
+	REPORT_REG_TO_CONSOLE r3
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test the l.mac instruction.  */
+
+	/* two small positive numbers  */
+
+	/* MAC two small positive numbers on a zero total  */
+	TEST_MAC 0x00000000, 0x00000000, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a small positive total  */
+	TEST_MAC 0x00000000, 0x00000006, 0x00000002, 0x00000003,
+
+	/* MAC two small positive numbers on a moderate positive total  */
+	TEST_MAC 0x00000000, 0xfffffffa, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a large positive total  */
+	TEST_MAC 0x3fffffff, 0xfffffffa, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a small negative total  */
+	TEST_MAC 0xffffffff, 0xfffffffa, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a moderate negative total  */
+	TEST_MAC 0xffffffff, 0x00000000, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a large negative total  */
+	TEST_MAC 0x80000000, 0x00000000, 0x00000002, 0x00000003
+
+	/* two moderate positive numbers  */
+
+	/* MAC two moderate positive numbers on a zero total  */
+	TEST_MAC 0x00000000, 0x00000000, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a small positive total  */
+	TEST_MAC 0x00000000, 0x00000002, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a moderate positive total  */
+	TEST_MAC 0x00000000, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a large positive total  */
+	TEST_MAC 0x7fffffff, 0x80000001, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a small negative total  */
+	TEST_MAC 0xffffffff, 0xffffffff, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a moderate negative total  */
+	TEST_MAC 0xffffffff, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a large negative total  */
+	TEST_MAC 0xfffffffe, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* two small negative numbers  */
+
+	/* MAC two small negative numbers on a zero total  */
+	TEST_MAC 0x00000000, 0x00000000, 0xfffffffe, 0xfffffffd
+
+	/* MAC two small negative numbers on a small positive total  */
+	TEST_MAC 0x00000000, 0x00000006, 0xfffffffe, 0xfffffffd
+
+	/* MAC two small negative numbers on a small negative total  */
+	TEST_MAC 0xffffffff, 0xffffffff, 0xfffffffe, 0xfffffffd
+
+	/* one small positive and one small negative  */
+
+	/* MAC one small positive and one small negative number on a zero
+	   total  */
+	TEST_MAC 0x00000000, 0x00000000, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a small
+	   positive total  */
+	TEST_MAC 0x00000000, 0x0000000c, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a
+	   moderate positive total  */
+	TEST_MAC 0x00000001, 0x00000005, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a large
+	   positive total  */
+	TEST_MAC 0x7fffffff, 0xffffffff, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a small
+	   negative total  */
+	TEST_MAC 0xffffffff, 0xffffffff, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a
+	   moderate negative total  */
+	TEST_MAC 0xffffffff, 0x00000005, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a large
+	   negative total  */
+	TEST_MAC 0x80000000, 0x00000006, 0x00000002, 0xfffffffd
+
+	/* one moderate positive and one moderate negative number  */
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   zero total  */
+	TEST_MAC 0x00000000, 0x00000000, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   small positive total  */
+	TEST_MAC 0x00000000, 0x00000006, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   moderate positive total  */
+	TEST_MAC 0x00000000, 0x80000000, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   large positive total  */
+	TEST_MAC 0x7fffffff, 0xffffffff, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   small negative total  */
+	TEST_MAC 0xffffffff, 0xffffffff, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   moderate negative total  */
+	TEST_MAC 0xffffffff, 0x7fffffff, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   large negative total  */
+	TEST_MAC 0x80000000, 0x80000000, 0x00008000, 0xffff0000
+
+	/* Test the l.maci instruction.  */
+
+	/* two small positive numbers  */
+
+	/* MAC two small positive numbers on a zero total  */
+	TEST_MACI 0x00000000, 0x00000000, 0x00000002, 0x0003
+
+	/* MAC two small positive numbers on a small positive total  */
+	TEST_MACI 0x00000000, 0x00000006, 0x00000002, 0x0003
+
+	/* MAC two small positive numbers on a moderate positive total  */
+	TEST_MACI 0x00000000, 0xfffffffa, 0x00000002, 0x0003
+
+	/* MAC two small positive numbers on a large positive total  */
+	TEST_MACI 0x3fffffff, 0xfffffffa, 0x00000002, 0x0003
+
+	/* MAC two small positive numbers on a small negative total  */
+	TEST_MACI 0xffffffff, 0xfffffffa, 0x00000002, 0x0003
+
+	/* MAC two small positive numbers on a moderate negative total  */
+	TEST_MACI 0xffffffff, 0x00000000, 0x00000002, 0x0003
+
+	/* MAC two small positive numbers on a large negative total  */
+	TEST_MACI 0x80000000, 0x00000000, 0x00000002, 0x0003
+
+	/* two moderate positive numbers  */
+
+	/* MAC two moderate positive numbers on a zero total  */
+	TEST_MACI 0x00000000, 0x00000000, 0x00010002, 0x7fff
+
+	/* MAC two moderate positive numbers on a small positive total  */
+	TEST_MACI 0x00000000, 0x00000002, 0x00010002, 0x7fff
+
+	/* MAC two moderate positive numbers on a moderate positive total  */
+	TEST_MACI 0x00000000, 0x80000002, 0x00010002, 0x7fff
+
+	/* MAC two moderate positive numbers on a large positive total  */
+	TEST_MACI 0x7fffffff, 0x80000001, 0x00010002, 0x7fff
+
+	/* MAC two moderate positive numbers on a small negative total  */
+	TEST_MACI 0xffffffff, 0xffffffff, 0x00010002, 0x7fff
+
+	/* MAC two moderate positive numbers on a moderate negative total  */
+	TEST_MACI 0xffffffff, 0x80000002, 0x00010002, 0x7fff
+
+	/* MAC two moderate positive numbers on a large negative total  */
+	TEST_MACI 0xfffffffe, 0x80000002, 0x00010002, 0x7fff
+
+	/* two small negative numbers  */
+
+	/* MAC two small negative numbers on a zero total  */
+	TEST_MACI 0x00000000, 0x00000000, 0xfffffffe, 0xfffd
+
+	/* MAC two small negative numbers on a small positive total  */
+	TEST_MACI 0x00000000, 0x00000006, 0xfffffffe, 0xfffd
+
+	/* MAC two small negative numbers on a small negative total  */
+	TEST_MACI 0xffffffff, 0xffffffff, 0xfffffffe, 0xfffd
+
+	/* one small positive and one small negative  */
+
+	/* MAC one small positive and one small negative number on a zero
+	   total  */
+	TEST_MACI 0x00000000, 0x00000000, 0x00000002, 0xfffd
+
+	/* MAC one small positive and one small negative number on a small
+	   positive total  */
+	TEST_MACI 0x00000000, 0x0000000c, 0x00000002, 0xfffd
+
+	/* MAC one small positive and one small negative number on a
+	   moderate positive total  */
+	TEST_MACI 0x00000001, 0x00000005, 0x00000002, 0xfffd
+
+	/* MAC one small positive and one small negative number on a large
+	   positive total  */
+	TEST_MACI 0x7fffffff, 0xffffffff, 0x00000002, 0xfffd
+
+	/* MAC one small positive and one small negative number on a small
+	   negative total  */
+	TEST_MACI 0xffffffff, 0xffffffff, 0x00000002, 0xfffd
+
+	/* MAC one small positive and one small negative number on a
+	   moderate negative total  */
+	TEST_MACI 0xffffffff, 0x00000005, 0x00000002, 0xfffd
+
+	/* MAC one small positive and one small negative number on a large
+	   negative total  */
+	TEST_MACI 0x80000000, 0x00000006, 0x00000002, 0xfffd
+
+	/* one moderate positive and one moderate negative  */
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   zero total  */
+	TEST_MACI 0x00000000, 0x00000000, 0x00010000, 0x8000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   small positive total  */
+	TEST_MACI 0x00000000, 0x00000006, 0x00010000, 0x8000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   moderate positive total  */
+	TEST_MACI 0x00000000, 0x80000000, 0x00010000, 0x8000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   large positive total  */
+	TEST_MACI 0x7fffffff, 0xffffffff, 0x00010000, 0x8000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   small negative total  */
+	TEST_MACI 0xffffffff, 0xffffffff, 0x00010000, 0x8000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   moderate negative total  */
+	TEST_MACI 0xffffffff, 0x7fffffff, 0x00010000, 0x8000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   large negative total  */
+	TEST_MACI 0x80000000, 0x80000000, 0x00010000, 0x8000
+
+	/* Test the l.macrc instruction.
+
+	   Note that these tests use the same input data as the ones for
+	   l.mac above.  The results are the same, but only the low 32-bits
+	   are compared.  */
+
+	/* two small positive numbers  */
+
+	/* MAC two small positive numbers on a zero total  */
+	TEST_MACRC 0x00000000, 0x00000000, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a small positive total  */
+	TEST_MACRC 0x00000000, 0x00000006, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a moderate positive total  */
+	TEST_MACRC 0x00000000, 0xfffffffa, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a large positive total  */
+	TEST_MACRC 0x3fffffff, 0xfffffffa, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a small negative total  */
+	TEST_MACRC 0xffffffff, 0xfffffffa, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a moderate negative total  */
+	TEST_MACRC 0xffffffff, 0x00000000, 0x00000002, 0x00000003
+
+	/* MAC two small positive numbers on a large negative total  */
+	TEST_MACRC 0x80000000, 0x00000000, 0x00000002, 0x00000003
+
+	/* two moderate positive numbers  */
+
+	/* MAC two moderate positive numbers on a zero total  */
+	TEST_MACRC 0x00000000, 0x00000000, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a small positive total  */
+	TEST_MACRC 0x00000000, 0x00000002, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a moderate positive total  */
+	TEST_MACRC 0x00000000, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a large positive total  */
+	TEST_MACRC 0x7fffffff, 0x80000001, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a small negative total  */
+	TEST_MACRC 0xffffffff, 0xffffffff, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a moderate negative total  */
+	TEST_MACRC 0xffffffff, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* MAC two moderate positive numbers on a large negative total  */
+	TEST_MACRC 0xfffffffe, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* two small negative numbers  */
+
+	/* MAC two small negative numbers on a zero total  */
+	TEST_MACRC 0x00000000, 0x00000000, 0xfffffffe, 0xfffffffd
+
+	/* MAC two small negative numbers on a small positive total  */
+	TEST_MACRC 0x00000000, 0x00000006, 0xfffffffe, 0xfffffffd
+
+	/* MAC two small negative numbers on a small negative total  */
+	TEST_MACRC 0xffffffff, 0xffffffff, 0xfffffffe, 0xfffffffd
+
+	/* one small positive and one small negative number  */
+
+	/* MAC one small positive and one small negative number on a zero
+	   total  */
+	TEST_MACRC 0x00000000, 0x00000000, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a small
+	   positive total  */
+	TEST_MACRC 0x00000000, 0x0000000c, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a
+	   moderate positive total  */
+	TEST_MACRC 0x00000001, 0x00000005, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a large
+	   positive total  */
+	TEST_MACRC 0x7fffffff, 0xffffffff, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a small
+	   negative total  */
+	TEST_MACRC 0xffffffff, 0xffffffff, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a
+	   moderate negative total  */
+	TEST_MACRC 0xffffffff, 0x00000005, 0x00000002, 0xfffffffd
+
+	/* MAC one small positive and one small negative number on a large
+	   negative total  */
+	TEST_MACRC 0x80000000, 0x00000006, 0x00000002, 0xfffffffd
+
+	/* one moderate positive and one moderate negative  */
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   zero total  */
+	TEST_MACRC 0x00000000, 0x00000000, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   small positive total  */
+	TEST_MACRC 0x00000000, 0x00000006, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   moderate positive total  */
+	TEST_MACRC 0x00000000, 0x80000000, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   large positive total  */
+	TEST_MACRC 0x7fffffff, 0xffffffff, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   small negative total  */
+	TEST_MACRC 0xffffffff, 0xffffffff, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   moderate negative total  */
+	TEST_MACRC 0xffffffff, 0x7fffffff, 0x00008000, 0xffff0000
+
+	/* MAC one moderate positive and one moderate negative number on a
+	   large negative total  */
+	TEST_MACRC 0x80000000, 0x80000000, 0x00008000, 0xffff0000
+
+	/* Test the l.msb instruction.  */
+
+	/* MSB two small positive numbers on a zero total  */
+	TEST_MSB 0x00000000, 0x00000000, 0x00000002, 0x00000003
+
+	/* MSB two small positive numbers on a small positive total  */
+	TEST_MSB 0x00000000, 0x0000000c, 0x00000002, 0x00000003
+
+	/* MSB two small positive numbers on a moderate positive total  */
+	TEST_MSB 0x00000001, 0x00000000, 0x00000002, 0x00000003
+
+	/* MSB two small positive numbers on a large positive total  */
+	TEST_MSB 0x40000000, 0x00000000, 0x00000002, 0x00000003
+
+	/* MSB two small positive numbers on a small negative total  */
+	TEST_MSB 0xffffffff, 0xfffffffa, 0x00000002, 0x00000003
+
+	/* MSB two small positive numbers on a moderate negative total  */
+	TEST_MSB 0xffffffff, 0x00000005, 0x00000002, 0x00000003
+
+	/* MSB two small positive numbers on a large negative total  */
+	TEST_MSB 0x80000000, 0x00000006, 0x00000002, 0x00000003
+
+	/* two moderate positive numbers  */
+
+	/* MSB two moderate positive numbers on a zero total  */
+	TEST_MSB 0x00000000, 0x00000000, 0x00008001, 0x0000fffe
+
+	/* MSB two moderate positive numbers on a small positive total  */
+	TEST_MSB 0x00000000, 0x00000002, 0x00008001, 0x0000fffe
+
+	/* MSB two moderate positive numbers on a moderate positive total  */
+	TEST_MSB 0x00000000, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* MSB two moderate positive numbers on a large positive total  */
+	TEST_MSB 0x7fffffff, 0x7ffffffd, 0x00008001, 0x0000fffe
+
+	/* MSB two moderate positive numbers on a small negative total  */
+	TEST_MSB 0xffffffff, 0xffffffff, 0x00008001, 0x0000fffe
+
+	/* MSB two moderate positive numbers on a moderate negative total  */
+	TEST_MSB 0xffffffff, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* MSB two moderate positive numbers on a large negative total  */
+	TEST_MSB 0xfffffffe, 0x80000002, 0x00008001, 0x0000fffe
+
+	/* two small negative numbers  */
+
+	/* MSB two small negative numbers on a zero total  */
+	TEST_MSB 0x00000000, 0x00000006, 0xfffffffe, 0xfffffffd
+
+	/* MSB two small negative numbers on a small positive total  */
+	TEST_MSB 0x00000000, 0x0000000c, 0xfffffffe, 0xfffffffd
+
+	/* MSB two small negative numbers on a small negative total  */
+	TEST_MSB 0xffffffff, 0xffffffff, 0xfffffffe, 0xfffffffd
+
+	/* one small positive and one small negative number  */
+
+	/* MSB one small positive and one small negative number on a zero
+	   total  */
+	TEST_MSB 0x00000000, 0x00000000, 0x00000002, 0xfffffffd
+
+	/* MSB one small positive and one small negative number on a small
+	   positive total  */
+	TEST_MSB 0x00000000, 0x00000006, 0x00000002, 0xfffffffd
+
+	/* MSB one small positive and one small negative number on a
+	   moderate positive total  */
+	TEST_MSB 0x00000000, 0xffffffff, 0x00000002, 0xfffffffd
+
+	/* MSB one small positive and one small negative number on a large
+	   positive total  */
+	TEST_MSB 0x7fffffff, 0xfffffff9, 0x00000002, 0xfffffffd
+
+	/* MSB one small positive and one small negative number on a small
+	   negative total  */
+	TEST_MSB 0xffffffff, 0xfffffff9, 0x00000002, 0xfffffffd
+
+	/* MSB one small positive and one small negative number on a
+	   moderate negative total  */
+	TEST_MSB 0xfffffffe, 0xffffffff, 0x00000002, 0xfffffffd
+
+	/* MSB one small positive and one small negative number on a large
+	   negative total  */
+	TEST_MSB 0x80000000, 0x00000000, 0x00000002, 0xfffffffd
+
+	/* one moderate positive and one moderate negative number  */
+
+	/* MSB one moderate positive and one moderate negative number on a
+	   zero total  */
+	TEST_MSB 0x00000000, 0x00000000, 0x00008000, 0xffff0000
+
+	/* MSB one moderate positive and one moderate negative number on a
+	   small positive total  */
+	TEST_MSB 0x00000000, 0x00000006, 0x00008000, 0xffff0000
+
+	/* MSB one moderate positive and one moderate negative number on a
+	   moderate positive total  */
+	TEST_MSB 0x00000000, 0x80000000, 0x00008000, 0xffff0000
+
+	/* MSB one moderate positive and one moderate negative number on a
+	   large positive total  */
+	TEST_MSB 0x7fffffff, 0x7fffffff, 0x00008000, 0xffff0000
+
+	/* MSB one moderate positive and one moderate negative number on a
+	   small negative total  */
+	TEST_MSB 0xffffffff, 0xffffffff, 0x00008000, 0xffff0000
+
+	/* MSB one moderate positive and one moderate negative number on a
+	   moderate negative total  */
+	TEST_MSB 0xfffffffe, 0xffffffff, 0x00008000, 0xffff0000
+
+	/* MSB one moderate positive and one moderate negative number on a
+	   large negative total  */
+	TEST_MSB 0x80000000, 0x00000000, 0x00008000, 0xffff0000
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/mfspr.S b/sim/testsuite/sim/or1k/mfspr.S
new file mode 100644
index 0000000000..577e03d754
--- /dev/null
+++ b/sim/testsuite/sim/or1k/mfspr.S
@@ -0,0 +1,171 @@
+/* Tests instructions l.mfspr and l.mtspr.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000000);\n
+# output: report(0x00002801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002801);\n
+# output: report(0x00000000);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002801);\n
+# output: report(0x00002801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00000801);\n
+# output: report(0x00002000);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002000);\n
+# output: report(0x00000801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002801);\n
+# output: report(0x00000001);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00000800);\n
+# output: report(0x00002801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x00002801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002801);\n
+# output: report(0x00000000);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002801);\n
+# output: report(0x00002801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00000801);\n
+# output: report(0x00002000);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002000);\n
+# output: report(0x00000801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00002801);\n
+# output: report(0x00000001);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: report(0x00000800);\n
+# output: report(0x00002801);\n
+# output: report(0xdeadbeef);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-env.h"
+
+#define MACLO_VAL 0xdeadbeef
+
+	/* A macro to carry out a test of l.mfspr.
+
+	   MACLO (0x2801) is used as the SPR, since it can be read and
+	   cleared using l.macrc and can be set using l.maci.  spr_number
+	   and immediate_val_to_or should be chosen to address this
+	   register.
+
+	   The value placed in the register is entirely arbitrary - we use
+	   0xdeadbeef.  */
+
+	.macro TEST_MFSPR  spr_number, immediate_val_to_or
+	REPORT_IMMEDIATE_TO_CONSOLE \spr_number
+	REPORT_IMMEDIATE_TO_CONSOLE \immediate_val_to_or
+	/* Write MACLO_VAL to MACLO.  */
+	l.macrc r2
+	LOAD_IMMEDIATE r2, MACLO_VAL
+	l.maci  r2, 1
+	LOAD_IMMEDIATE r5, \spr_number
+	l.mfspr r4, r5, \immediate_val_to_or
+	REPORT_REG_TO_CONSOLE r4
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	/* A macro to carry out a test of l.mtspr
+
+	   MACLO (0x2801) is used as the SPR, since it can be read and
+	   cleared using l.macrc and can be set using l.maci.  The
+	   arguments spr_number and immediate_val_to_or should be chosen
+	   to address this register.
+
+	   The value placed in the register is entirely arbitrary - we use
+	   0xdeadbeef.  */
+
+	.macro TEST_MTSPR  spr_number, immediate_val_to_or
+	REPORT_IMMEDIATE_TO_CONSOLE \spr_number
+	REPORT_IMMEDIATE_TO_CONSOLE \immediate_val_to_or
+	/* Clear MACLO  */
+	l.macrc r2
+	LOAD_IMMEDIATE r4, MACLO_VAL
+	LOAD_IMMEDIATE r5, \spr_number
+	l.mtspr r5, r4, \immediate_val_to_or
+	/* Retrieve MACLO.  */
+	l.macrc r4
+	REPORT_REG_TO_CONSOLE r4
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test the l.mfspr instruction with a range of operands.  */
+
+	/* Move a test value using zero in the register.  */
+	TEST_MFSPR SPR_VR, SPR_MACLO /* 0x0000, 0x2801  */
+
+	/* Move a test value using zero as the constant.  */
+	TEST_MFSPR SPR_MACLO, SPR_VR /* 0x2801, 0x0000  */
+
+	/* Move a test value using non-zero in both register and constant.  */
+
+	/* Some of these values will not give the correct result if OR
+	   rather than ADD is used to determine the SPR address.  */
+	TEST_MFSPR SPR_MACLO,  SPR_MACLO /* 0x2801, 0x2801  */
+	TEST_MFSPR SPR_DMMUPR, SPR_ICCR /* 0x0801, 0x2000  */
+	TEST_MFSPR SPR_ICCR,   SPR_DMMUPR /* 0x2000, 0x0801  */
+	TEST_MFSPR SPR_MACLO,  SPR_UPR /* 0x2801, 0x0001  */
+	TEST_MFSPR SPR_DMMUCR, SPR_MACLO /* 0x0800, 0x2801  */
+
+	/* Test the l.mtspr instruction with a range of operands.  */
+
+	/* Move a test value using zero in the register.  */
+	TEST_MTSPR SPR_VR, SPR_MACLO /* 0x0000, 0x2801  */
+
+	/* Move a test value using zero as the constant.  */
+	TEST_MTSPR SPR_MACLO, SPR_VR /* 0x2801, 0x0000  */
+
+	/* Move a test value using non-zero in both register and constant.  */
+
+	/* Some of these values will not give the correct result if or
+	   rather than add is used to determine the SPR address.  */
+	TEST_MTSPR SPR_MACLO,  SPR_MACLO /* 0x2801, 0x2801  */
+	TEST_MTSPR SPR_DMMUPR, SPR_ICCR /* 0x0801, 0x2000  */
+	TEST_MTSPR SPR_ICCR,   SPR_DMMUPR /* 0x2000, 0x0801  */
+	TEST_MTSPR SPR_MACLO,  SPR_UPR /* 0x2801, 0x0001  */
+	TEST_MTSPR SPR_DMMUCR, SPR_MACLO /* 0x0800, 0x2801  */
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/mul.S b/sim/testsuite/sim/or1k/mul.S
new file mode 100644
index 0000000000..484d31c163
--- /dev/null
+++ b/sim/testsuite/sim/or1k/mul.S
@@ -0,0 +1,574 @@
+/* Tests the multiply instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00008001);\n
+# output: report(0x0000fffe);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00008000);\n
+# output: report(0x00010000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00010000);\n
+# output: report(0x00010000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000006);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0xffff0002);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0xffff0000);\n
+# output: report(0x80010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff0000);\n
+# output: report(0xfffeffff);\n
+# output: report(0x00010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000002);\n
+# output: report(0xfffffffd);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff8000);\n
+# output: report(0x00010000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0x00010000);\n
+# output: report(0x7fff0000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00008000);\n
+# output: report(0x00010000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x00000002);\n
+# output: report(0xfffffffd);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0xffff0000);\n
+# output: report(0x80010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00010002);\n
+# output: report(0x00007fff);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00020000);\n
+# output: report(0x00004000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00040000);\n
+# output: report(0x00004000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffffe);\n
+# output: report(0x0000fffd);\n
+# output: report(0x00000006);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffefffe);\n
+# output: report(0x00008001);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffe0000);\n
+# output: report(0x0000bfff);\n
+# output: report(0x80020000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffdfffe);\n
+# output: report(0x00008000);\n
+# output: report(0x00010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000002);\n
+# output: report(0x0000fffd);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00010000);\n
+# output: report(0x00008000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffdfffc);\n
+# output: report(0x00004000);\n
+# output: report(0x7fff0000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00020000);\n
+# output: report(0x00004000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0xfffffffe);\n
+# output: report(0x0000fffd);\n
+# output: report(0x00000006);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffdfffe);\n
+# output: report(0x00008000);\n
+# output: report(0x00010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x00000002);\n
+# output: report(0x00000003);\n
+# output: report(0x00000006);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00008001);\n
+# output: report(0x0000fffe);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00008000);\n
+# output: report(0x00010000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00010000);\n
+# output: report(0x00010000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffffe);\n
+# output: report(0xfffffffd);\n
+# output: report(0x00000006);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0xffff0002);\n
+# output: report(0x7ffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0xffff0000);\n
+# output: report(0x80010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff0000);\n
+# output: report(0xfffeffff);\n
+# output: report(0x00010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000002);\n
+# output: report(0xfffffffd);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff8000);\n
+# output: report(0x00010000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0x00010000);\n
+# output: report(0x7fff0000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80000000);\n
+# output: report(0x00000001);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00008000);\n
+# output: report(0x00010000);\n
+# output: report(0x80000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000002);\n
+# output: report(0xfffffffd);\n
+# output: report(0xfffffffa);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffff7fff);\n
+# output: report(0xffff0000);\n
+# output: report(0x80010000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .exception_vectors
+
+	/* Range exception.  */
+	.org	0xb00
+
+	/* The handling is a bit dubious at present.  We just patch the
+	   instruction with l.nop and restart.  This will go wrong in branch
+	   delay slots, but we are not testing that here.  */
+	l.addi r1, r1, -EXCEPTION_STACK_SKIP_SIZE
+	PUSH r2
+	PUSH r3
+	/* Save the address of the instruction that caused the problem.  */
+	MOVE_FROM_SPR r2, SPR_EPCR_BASE
+	LOAD_IMMEDIATE r3, 0x15000000 /* Opcode for l.nop  */
+	l.sw	0(r2), r3
+	POP r3
+	POP r2
+	l.addi r1, r1, EXCEPTION_STACK_SKIP_SIZE
+	l.rfe
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test l.mul  */
+
+	/* Multiply two small positive numbers.  This should set no flags.
+	   */
+	TEST_INST_I32_I32 l.mul, 0x00000002, 0x00000003
+
+	/* Multiply two quite large positive numbers.  This should set no
+	   flags  */
+	TEST_INST_I32_I32 l.mul, 0x00008001, 0x0000fffe
+
+	/* Multiply two slightly too large positive numbers.  This should
+	   set the overflow, but not the carry flag .  */
+	TEST_INST_I32_I32 l.mul, 0x00008000, 0x00010000
+
+	/* Multiply two large positive numbers.  This should set both the
+	   carry and overflow flags (even though the result is not a
+	   negative number.  */
+	TEST_INST_I32_I32 l.mul, 0x00010000, 0x00010000
+
+	/* Multiply two small negative numbers.  This will set the carry
+	   flag, but not the overflow flag.  */
+	TEST_INST_I32_I32 l.mul, 0xfffffffe, 0xfffffffd
+
+	/* Multiply two quite large negative numbers.  This will set the
+	   carry flag, but not the overflow flag.  */
+	TEST_INST_I32_I32 l.mul, 0xffff7fff, 0xffff0002
+
+	/* Multiply two slightly too large negative numbers.  This should
+	   set both the overflow, and the carry flags  */
+	TEST_INST_I32_I32 l.mul, 0xffff7fff, 0xffff0000
+
+	/* Multiply two large negative numbers.  This should set the
+	   both the carry and overflow flags (even though the result is a
+	   positive number.  */
+	TEST_INST_I32_I32 l.mul, 0xffff0000, 0xfffeffff
+
+	/* Multiply one small negative number and one small positive
+	   number.  This will set the carry flag, but not the overflow
+	   flag.  */
+	TEST_INST_I32_I32 l.mul, 0x00000002, 0xfffffffd
+
+	/* Multiply one quite large negative number and one quite large
+	   positive number.  This will set the carry, but not the
+	   overflow flag.  */
+	TEST_INST_I32_I32 l.mul, 0xffff8000, 0x00010000
+
+	/* Multiply one slightly too large negative number and one slightly
+	   too large positive number.  This should set both the carry and
+	   overflow flags.  */
+	TEST_INST_I32_I32 l.mul, 0xffff7fff, 0x00010000
+
+	/* Multiply the largest negative number by positive unity.  This
+	   should set neither carry, nor overflow flag.  */
+	TEST_INST_I32_I32 l.mul, 0x80000000, 0x00000001
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that an overflow alone causes a RANGE Exception.  */
+	TEST_INST_I32_I32 l.mul, 0x00008000, 0x00010000
+
+	/* Check that a carry alone does not cause a RANGE Exception.  */
+	TEST_INST_I32_I32 l.mul, 0x00000002, 0xfffffffd
+
+	/* Check that carry and overflow together cause an exception.  */
+	TEST_INST_I32_I32 l.mul, 0xffff7fff, 0xffff0000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+
+	/* Test l.muli  */
+
+	/* Multiply two small positive numbers.  This should set no flags.  */
+	TEST_INST_I32_I16 l.muli, 0x00000002, 0x0003
+
+	/* Multiply two quite large positive numbers.  This should set no
+	   flags */
+	TEST_INST_I32_I16 l.muli, 0x00010002, 0x7fff
+
+	/* Multiply two slightly too large positive numbers.  This should
+	   set the overflow, but not the carry flag.  */
+	TEST_INST_I32_I16 l.muli, 0x00020000, 0x4000
+
+	/* Multiply two large positive numbers.  This should set both the
+	   carry and overflow flags (even though the result is not a
+	   negative number.  */
+	TEST_INST_I32_I16 l.muli, 0x00040000, 0x4000
+
+	/* Multiply two small negative numbers.  This should set the
+	   carry flag, but not the overflow flag.  */
+	TEST_INST_I32_I16 l.muli, 0xfffffffe, 0xfffd
+
+	/* Multiply two quite large negative numbers.  This will set the
+	   carry, but not the overflow flag.  */
+	TEST_INST_I32_I16 l.muli, 0xfffefffe, 0x8001
+
+	/* Multiply two slightly too large negative numbers.  This should
+	   set both the overflow, and the carry flags  */
+	TEST_INST_I32_I16 l.muli, 0xfffe0000, 0xbfff
+
+	/* Multiply two large negative numbers.  This should set the both
+	   the carry and overflow flags (even though the result is a
+	   positive number.  */
+	TEST_INST_I32_I16 l.muli, 0xfffdfffe, 0x8000
+
+	/* Multiply one small negative number and one small positive
+	   number.  This will set the carry flag, but not the overflow
+	   flag.  */
+	TEST_INST_I32_I16 l.muli, 0x00000002, 0xfffd
+
+	/* Multiply one quite large negative number and one quite large
+	   positive number.  This will set the carry flag, but not the
+	   overflow flag.  */
+	TEST_INST_I32_I16 l.muli, 0x00010000, 0x8000
+
+	/* Multiply one slightly too large negative number and one slightly
+	   too large positive number.  This should set both the carry and
+	   overflow flags.  */
+	TEST_INST_I32_I16 l.muli, 0xfffdfffc, 0x4000
+
+	/* Multiply the largest negative number by positive unity.  Should
+	   set neither carry, nor overflow flag.  */
+	TEST_INST_I32_I16 l.muli, 0x80000000, 0x0001
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that an overflow alone causes a RANGE Exception.  */
+	TEST_INST_I32_I16 l.muli, 0x00020000, 0x4000
+
+	/* Check that a carry alone does not cause a RANGE Exception.  */
+	TEST_INST_I32_I16 l.muli, 0xfffffffe, 0xfffd
+
+	/* Check that carry and overflow together cause an exception.  */
+	TEST_INST_I32_I16 l.muli, 0xfffdfffe, 0x8000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test l.mulu  */
+
+	/* Multiply two small positive numbers.  This should set no flags.  */
+	TEST_INST_I32_I32 l.mulu, 0x00000002, 0x00000003
+
+	/* Multiply two quite large positive numbers.  This should set no
+	   flags.  */
+	TEST_INST_I32_I32 l.mulu, 0x00008001, 0x0000fffe
+
+	/* Multiply two slightly too large positive numbers.  This will set
+	   no flags.  */
+	TEST_INST_I32_I32 l.mulu, 0x00008000, 0x00010000
+
+	/* Multiply two large positive numbers.  This will set the overflow
+	   flag.  */
+	TEST_INST_I32_I32 l.mulu, 0x00010000, 0x00010000
+
+	/* Multiply two small negative numbers.  This will set the
+	   carry flag, but not the overflow flag.  */
+	TEST_INST_I32_I32 l.mulu, 0xfffffffe, 0xfffffffd
+
+	/* Multiply two quite large negative numbers.  This will set the
+	   carry flag, but not the overflow flag.  */
+	TEST_INST_I32_I32 l.mulu, 0xffff7fff, 0xffff0002
+
+	/* Multiply two slightly too large negative numbers.  This will set
+	   the carry flag, and not the overflow flag  */
+	TEST_INST_I32_I32 l.mulu, 0xffff7fff, 0xffff0000
+
+	/* Multiply two large negative numbers.  This will set the both the
+	   carry flag (even though the result is a positive number.)  */
+	TEST_INST_I32_I32 l.mulu, 0xffff0000, 0xfffeffff
+
+	/* Multiply one small negative number and one small positive
+	   number.  This will set the carry flag, but not the overflow
+	   flag.  */
+	TEST_INST_I32_I32 l.mulu, 0x00000002, 0xfffffffd
+
+	/* Multiply one quite large negative number and one quite large
+	   positive number.  This will set the carry flag, but not the
+	   overflow flag.  */
+	TEST_INST_I32_I32 l.mulu, 0xffff8000, 0x00010000
+
+	/* Multiply one slightly too large negative number and one slightly
+	   too large positive number.  This will set the carry flag, but
+	   not the overflow flag.  */
+	TEST_INST_I32_I32 l.mulu, 0xffff7fff, 0x00010000
+
+	/* Multiply the largest negative number by positive unity.  Should
+	   set neither carry, nor overflow flag.  */
+	TEST_INST_I32_I32 l.mulu, 0x80000000, 0x00000001
+
+	/* Check that range exceptions are never triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that what would cause an overflow alone in 2's complement
+	   does not cause a RANGE Exception.  */
+	TEST_INST_I32_I32 l.mulu, 0x00008000, 0x00010000
+
+	/* Check that a carry alone does not cause a RANGE Exception.  */
+	TEST_INST_I32_I32 l.mulu, 0x00000002, 0xfffffffd
+
+	/* Check that what would cause an overflow and carry in 2's
+	   complement does not cause a RANGE Exception.  */
+	TEST_INST_I32_I32 l.mulu, 0xffff7fff, 0xffff0000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/or.S b/sim/testsuite/sim/or1k/or.S
new file mode 100644
index 0000000000..691b921bd0
--- /dev/null
+++ b/sim/testsuite/sim/or1k/or.S
@@ -0,0 +1,199 @@
+/* Tests instructions l.or, l.ori.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x55555555);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x55555555);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xb38f0f83);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xc4c70f07);\n
+# output: report(0xccf7ff7f);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x38f0f83b);\n
+# output: report(0xbbffffbb);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x0000ffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x0000aaaa);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00005555);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00005555);\n
+# output: report(0xaaaaffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000f83);\n
+# output: report(0x4c70ffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000f07);\n
+# output: report(0x4c70ff7f);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000f83b);\n
+# output: report(0xb38fffbb);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Always set OVE.  We should never trigger an exception, even if
+	   this bit is set.  */
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test the l.or instruction with a range of operands.  */
+
+	TEST_INST_I32_I32 l.or, 0x00000000, 0x00000000
+	TEST_INST_I32_I32 l.or, 0xffffffff, 0xffffffff
+	TEST_INST_I32_I32 l.or, 0xaaaaaaaa, 0x00000000
+	TEST_INST_I32_I32 l.or, 0xaaaaaaaa, 0xaaaaaaaa
+	TEST_INST_I32_I32 l.or, 0x55555555, 0x00000000
+	TEST_INST_I32_I32 l.or, 0x55555555, 0x55555555
+	TEST_INST_I32_I32 l.or, 0xaaaaaaaa, 0x55555555
+	TEST_INST_I32_I32 l.or, 0x4c70f07c, 0xb38f0f83
+	TEST_INST_I32_I32 l.or, 0x4c70f07c, 0xc4c70f07
+	TEST_INST_I32_I32 l.or, 0xb38f0f83, 0x38f0f83b
+
+	/* Test the l.ori instruction with a range of operands.  */
+	TEST_INST_I32_I16 l.ori, 0x00000000, 0x0000
+	TEST_INST_I32_I16 l.ori, 0xffffffff, 0xffff
+	TEST_INST_I32_I16 l.ori, 0xaaaaaaaa, 0x0000
+	TEST_INST_I32_I16 l.ori, 0xaaaaaaaa, 0xaaaa
+	TEST_INST_I32_I16 l.ori, 0x55555555, 0x0000
+	TEST_INST_I32_I16 l.ori, 0x55555555, 0x5555
+	TEST_INST_I32_I16 l.ori, 0xaaaaaaaa, 0x5555
+	TEST_INST_I32_I16 l.ori, 0x4c70f07c, 0x0f83
+	TEST_INST_I32_I16 l.ori, 0x4c70f07c, 0x0f07
+	TEST_INST_I32_I16 l.ori, 0xb38f0f83, 0xf83b
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/or1k-asm-test-env.h b/sim/testsuite/sim/or1k/or1k-asm-test-env.h
new file mode 100644
index 0000000000..38e01f6927
--- /dev/null
+++ b/sim/testsuite/sim/or1k/or1k-asm-test-env.h
@@ -0,0 +1,59 @@
+/* Testsuite macros for OpenRISC.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+#ifndef OR1K_ASM_TEST_ENV_H
+#define OR1K_ASM_TEST_ENV_H
+
+#include "or1k-asm.h"
+#include "or1k-asm-test.h"
+
+	.macro STANDARD_TEST_HEADER
+	/* Without the "a" (allocatable) flag, this section gets some
+	   default flags and is discarded by objcopy when flattening to
+	   the binary file.  */
+	.section .exception_vectors, "ax"
+	.org    0x100
+	.global _start
+_start:
+	/* Clear R0 on start-up. There is no guarantee that R0 is hardwired
+	   to zero and indeed it is not when simulating.  */
+	CLEAR_REG r0
+	OR1K_DELAYED_NOP(l.j test_startup)
+	.section .text
+test_startup:
+	.endm
+
+	.macro STANDARD_TEST_BODY
+	LOAD_IMMEDIATE STACK_POINTER_R1, stack_begin
+	CLEAR_BSS r3, r4
+	CALL r3, start_tests
+	EXIT_SIMULATION_WITH_IMMEDIATE_EXIT_CODE SEC_SUCCESS
+	.section .stack
+	.space 4096 /* We need more than EXCEPTION_STACK_SKIP_SIZE bytes.  */
+stack_begin:
+	.endm
+
+	.macro STANDARD_TEST_ENVIRONMENT
+	/* One of the test cases needs to do some tests before setting up
+	   the stack and so on.  That's the reason this macro is split into
+	   2 parts allowing the caller to inject code between the 2
+	   initialisation phases.  */
+	STANDARD_TEST_HEADER
+	STANDARD_TEST_BODY
+	.endm
+
+#endif /* OR1K_ASM_TEST_ENV_H */
diff --git a/sim/testsuite/sim/or1k/or1k-asm-test-helpers.h b/sim/testsuite/sim/or1k/or1k-asm-test-helpers.h
new file mode 100644
index 0000000000..49be3a28e6
--- /dev/null
+++ b/sim/testsuite/sim/or1k/or1k-asm-test-helpers.h
@@ -0,0 +1,121 @@
+/* Testsuite helpers for OpenRISC.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+#ifndef OR1K_ASM_TEST_HELPERS_H
+#define OR1K_ASM_TEST_HELPERS_H
+
+#include "spr-defs.h"
+#include "or1k-asm-test-env.h"
+
+	/* During exception handling the instruction under test is
+	   overwritten with a nop.  Here we check if that is the case and
+	   report.  */
+
+	.macro REPORT_EXCEPTION  instruction_addr
+	PUSH r2
+	PUSH r3
+	LOAD_IMMEDIATE r3, \instruction_addr
+	l.lws r2, 0(r3)
+	LOAD_IMMEDIATE r3, 0x15000000 /* l.nop */
+	l.sfeq r2, r3
+	OR1K_DELAYED_NOP (l.bnf 1f)
+	REPORT_IMMEDIATE_TO_CONSOLE 0x00000001
+	OR1K_DELAYED_NOP (l.j 2f)
+1:
+	REPORT_IMMEDIATE_TO_CONSOLE 0x00000000
+2:
+	POP r3
+	POP r2
+	.endm
+
+	/* Test that will set and clear sr flags, run instruction report
+	   the result and whether or not there was an exception.
+
+	   Arguments:
+	     flags_to_set - sr flags to set
+	     flags_to_clear - sr flags to clear
+	     opcode - the instruction to execute
+	     op1 - first argument to the instruction
+	     op2 - second argument to the function
+
+	   Reports:
+	     report(0x00000001);\n op1
+	     report(0x00000002);\n op1
+	     report(0x00000003);\n result
+	     report(0x00000000);\n 1 if carry
+	     report(0x00000000);\n 1 if overflow
+	     report(0x00000000);\n 1 if exception
+	     \n */
+
+	.macro TEST_INST_FF_I32_I32  flags_to_set, flags_to_clear, opcode, op1, op2
+	LOAD_IMMEDIATE r5, \op1
+	LOAD_IMMEDIATE r6, \op2
+	REPORT_REG_TO_CONSOLE r5
+	REPORT_REG_TO_CONSOLE r6
+	/* Clear the last exception address.  */
+	MOVE_TO_SPR SPR_EPCR_BASE, ZERO_R0
+	SET_SPR_SR_FLAGS   \flags_to_set  , r2, r3
+	CLEAR_SPR_SR_FLAGS \flags_to_clear, r2, r3
+\@1$:	\opcode r4, r5, r6
+	MOVE_FROM_SPR r2, SPR_SR /* Save the flags.  */
+	REPORT_REG_TO_CONSOLE r4
+
+	REPORT_BIT_TO_CONSOLE r2, SPR_SR_CY
+	REPORT_BIT_TO_CONSOLE r2, SPR_SR_OV
+	REPORT_EXCEPTION \@1$
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	.macro TEST_INST_FF_I32_I16  flags_to_set, flags_to_clear, opcode, op1, op2
+	LOAD_IMMEDIATE r5, \op1
+	REPORT_REG_TO_CONSOLE r5
+	REPORT_IMMEDIATE_TO_CONSOLE \op2
+	SET_SPR_SR_FLAGS   \flags_to_set  , r2, r3
+	CLEAR_SPR_SR_FLAGS \flags_to_clear, r2, r3
+	/* Clear the last exception address.  */
+	MOVE_TO_SPR SPR_EPCR_BASE, ZERO_R0
+\@1$:	\opcode r4, r5, \op2
+	MOVE_FROM_SPR r2, SPR_SR /* Save the flags.  */
+	REPORT_REG_TO_CONSOLE r4
+	REPORT_BIT_TO_CONSOLE r2, SPR_SR_CY
+	REPORT_BIT_TO_CONSOLE r2, SPR_SR_OV
+	REPORT_EXCEPTION \@1$
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	.macro TEST_INST_I32_I32  opcode, op1, op2
+	TEST_INST_FF_I32_I32 0, 0, \opcode, \op1, \op2
+	.endm
+
+	.macro TEST_INST_I32_I16  opcode, op1, op2
+	TEST_INST_FF_I32_I16 0, 0, \opcode, \op1, \op2
+	.endm
+
+	.macro CHECK_CARRY_AND_OVERFLOW_NOT_SET  overwritten_reg1, overwritten_reg2
+	MOVE_FROM_SPR \overwritten_reg1, SPR_SR
+
+	LOAD_IMMEDIATE \overwritten_reg2, SPR_SR_CY + SPR_SR_OV
+	l.and   \overwritten_reg1, \overwritten_reg1, \overwritten_reg2
+	l.sfne \overwritten_reg1, ZERO_R0
+
+	OR1K_DELAYED_NOP (l.bnf \@2$)
+
+	EXIT_SIMULATION_WITH_IMMEDIATE_EXIT_CODE  SEC_GENERIC_ERROR
+\@2$:
+	.endm
+
+#endif /* OR1K_ASM_TEST_HELPERS_H */
diff --git a/sim/testsuite/sim/or1k/or1k-asm-test.h b/sim/testsuite/sim/or1k/or1k-asm-test.h
new file mode 100644
index 0000000000..83a8bb108c
--- /dev/null
+++ b/sim/testsuite/sim/or1k/or1k-asm-test.h
@@ -0,0 +1,226 @@
+/* Testsuite architecture macros for OpenRISC.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+#ifndef OR1K_ASM_TEST_H
+#define OR1K_ASM_TEST_H
+
+#include "spr-defs.h"
+
+/* Register definitions */
+
+/* The "jump and link" instructions store the return address in R9.  */
+#define LINK_REGISTER_R9 r9
+
+/* These register definitions match the ABI.  */
+#define ZERO_R0          r0
+#define STACK_POINTER_R1 r1
+#define FRAME_POINTER_R2 r2
+#define RETURN_VALUE_R11 r11
+
+	/* Load/move/clear helpers  */
+
+	.macro LOAD_IMMEDIATE  reg, val
+	l.movhi \reg,       hi ( \val )
+	l.ori   \reg, \reg, lo ( \val )
+	.endm
+
+	.macro MOVE_REG  dest_reg, src_reg
+	.ifnes "\dest_reg","\src_reg"
+	l.ori \dest_reg, \src_reg, 0
+	.endif
+	.endm
+
+	.macro CLEAR_REG reg
+	l.movhi \reg, 0
+	.endm
+
+	.macro MOVE_FROM_SPR  reg, spr_reg
+	l.mfspr \reg, ZERO_R0, \spr_reg
+	.endm
+
+	.macro MOVE_TO_SPR  spr_reg, reg
+	l.mtspr ZERO_R0, \reg, \spr_reg
+	.endm
+
+	.macro SET_SPR_SR_FLAGS flag_mask, scratch_reg_1, scratch_reg_2
+	/* We cannot use PUSH and POP here because some flags like Carry
+	   would get overwritten.  */
+
+	/* We could optimise this routine, as instruction l.mtspr already
+	   does a logical OR.  */
+	MOVE_FROM_SPR \scratch_reg_2, SPR_SR
+	LOAD_IMMEDIATE \scratch_reg_1, \flag_mask
+	l.or \scratch_reg_2, \scratch_reg_2, \scratch_reg_1
+	MOVE_TO_SPR SPR_SR, \scratch_reg_2
+	.endm
+
+	.macro CLEAR_SPR_SR_FLAGS flag_mask, scratch_reg_1, scratch_reg_2
+	/* We cannot use PUSH and POP here because some flags like Carry
+	   would get overwritten.  */
+
+	MOVE_FROM_SPR \scratch_reg_2, SPR_SR
+	LOAD_IMMEDIATE \scratch_reg_1, ~\flag_mask
+	l.and \scratch_reg_2, \scratch_reg_2, \scratch_reg_1
+	MOVE_TO_SPR SPR_SR, \scratch_reg_2
+
+	.endm
+
+	/* Stack helpers  */
+
+/* This value is defined in the OpenRISC 1000 specification.  */
+#define EXCEPTION_STACK_SKIP_SIZE  128
+
+	/* WARNING: Functions without prolog cannot use these PUSH or POP
+	   macros.
+
+	   PERFORMANCE WARNING: These PUSH/POP macros are convenient, but
+	   can lead to slow code.  If you need to PUSH or POP several
+	   registers, it's faster to use non-zero offsets when
+	   loading/storing and then increment/decrement the stack pointer
+	   just once.  */
+
+	.macro PUSH reg
+	l.addi STACK_POINTER_R1, STACK_POINTER_R1, -4
+	l.sw   0(STACK_POINTER_R1), \reg
+	.endm
+
+	/* WARNING: see the warnings for PUSH.  */
+	.macro POP reg
+	l.lwz  \reg, 0(STACK_POINTER_R1)
+	l.addi STACK_POINTER_R1, STACK_POINTER_R1, 4
+	.endm
+
+/* l.nop definitions for simulation control and console output.  */
+
+/* Register definitions for the simulation l.nop codes.  */
+#define NOP_REPORT_R3 r3
+#define NOP_EXIT_R3   r3
+
+/* SEC = Simulation Exit Code  */
+#define SEC_SUCCESS            0
+#define SEC_RETURNED_FROM_MAIN 1
+#define SEC_GENERIC_ERROR      2
+
+	/* When running under the simulator, this l.nop code terminates the
+	   simulation.  */
+	.macro EXIT_SIMULATION_WITH_IMMEDIATE_EXIT_CODE immediate_value
+	LOAD_IMMEDIATE NOP_EXIT_R3, \immediate_value
+	l.nop 1
+	.endm
+
+	.macro EXIT_SIMULATION_WITH_REG_EXIT_CODE reg
+	MOVE_REG NOP_EXIT_R3, \reg
+	l.nop 1
+	.endm
+
+	/* When running under the simulator, this l.nop code prints the
+	   value of R3 to the console.  */
+	.macro REPORT_TO_CONSOLE
+	l.nop 2
+	.endm
+
+	/* NOTE: The stack must be set up, as this macro uses PUSH and POP.  */
+	.macro REPORT_REG_TO_CONSOLE reg
+	.ifeqs "\reg","r3"
+	 /* Nothing more to do here, R3 is the register that gets printed.  */
+	 REPORT_TO_CONSOLE
+	.else
+	 PUSH     NOP_REPORT_R3
+	 MOVE_REG NOP_REPORT_R3, \reg
+	 REPORT_TO_CONSOLE
+	 POP      NOP_REPORT_R3
+	.endif
+	.endm
+
+	/* NOTE: The stack must be set up, as this macro uses PUSH and POP.  */
+	.macro REPORT_IMMEDIATE_TO_CONSOLE val
+	PUSH     NOP_REPORT_R3
+	LOAD_IMMEDIATE NOP_REPORT_R3, \val
+	REPORT_TO_CONSOLE
+	POP      NOP_REPORT_R3
+	.endm
+
+	.macro PRINT_NEWLINE_TO_CONSOLE
+	PUSH  r3
+	LOAD_IMMEDIATE r3, 0x0A
+	l.nop 4
+	POP   r3
+	.endm
+
+	/* If SR[F] is set, writes 0x00000001 to the console, otherwise it
+	   writes 0x00000000.  */
+	.macro REPORT_SRF_TO_CONSOLE
+	OR1K_DELAYED_NOP (l.bnf \@1$)
+	REPORT_IMMEDIATE_TO_CONSOLE 0x00000001
+	OR1K_DELAYED_NOP (l.j \@2$)
+\@1$:
+	REPORT_IMMEDIATE_TO_CONSOLE 0x00000000
+\@2$:
+	.endm
+
+	/* If the given register is 0, writes 0x00000000 to the console,
+	   otherwise it writes 0x00000001.  */
+	.macro REPORT_BOOL_TO_CONSOLE  reg
+	l.sfne \reg, ZERO_R0
+	REPORT_SRF_TO_CONSOLE
+	.endm
+
+	/* Writes to the console the value of the given register bit.  */
+	.macro REPORT_BIT_TO_CONSOLE  reg, single_bit_mask
+	PUSH r2
+	PUSH r3
+	PUSH r4
+	MOVE_REG r2, \reg
+	LOAD_IMMEDIATE r4, \single_bit_mask
+	l.and   r3, r2, r4
+	REPORT_BOOL_TO_CONSOLE r3
+	POP r4
+	POP r3
+	POP r2
+	.endm
+
+	/* Jump helpers */
+
+	.macro CALL overwritten_reg, subroutine_name
+	LOAD_IMMEDIATE \overwritten_reg, \subroutine_name
+	OR1K_DELAYED_NOP (l.jalr  \overwritten_reg)
+	.endm
+
+	.macro RETURN_TO_LINK_REGISTER_R9
+	OR1K_DELAYED_NOP (l.jr LINK_REGISTER_R9)
+	.endm
+
+	/* Clear the BSS section on start-up */
+
+	.macro CLEAR_BSS overwritten_reg1, overwritten_reg2
+	LOAD_IMMEDIATE \overwritten_reg1, _bss_begin
+	LOAD_IMMEDIATE \overwritten_reg2, _bss_end
+	l.sfgeu \overwritten_reg1, \overwritten_reg2
+	OR1K_DELAYED_NOP (l.bf    bss_is_empty)
+bss_clear_loop:
+	/* Possible optimisation to investigate:
+	   move "l.sw 0(\overwritten_reg1), r0" to the jump delay slot as
+	   "l.sw -4(\overwritten_reg1), r0" or similar. But keep in mind that
+	   there are plans to remove the jump delay slot.  */
+	l.sw    0(\overwritten_reg1), r0
+	l.addi  \overwritten_reg1, \overwritten_reg1, 4
+	l.sfgtu \overwritten_reg2, \overwritten_reg1
+	OR1K_DELAYED_NOP (l.bf    bss_clear_loop)
+bss_is_empty:
+	.endm
+
+#endif /* OR1K_ASM_TEST_H */
diff --git a/sim/testsuite/sim/or1k/or1k-asm.h b/sim/testsuite/sim/or1k/or1k-asm.h
new file mode 100644
index 0000000000..a4f05d8439
--- /dev/null
+++ b/sim/testsuite/sim/or1k/or1k-asm.h
@@ -0,0 +1,37 @@
+/* Testsuite assembly helpers for OpenRISC.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+#ifndef OR1K_ASM_H
+#define OR1K_ASM_H
+
+#define OR1K_INST(...) __VA_ARGS__
+
+#if defined(__OR1K_NODELAY__)
+#define OR1K_DELAYED(a, b) a; b
+#define OR1K_DELAYED_NOP(a) a
+.nodelay
+#elif defined(__OR1K_DELAY__)
+#define OR1K_DELAYED(a, b) b; a
+#define OR1K_DELAYED_NOP(a) a; l.nop
+#elif defined(__OR1K_DELAY_COMPAT__)
+#define OR1K_DELAYED(a, b) a; b; l.nop
+#define OR1K_DELAYED_NOP(a) a; l.nop
+#else
+#error One of __OR1K_NODELAY__, __OR1K_DELAY__, or __OR1K_DELAY_COMPAT__ must be defined
+#endif
+
+#endif /* OR1K_ASM_H */
diff --git a/sim/testsuite/sim/or1k/or1k-test.ld b/sim/testsuite/sim/or1k/or1k-test.ld
new file mode 100644
index 0000000000..0631e9a926
--- /dev/null
+++ b/sim/testsuite/sim/or1k/or1k-test.ld
@@ -0,0 +1,75 @@
+/* Test linker script for OpenRISC.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+MEMORY
+{
+    /* The exception vectors actually start at 0x100, but if you specify
+       that address here, the "--output-target binary" step will start from
+       address 0 with the contents meant for address 0x100.  */
+    exception_vectors : ORIGIN =  0 , LENGTH = 8K
+    ram               : ORIGIN =  8K, LENGTH = 2M - 8K
+}
+
+SECTIONS
+{
+    .exception_vectors :
+    {
+	KEEP(*(.exception_vectors))
+    } > exception_vectors
+
+    .text :
+    {
+	*(.text)
+	*(.text.*)
+	*(.rodata)
+	*(.rodata.*)
+    } > ram
+
+    .data :
+    {
+	*(.data)
+	*(.data.*)
+    } > ram
+
+    .bss :
+    {
+	*(.bss)
+	*(.bss.*)
+
+	/* WARNING about section size alignment:
+	   The start-up assembly code can only clear BSS section sizes
+	   which are aligned to 4 bytes.  However, the size of the BSS
+	   section may not be aligned, therefore up to 3 bytes more could
+	   be zeroed on start-up.  This is normally not an issue, as the
+	   start of the next section is usually aligned too, so those extra
+	   bytes should be just padding.  I did try the following trick to
+	   align the BSS section size, to no avail:
+
+	   . = ALIGN(., 4);
+	*/
+    } > ram
+
+    _bss_begin = ADDR(.bss);
+    _bss_end   = _bss_begin + SIZEOF(.bss);
+
+    .stack ALIGN(16) (NOLOAD):
+    {
+      *(.stack)
+    } > ram
+}
+
+ENTRY(_start)  /* Otherwise, --gc-sections would throw everything away. */
diff --git a/sim/testsuite/sim/or1k/ror.S b/sim/testsuite/sim/or1k/ror.S
new file mode 100644
index 0000000000..b28aa0dd0d
--- /dev/null
+++ b/sim/testsuite/sim/or1k/ror.S
@@ -0,0 +1,159 @@
+/* Tests instructions l.ror and l.rori.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0x3b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0x0f83b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0x671e1f07);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00002224);\n
+# output: report(0x3b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00f789f0);\n
+# output: report(0x0f83b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0xffffffff);\n
+# output: report(0x671e1f07);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0x3b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0x0f83b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0x671e1f07);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000024);\n
+# output: report(0x3b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000030);\n
+# output: report(0x0f83b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000003f);\n
+# output: report(0x671e1f07);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-env.h"
+
+	.macro TEST_ROR op1, op2, res
+	/* Note that 'res' is not used here.  We could stop using the
+	   .TestResults file and use 'res' here instead.  */
+	LOAD_IMMEDIATE r5, \op1
+	LOAD_IMMEDIATE r6, \op2
+	REPORT_REG_TO_CONSOLE r5
+	REPORT_REG_TO_CONSOLE r6
+	l.ror r4, r5, r6
+	REPORT_REG_TO_CONSOLE r4
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	.macro TEST_RORI op1, op2, res
+	/* Note that 'res' is not used here.  We could stop using the
+	   .TestResults file and use 'res' here instead.  */
+	LOAD_IMMEDIATE r5, \op1
+	REPORT_REG_TO_CONSOLE r5
+	REPORT_IMMEDIATE_TO_CONSOLE \op2
+	l.rori r4, r5, \op2
+	REPORT_REG_TO_CONSOLE r4
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test the l.ror instruction.  */
+
+	/* Rotate by zero  */
+	TEST_ROR 0xb38f0f83, 0x00000000, 0xb38f0f83
+
+	/* Rotate by amounts in the 1 - 31 range.  */
+	TEST_ROR 0xb38f0f83, 0x00000001, 0xd9c787c1
+	TEST_ROR 0xb38f0f83, 0x00000004, 0x3b38f0f8
+	TEST_ROR 0xb38f0f83, 0x00000010, 0x0f83b38f
+	TEST_ROR 0xb38f0f83, 0x0000001f, 0x671e1f07
+
+	/* Rotate by larger amounts - should be masked.  */
+	TEST_ROR 0xb38f0f83, 0x00000021, 0xd9c787c1
+	TEST_ROR 0xb38f0f83, 0x00002224, 0x3b38f0f8
+	TEST_ROR 0xb38f0f83, 0x00f789f0, 0x0f83b38f
+	TEST_ROR 0xb38f0f83, 0xffffffff, 0x671e1f07
+
+	/* Test the l.rori instruction.  */
+
+	/* Rotate by zero */
+	TEST_RORI 0xb38f0f83, 0x00000000, 0xb38f0f83
+
+	/* Rotate by amounts in the 1 - 31 range.  */
+	TEST_RORI 0xb38f0f83, 0x01, 0xd9c787c1
+	TEST_RORI 0xb38f0f83, 0x04, 0x3b38f0f8
+	TEST_RORI 0xb38f0f83, 0x10, 0x0f83b38f
+	TEST_RORI 0xb38f0f83, 0x1f, 0x671e1f07
+
+	/* Rotate by larger amounts (32 - 63) - should be masked.  */
+	TEST_RORI 0xb38f0f83, 0x21, 0xd9c787c1
+	TEST_RORI 0xb38f0f83, 0x24, 0x3b38f0f8
+	TEST_RORI 0xb38f0f83, 0x30, 0x0f83b38f
+	TEST_RORI 0xb38f0f83, 0x3f, 0x671e1f07
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/shift.S b/sim/testsuite/sim/or1k/shift.S
new file mode 100644
index 0000000000..5fc9b9cf94
--- /dev/null
+++ b/sim/testsuite/sim/or1k/shift.S
@@ -0,0 +1,541 @@
+/* Tests the shift instructions.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0x671e1f06);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0x38f0f830);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0x0f830000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0x80000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0x671e1f06);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00002224);\n
+# output: report(0x38f0f830);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00f789f0);\n
+# output: report(0x0f830000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0xffffffff);\n
+# output: report(0x80000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0x671e1f06);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0x38f0f830);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0x0f830000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0x80000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0x671e1f06);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000024);\n
+# output: report(0x38f0f830);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000030);\n
+# output: report(0x0f830000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000003f);\n
+# output: report(0x80000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0xfb38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0xffffb38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0xffffffff);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000001);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000004);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000010);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x0000001f);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00002224);\n
+# output: report(0xfb38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00f789f0);\n
+# output: report(0xffffb38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000021);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00002224);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00f789f0);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0xfb38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0xffffb38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0xffffffff);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000001);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000004);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000010);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x0000001f);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0xd9c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000024);\n
+# output: report(0xfb38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000030);\n
+# output: report(0xffffb38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000003f);\n
+# output: report(0xffffffff);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000021);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000024);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000030);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x0000003f);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0x59c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0x0b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0x0000b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000001);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000004);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000010);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x0000001f);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0x59c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00002224);\n
+# output: report(0x0b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00f789f0);\n
+# output: report(0x0000b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000021);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00002224);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00f789f0);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000000);\n
+# output: report(0xb38f0f83);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000001);\n
+# output: report(0x59c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000004);\n
+# output: report(0x0b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000010);\n
+# output: report(0x0000b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000001f);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000001);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000004);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000010);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x0000001f);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000021);\n
+# output: report(0x59c787c1);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000024);\n
+# output: report(0x0b38f0f8);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x00000030);\n
+# output: report(0x0000b38f);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000003f);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000021);\n
+# output: report(0x2638783e);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000024);\n
+# output: report(0x04c70f07);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000030);\n
+# output: report(0x00004c70);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x0000003f);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	.macro TEST_SHIFT opcode, op1, op2
+	LOAD_IMMEDIATE r5, \op1
+	LOAD_IMMEDIATE r6, \op2
+	REPORT_REG_TO_CONSOLE r5
+	REPORT_REG_TO_CONSOLE r6
+	\opcode r4, r5, r6
+	CHECK_CARRY_AND_OVERFLOW_NOT_SET r2, r3
+	REPORT_REG_TO_CONSOLE r4
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	.macro TEST_SHIFT_I opcode, op1, op2
+	LOAD_IMMEDIATE r5, \op1
+	REPORT_REG_TO_CONSOLE r5
+	REPORT_IMMEDIATE_TO_CONSOLE \op2
+	\opcode r4, r5, \op2
+	CHECK_CARRY_AND_OVERFLOW_NOT_SET r2, r3
+	REPORT_REG_TO_CONSOLE r4
+	PRINT_NEWLINE_TO_CONSOLE
+	.endm
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Always set OVE.  We should never trigger an exception, even if
+	   this bit is set.  */
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test l.sll  */
+
+	/* Shift left by zero.  */
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x00000000
+
+	/* Shift left by amounts in the 1-31 range.  */
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x00000001
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x00000004
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x00000010
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x0000001f
+
+	/* Shift left by larger amounts - should be masked.  */
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x00000021
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x00002224
+	TEST_SHIFT l.sll, 0xb38f0f83, 0x00f789f0
+	TEST_SHIFT l.sll, 0xb38f0f83, 0xffffffff
+
+	/* Test l.slli  */
+
+	/* Shift left by zero.  */
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x0000
+
+	/* Shift left by amounts in the 1-31 range.  */
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x0001
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x0004
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x0010
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x001f
+
+	/* Shift left by larger amounts - should be masked.  */
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x0021
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x0024
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x0030
+	TEST_SHIFT_I l.slli, 0xb38f0f83, 0x003f
+
+	/* Test l.sra  */
+
+	/* Shift right by zero.  */
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x00000000
+
+	/* Shift right by amounts in the 1-31 range.  */
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x00000001
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x00000004
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x00000010
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x0000001f
+
+	TEST_SHIFT l.sra, 0x4c70f07c, 0x00000001
+	TEST_SHIFT l.sra, 0x4c70f07c, 0x00000004
+	TEST_SHIFT l.sra, 0x4c70f07c, 0x00000010
+	TEST_SHIFT l.sra, 0x4c70f07c, 0x0000001f
+
+	/* Shift right by larger amounts - should be masked.  */
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x00000021
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x00002224
+	TEST_SHIFT l.sra, 0xb38f0f83, 0x00f789f0
+	TEST_SHIFT l.sra, 0xb38f0f83, 0xffffffff
+
+	TEST_SHIFT l.sra, 0x4c70f07c, 0x00000021
+	TEST_SHIFT l.sra, 0x4c70f07c, 0x00002224
+	TEST_SHIFT l.sra, 0x4c70f07c, 0x00f789f0
+	TEST_SHIFT l.sra, 0x4c70f07c, 0xffffffff
+
+	/* Test l.srai  */
+
+	/* Shift right by zero.  */
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x0000
+
+	/* Shift right by amounts in the 1-31 range.  */
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x0001
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x0004
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x0010
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x001f
+
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x0001
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x0004
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x0010
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x001f
+
+	/* Shift right by larger amounts - should be masked.  */
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x0021
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x0024
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x0030
+	TEST_SHIFT_I l.srai, 0xb38f0f83, 0x003f
+
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x0021
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x0024
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x0030
+	TEST_SHIFT_I l.srai, 0x4c70f07c, 0x003f
+
+	/* Test l.srl  */
+
+	/* Shift right by zero.  */
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x00000000
+
+	/* Shift right by amounts in the 1-31 range.  */
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x00000001
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x00000004
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x00000010
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x0000001f
+
+	TEST_SHIFT l.srl, 0x4c70f07c, 0x00000001
+	TEST_SHIFT l.srl, 0x4c70f07c, 0x00000004
+	TEST_SHIFT l.srl, 0x4c70f07c, 0x00000010
+	TEST_SHIFT l.srl, 0x4c70f07c, 0x0000001f
+
+	/* Shift right by larger amounts - should be masked.  */
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x00000021
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x00002224
+	TEST_SHIFT l.srl, 0xb38f0f83, 0x00f789f0
+	TEST_SHIFT l.srl, 0xb38f0f83, 0xffffffff
+
+	TEST_SHIFT l.srl, 0x4c70f07c, 0x00000021
+	TEST_SHIFT l.srl, 0x4c70f07c, 0x00002224
+	TEST_SHIFT l.srl, 0x4c70f07c, 0x00f789f0
+	TEST_SHIFT l.srl, 0x4c70f07c, 0xffffffff
+
+	/* Test l.srli  */
+
+	/* Shift right by zero.  */
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x0000
+
+	/* Shift right by amounts in the 1-31 range.  */
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x0001
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x0004
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x0010
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x001f
+
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x0001
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x0004
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x0010
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x001f
+
+	/* Shift right by larger amounts - should be masked.  */
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x0021
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x0024
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x0030
+	TEST_SHIFT_I l.srli, 0xb38f0f83, 0x003f
+
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x0021
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x0024
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x0030
+	TEST_SHIFT_I l.srli, 0x4c70f07c, 0x003f
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/spr-defs.h b/sim/testsuite/sim/or1k/spr-defs.h
new file mode 100644
index 0000000000..71c927bd07
--- /dev/null
+++ b/sim/testsuite/sim/or1k/spr-defs.h
@@ -0,0 +1,120 @@
+/* Special Purpose Registers definitions
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+#ifndef SPR_DEFS_H
+#define SPR_DEFS_H
+
+#define MAX_GRPS 32
+#define MAX_SPRS_PER_GRP_BITS 11
+
+/* Base addresses for the groups */
+#define SPRGROUP_SYS   (0<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_DMMU  (1<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_IMMU  (2<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_DC    (3<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_IC    (4<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_MAC   (5<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_D     (6<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_PC    (7<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_PM    (8<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_PIC   (9<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_TT    (10<< MAX_SPRS_PER_GRP_BITS)
+#define SPRGROUP_FP    (11<< MAX_SPRS_PER_GRP_BITS)
+
+/* System control and status group */
+#define SPR_VR          (SPRGROUP_SYS + 0)
+#define SPR_UPR         (SPRGROUP_SYS + 1)
+#define SPR_CPUCFGR     (SPRGROUP_SYS + 2)
+#define SPR_DMMUCFGR    (SPRGROUP_SYS + 3)
+#define SPR_IMMUCFGR    (SPRGROUP_SYS + 4)
+#define SPR_DCCFGR      (SPRGROUP_SYS + 5)
+#define SPR_ICCFGR      (SPRGROUP_SYS + 6)
+#define SPR_DCFGR       (SPRGROUP_SYS + 7)
+#define SPR_PCCFGR      (SPRGROUP_SYS + 8)
+#define SPR_NPC         (SPRGROUP_SYS + 16)
+#define SPR_SR          (SPRGROUP_SYS + 17)
+#define SPR_PPC         (SPRGROUP_SYS + 18)
+#define SPR_FPCSR       (SPRGROUP_SYS + 20)
+#define SPR_EPCR_BASE   (SPRGROUP_SYS + 32)
+#define SPR_EPCR_LAST   (SPRGROUP_SYS + 47)
+#define SPR_EEAR_BASE   (SPRGROUP_SYS + 48)
+#define SPR_EEAR_LAST   (SPRGROUP_SYS + 63)
+#define SPR_ESR_BASE    (SPRGROUP_SYS + 64)
+#define SPR_ESR_LAST    (SPRGROUP_SYS + 79)
+#define SPR_GPR_BASE    (SPRGROUP_SYS + 1024)
+
+/* Data MMU group */
+#define SPR_DMMUCR  (SPRGROUP_DMMU + 0)
+#define SPR_DMMUPR  (SPRGROUP_DMMU + 1)
+#define SPR_DTLBEIR     (SPRGROUP_DMMU + 2)
+#define SPR_DTLBMR_BASE(WAY)    (SPRGROUP_DMMU + 0x200 + (WAY) * 0x100)
+#define SPR_DTLBMR_LAST(WAY)    (SPRGROUP_DMMU + 0x27f + (WAY) * 0x100)
+#define SPR_DTLBTR_BASE(WAY)    (SPRGROUP_DMMU + 0x280 + (WAY) * 0x100)
+#define SPR_DTLBTR_LAST(WAY)    (SPRGROUP_DMMU + 0x2ff + (WAY) * 0x100)
+
+/* Instruction MMU group */
+#define SPR_IMMUCR  (SPRGROUP_IMMU + 0)
+#define SPR_ITLBEIR     (SPRGROUP_IMMU + 2)
+#define SPR_ITLBMR_BASE(WAY)    (SPRGROUP_IMMU + 0x200 + (WAY) * 0x100)
+#define SPR_ITLBMR_LAST(WAY)    (SPRGROUP_IMMU + 0x27f + (WAY) * 0x100)
+#define SPR_ITLBTR_BASE(WAY)    (SPRGROUP_IMMU + 0x280 + (WAY) * 0x100)
+#define SPR_ITLBTR_LAST(WAY)    (SPRGROUP_IMMU + 0x2ff + (WAY) * 0x100)
+
+/* Data cache group */
+#define SPR_DCCR    (SPRGROUP_DC + 0)
+#define SPR_DCBPR   (SPRGROUP_DC + 1)
+#define SPR_DCBFR   (SPRGROUP_DC + 2)
+#define SPR_DCBIR   (SPRGROUP_DC + 3)
+#define SPR_DCBWR   (SPRGROUP_DC + 4)
+#define SPR_DCBLR   (SPRGROUP_DC + 5)
+#define SPR_DCR_BASE(WAY)   (SPRGROUP_DC + 0x200 + (WAY) * 0x200)
+#define SPR_DCR_LAST(WAY)   (SPRGROUP_DC + 0x3ff + (WAY) * 0x200)
+
+/* Instruction cache group */
+#define SPR_ICCR    (SPRGROUP_IC + 0)
+#define SPR_ICBPR   (SPRGROUP_IC + 1)
+#define SPR_ICBIR   (SPRGROUP_IC + 2)
+#define SPR_ICBLR   (SPRGROUP_IC + 3)
+#define SPR_ICR_BASE(WAY)   (SPRGROUP_IC + 0x200 + (WAY) * 0x200)
+#define SPR_ICR_LAST(WAY)   (SPRGROUP_IC + 0x3ff + (WAY) * 0x200)
+
+/* MAC group */
+#define SPR_MACLO   (SPRGROUP_MAC + 1)
+#define SPR_MACHI   (SPRGROUP_MAC + 2)
+
+/* Bit definitions for the Supervision Register.  */
+#define SPR_SR_SM          0x00000001 /* Supervisor Mode */
+#define SPR_SR_TEE         0x00000002 /* Tick timer Exception Enable */
+#define SPR_SR_IEE         0x00000004 /* Interrupt Exception Enable */
+#define SPR_SR_DCE         0x00000008 /* Data Cache Enable */
+#define SPR_SR_ICE         0x00000010 /* Instruction Cache Enable */
+#define SPR_SR_DME         0x00000020 /* Data MMU Enable */
+#define SPR_SR_IME         0x00000040 /* Instruction MMU Enable */
+#define SPR_SR_LEE         0x00000080 /* Little Endian Enable */
+#define SPR_SR_CE          0x00000100 /* CID Enable */
+#define SPR_SR_F           0x00000200 /* Condition Flag */
+#define SPR_SR_CY          0x00000400 /* Carry flag */
+#define SPR_SR_OV          0x00000800 /* Overflow flag */
+#define SPR_SR_OVE         0x00001000 /* Overflow flag Exception */
+#define SPR_SR_DSX         0x00002000 /* Delay Slot Exception */
+#define SPR_SR_EPH         0x00004000 /* Exception Prefix High */
+#define SPR_SR_FO          0x00008000 /* Fixed one */
+#define SPR_SR_SUMRA       0x00010000 /* Supervisor SPR read access */
+#define SPR_SR_RES         0x0ffe0000 /* Reserved */
+#define SPR_SR_CID         0xf0000000 /* Context ID */
+
+#endif /* SPR_DEFS_H */
diff --git a/sim/testsuite/sim/or1k/sub.S b/sim/testsuite/sim/or1k/sub.S
new file mode 100644
index 0000000000..f8557cafda
--- /dev/null
+++ b/sim/testsuite/sim/or1k/sub.S
@@ -0,0 +1,215 @@
+/* Tests instruction l.sub.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000003);\n
+# output: report(0x00000002);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000001);\n
+# output: report(0x00000002);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000003);\n
+# output: report(0x00000002);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xfffffffd);\n
+# output: report(0xfffffffe);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xfffffffe);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fffffff);\n
+# output: report(0x3fffffff);\n
+# output: report(0x40000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x40000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x3fffffff);\n
+# output: report(0x40000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x40000000);\n
+# output: report(0x3fffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x80000000);\n
+# output: report(0x7fffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: report(0x3fffffff);\n
+# output: report(0x40000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x7fffffff);\n
+# output: report(0x80000000);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: report(0x00000001);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .exception_vectors
+
+	/* Range exception.  */
+	.org	0xb00
+
+	/* The handling is a bit dubious at present.  We just patch the
+	   instruction with l.nop and restart.  This will go wrong in branch
+	   delay slots.  But we don't have those in this test.  */
+	l.addi r1, r1, -EXCEPTION_STACK_SKIP_SIZE
+	PUSH r2
+	PUSH r3
+	/* Save the address of the instruction that caused the problem.  */
+	MOVE_FROM_SPR r2, SPR_EPCR_BASE
+	LOAD_IMMEDIATE r3, 0x15000000 /* Opcode for l.nop  */
+	l.sw	0(r2), r3
+	POP r3
+	POP r2
+	l.addi r1, r1, EXCEPTION_STACK_SKIP_SIZE
+	l.rfe
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Test l.sub */
+
+	/* Subtract two small positive numbers.  Sets the carry, but never
+	   the overflow if the result is negative.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x00000003, \
+	  0x00000002
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x00000001, \
+	  0x00000002
+
+	/* Check carry in is ignored.  */
+	TEST_INST_FF_I32_I32 SPR_SR_CY, SPR_SR_OV, l.sub, 0x00000003, 0x00000002
+
+	/* Subtract two small negative numbers.  Sets the carry flag if
+	   the result is negative, but never the overflow flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0xfffffffd, \
+	  0xfffffffe
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0xffffffff, \
+	  0xfffffffe
+
+	/* Subtract two quite large positive numbers.  Should set neither
+	   the overflow nor the carry flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x7fffffff, \
+	  0x3fffffff
+
+	/* Subtract two quite large negative numbers.  Should set neither
+	   the overflow nor the carry flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x40000000, \
+	  0x40000000
+
+	/* Subtract two large positive numbers with a negative result.
+	   Should set the carry, but not the overflow flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x3fffffff, \
+	  0x40000000
+
+	/* Subtract two large negative numbers with a positive result.
+	   Should set neither the carry nor the overflow flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x40000000, \
+	  0x3fffffff
+
+	/* Subtract a large positive from a large negative number.  Should
+	   set overflow but not the carry flag.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x80000000, \
+	  0x7fffffff
+
+	/* Subtract a large negative from a large positive number.  Should
+	   set both the overflow and carry flags.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x7fffffff, \
+	  0x80000000
+
+	/* Check that range exceptions are triggered.  */
+
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Check that an overflow alone causes a RANGE Exception.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x80000000, \
+	  0x7fffffff
+
+	/* Check that a carry alone does not cause a RANGE Exception.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x3fffffff, \
+	  0x40000000
+
+	/* Check that carry and overflow together cause an exception.  */
+	TEST_INST_FF_I32_I32 0, SPR_SR_CY | SPR_SR_OV, l.sub, 0x7fffffff, \
+	  0x80000000
+
+	CLEAR_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
diff --git a/sim/testsuite/sim/or1k/xor.S b/sim/testsuite/sim/or1k/xor.S
new file mode 100644
index 0000000000..1fa94498e0
--- /dev/null
+++ b/sim/testsuite/sim/or1k/xor.S
@@ -0,0 +1,200 @@
+/* Tests instructions l.xor, l.xori.
+
+   Copyright (C) 2017 Free Software Foundation, Inc.
+
+   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 3 of the License, 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 <http://www.gnu.org/licenses/>.  */
+
+# mach: or1k
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x55555555);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xb38f0f83);\n
+# output: report(0xffffffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0xc4c70f07);\n
+# output: report(0x88b7ff7b);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x38f0f83b);\n
+# output: report(0x8b7ff7b8);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xffffffff);\n
+# output: report(0x0000ffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x0000aaaa);\n
+# output: report(0x55550000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x55555555);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x55555555);\n
+# output: report(0x00005555);\n
+# output: report(0x55550000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xaaaaaaaa);\n
+# output: report(0x00005555);\n
+# output: report(0xaaaaffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000f83);\n
+# output: report(0x4c70ffff);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0x4c70f07c);\n
+# output: report(0x00000f07);\n
+# output: report(0x4c70ff7b);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: report(0xb38f0f83);\n
+# output: report(0x0000f83b);\n
+# output: report(0x4c70f7b8);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: report(0x00000000);\n
+# output: \n
+# output: exit(0)\n
+
+#include "or1k-asm-test-helpers.h"
+
+	STANDARD_TEST_ENVIRONMENT
+
+	.section .text
+start_tests:
+	PUSH LINK_REGISTER_R9
+
+	/* Always set OVE.  We should never trigger an exception, even if
+	   this bit is set.  */
+	SET_SPR_SR_FLAGS SPR_SR_OVE, r2, r3
+
+	/* Test the l.xor instruction with a range of operands.  */
+
+	TEST_INST_I32_I32 l.xor, 0x00000000, 0x00000000
+	TEST_INST_I32_I32 l.xor, 0xffffffff, 0xffffffff
+	TEST_INST_I32_I32 l.xor, 0xaaaaaaaa, 0x00000000
+	TEST_INST_I32_I32 l.xor, 0xaaaaaaaa, 0xaaaaaaaa
+	TEST_INST_I32_I32 l.xor, 0x55555555, 0x00000000
+	TEST_INST_I32_I32 l.xor, 0x55555555, 0x55555555
+	TEST_INST_I32_I32 l.xor, 0xaaaaaaaa, 0x55555555
+	TEST_INST_I32_I32 l.xor, 0x4c70f07c, 0xb38f0f83
+	TEST_INST_I32_I32 l.xor, 0x4c70f07c, 0xc4c70f07
+	TEST_INST_I32_I32 l.xor, 0xb38f0f83, 0x38f0f83b
+
+	/* Test the l.xori instruction with a range of operands.  */
+
+	TEST_INST_I32_I16 l.xori, 0x00000000, 0x0000
+	TEST_INST_I32_I16 l.xori, 0xffffffff, 0xffff
+	TEST_INST_I32_I16 l.xori, 0xaaaaaaaa, 0x0000
+	TEST_INST_I32_I16 l.xori, 0xaaaaaaaa, 0xaaaa
+	TEST_INST_I32_I16 l.xori, 0x55555555, 0x0000
+	TEST_INST_I32_I16 l.xori, 0x55555555, 0x5555
+	TEST_INST_I32_I16 l.xori, 0xaaaaaaaa, 0x5555
+	TEST_INST_I32_I16 l.xori, 0x4c70f07c, 0x0f83
+	TEST_INST_I32_I16 l.xori, 0x4c70f07c, 0x0f07
+	TEST_INST_I32_I16 l.xori, 0xb38f0f83, 0xf83b
+
+	POP LINK_REGISTER_R9
+	RETURN_TO_LINK_REGISTER_R9
