blob: 1c369a5836bad1a1d851098c7b7ce52ebf2b7aeb [file] [log] [blame]
/*
* Copyright (c) 2013 The Native Client Authors. All rights reserved.
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#include <assert.h>
#include <setjmp.h>
#include <stdlib.h>
#include "gtest/gtest.h"
// TODO: port asm to aarch64 and x86_64 instructions
static volatile double should_be_two = 2.0;
namespace {
class LongJmpFloatTests : public ::testing::Test {
protected:
LongJmpFloatTests() {
// You can do set-up work for each test here.
}
~LongJmpFloatTests() override {}
void SetUp() override {}
void TearDown() override {}
};
} // namespace
TEST_F(LongJmpFloatTests, TestLongJmpFloat) {
jmp_buf buf;
/* LLVM assembler doesn't parse vfpv3, but we've set the default */
#if !defined(__llvm__)
__asm__(".fpu vfpv3");
#endif
ASSERT_EQ(should_be_two, 2.0);
/* Copy |should_be_two| into regs. */
__asm__("vmov.f64 d8, %P[value]\n\t"
"vmov.f64 d9, %P[value]\n\t"
"vmov.f64 d10, %P[value]\n\t"
"vmov.f64 d11, %P[value]\n\t"
"vmov.f64 d12, %P[value]\n\t"
"vmov.f64 d13, %P[value]\n\t"
"vmov.f64 d14, %P[value]\n\t"
"vmov.f64 d15, %P[value]"
:
: [value] "w"(should_be_two)
: "d8", "d9", "d10", "d11", "d12", "d13", "d14", "d15");
if (!setjmp(buf)) {
/* Clobber the regs */
__asm__("vmov.f64 d8, #1.0\n\t"
"vmov.f64 d9, #1.0\n\t"
"vmov.f64 d10, #1.0\n\t"
"vmov.f64 d11, #1.0\n\t"
"vmov.f64 d12, #1.0\n\t"
"vmov.f64 d13, #1.0\n\t"
"vmov.f64 d14, #1.0\n\t"
"vmov.f64 d15, #1.0"
:
:
: "d8", "d9", "d10", "d11", "d12", "d13", "d14", "d15");
longjmp(buf, 1);
ASSERT_TRUE(false) << "this statement should not be reached";
} else {
double restored_val;
__asm__("vmov.f64 %P0, d8\n\t" : "=w"(restored_val) :);
assert(restored_val == 2.0);
__asm__("vmov.f64 %P0, d9\n\t" : "=w"(restored_val) :);
assert(restored_val == 2.0);
__asm__("vmov.f64 %P0, d10\n\t" : "=w"(restored_val) :);
assert(restored_val == 2.0);
__asm__("vmov.f64 %P0, d11\n\t" : "=w"(restored_val) :);
assert(restored_val == 2.0);
__asm__("vmov.f64 %P0, d12\n\t" : "=w"(restored_val) :);
assert(restored_val == 2.0);
__asm__("vmov.f64 %P0, d13\n\t" : "=w"(restored_val) :);
assert(restored_val == 2.0);
__asm__("vmov.f64 %P0, d14\n\t" : "=w"(restored_val) :);
assert(restored_val == 2.0);
__asm__("vmov.f64 %P0, d15\n\t" : "=w"(restored_val) :);
ASSERT_EQ(restored_val, 2.0);
}
}