mirror of
https://github.com/corda/corda.git
synced 2025-01-09 06:23:04 +00:00
begin splitting out arm assembler
This commit is contained in:
parent
d1a149a0a1
commit
fd59e1e08d
@ -8,13 +8,17 @@
|
|||||||
There is NO WARRANTY for this software. See license.txt for
|
There is NO WARRANTY for this software. See license.txt for
|
||||||
details. */
|
details. */
|
||||||
|
|
||||||
|
#include <avian/util/runtime-array.h>
|
||||||
|
|
||||||
#include <avian/vm/codegen/assembler.h>
|
#include <avian/vm/codegen/assembler.h>
|
||||||
#include <avian/vm/codegen/registers.h>
|
#include <avian/vm/codegen/registers.h>
|
||||||
|
|
||||||
|
#include "context.h"
|
||||||
|
#include "block.h"
|
||||||
|
|
||||||
#include "alloc-vector.h"
|
#include "alloc-vector.h"
|
||||||
#include <avian/util/abort.h>
|
#include <avian/util/abort.h>
|
||||||
|
|
||||||
#include <avian/util/runtime-array.h>
|
|
||||||
|
|
||||||
#define CAST1(x) reinterpret_cast<UnaryOperationType>(x)
|
#define CAST1(x) reinterpret_cast<UnaryOperationType>(x)
|
||||||
#define CAST2(x) reinterpret_cast<BinaryOperationType>(x)
|
#define CAST2(x) reinterpret_cast<BinaryOperationType>(x)
|
||||||
@ -25,7 +29,8 @@ using namespace vm;
|
|||||||
using namespace avian::codegen;
|
using namespace avian::codegen;
|
||||||
using namespace avian::util;
|
using namespace avian::util;
|
||||||
|
|
||||||
namespace local {
|
namespace avian {
|
||||||
|
namespace codegen {
|
||||||
|
|
||||||
namespace isa {
|
namespace isa {
|
||||||
// SYSTEM REGISTERS
|
// SYSTEM REGISTERS
|
||||||
@ -196,6 +201,8 @@ bool vfpSupported() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
namespace arm {
|
||||||
|
|
||||||
const uint64_t MASK_LO32 = 0xffffffff;
|
const uint64_t MASK_LO32 = 0xffffffff;
|
||||||
const unsigned MASK_LO16 = 0xffff;
|
const unsigned MASK_LO16 = 0xffff;
|
||||||
const unsigned MASK_LO8 = 0xff;
|
const unsigned MASK_LO8 = 0xff;
|
||||||
@ -239,8 +246,6 @@ const int32_t PoolOffsetMask = 0xFFF;
|
|||||||
|
|
||||||
const bool DebugPool = false;
|
const bool DebugPool = false;
|
||||||
|
|
||||||
class Context;
|
|
||||||
class MyBlock;
|
|
||||||
class PoolOffset;
|
class PoolOffset;
|
||||||
class PoolEvent;
|
class PoolEvent;
|
||||||
|
|
||||||
@ -250,113 +255,12 @@ resolve(MyBlock*);
|
|||||||
unsigned
|
unsigned
|
||||||
padding(MyBlock*, unsigned);
|
padding(MyBlock*, unsigned);
|
||||||
|
|
||||||
class MyBlock: public Assembler::Block {
|
|
||||||
public:
|
|
||||||
MyBlock(Context* context, unsigned offset):
|
|
||||||
context(context), next(0), poolOffsetHead(0), poolOffsetTail(0),
|
|
||||||
lastPoolOffsetTail(0), poolEventHead(0), poolEventTail(0),
|
|
||||||
lastEventOffset(0), offset(offset), start(~0), size(0)
|
|
||||||
{ }
|
|
||||||
|
|
||||||
virtual unsigned resolve(unsigned start, Assembler::Block* next) {
|
|
||||||
this->start = start;
|
|
||||||
this->next = static_cast<MyBlock*>(next);
|
|
||||||
|
|
||||||
local::resolve(this);
|
|
||||||
|
|
||||||
return start + size + padding(this, size);
|
|
||||||
}
|
|
||||||
|
|
||||||
Context* context;
|
|
||||||
MyBlock* next;
|
|
||||||
PoolOffset* poolOffsetHead;
|
|
||||||
PoolOffset* poolOffsetTail;
|
|
||||||
PoolOffset* lastPoolOffsetTail;
|
|
||||||
PoolEvent* poolEventHead;
|
|
||||||
PoolEvent* poolEventTail;
|
|
||||||
unsigned lastEventOffset;
|
|
||||||
unsigned offset;
|
|
||||||
unsigned start;
|
|
||||||
unsigned size;
|
|
||||||
};
|
|
||||||
|
|
||||||
class Task;
|
class Task;
|
||||||
class ConstantPoolEntry;
|
class ConstantPoolEntry;
|
||||||
|
|
||||||
class Context {
|
class OffsetPromise: public Promise {
|
||||||
public:
|
public:
|
||||||
Context(System* s, Allocator* a, Zone* zone):
|
OffsetPromise(Context* con, MyBlock* block, unsigned offset, bool forTrace):
|
||||||
s(s), zone(zone), client(0), code(s, a, 1024), tasks(0), result(0),
|
|
||||||
firstBlock(new(zone) MyBlock(this, 0)),
|
|
||||||
lastBlock(firstBlock), poolOffsetHead(0), poolOffsetTail(0),
|
|
||||||
constantPool(0), constantPoolCount(0)
|
|
||||||
{ }
|
|
||||||
|
|
||||||
System* s;
|
|
||||||
Zone* zone;
|
|
||||||
Assembler::Client* client;
|
|
||||||
Vector code;
|
|
||||||
Task* tasks;
|
|
||||||
uint8_t* result;
|
|
||||||
MyBlock* firstBlock;
|
|
||||||
MyBlock* lastBlock;
|
|
||||||
PoolOffset* poolOffsetHead;
|
|
||||||
PoolOffset* poolOffsetTail;
|
|
||||||
ConstantPoolEntry* constantPool;
|
|
||||||
unsigned constantPoolCount;
|
|
||||||
};
|
|
||||||
|
|
||||||
class Task {
|
|
||||||
public:
|
|
||||||
Task(Task* next): next(next) { }
|
|
||||||
|
|
||||||
virtual void run(Context* con) = 0;
|
|
||||||
|
|
||||||
Task* next;
|
|
||||||
};
|
|
||||||
|
|
||||||
typedef void (*OperationType)(Context*);
|
|
||||||
|
|
||||||
typedef void (*UnaryOperationType)(Context*, unsigned, lir::Operand*);
|
|
||||||
|
|
||||||
typedef void (*BinaryOperationType)
|
|
||||||
(Context*, unsigned, lir::Operand*, unsigned, lir::Operand*);
|
|
||||||
|
|
||||||
typedef void (*TernaryOperationType)
|
|
||||||
(Context*, unsigned, lir::Operand*, lir::Operand*,
|
|
||||||
lir::Operand*);
|
|
||||||
|
|
||||||
typedef void (*BranchOperationType)
|
|
||||||
(Context*, lir::TernaryOperation, unsigned, lir::Operand*,
|
|
||||||
lir::Operand*, lir::Operand*);
|
|
||||||
|
|
||||||
class ArchitectureContext {
|
|
||||||
public:
|
|
||||||
ArchitectureContext(System* s): s(s) { }
|
|
||||||
|
|
||||||
System* s;
|
|
||||||
OperationType operations[lir::OperationCount];
|
|
||||||
UnaryOperationType unaryOperations[lir::UnaryOperationCount
|
|
||||||
* lir::OperandTypeCount];
|
|
||||||
BinaryOperationType binaryOperations
|
|
||||||
[lir::BinaryOperationCount * lir::OperandTypeCount * lir::OperandTypeCount];
|
|
||||||
TernaryOperationType ternaryOperations
|
|
||||||
[lir::NonBranchTernaryOperationCount * lir::OperandTypeCount];
|
|
||||||
BranchOperationType branchOperations
|
|
||||||
[lir::BranchOperationCount * lir::OperandTypeCount * lir::OperandTypeCount];
|
|
||||||
};
|
|
||||||
|
|
||||||
inline Aborter* getAborter(Context* con) {
|
|
||||||
return con->s;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline Aborter* getAborter(ArchitectureContext* con) {
|
|
||||||
return con->s;
|
|
||||||
}
|
|
||||||
|
|
||||||
class Offset: public Promise {
|
|
||||||
public:
|
|
||||||
Offset(Context* con, MyBlock* block, unsigned offset, bool forTrace):
|
|
||||||
con(con), block(block), offset(offset), forTrace(forTrace)
|
con(con), block(block), offset(offset), forTrace(forTrace)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
@ -378,10 +282,8 @@ class Offset: public Promise {
|
|||||||
bool forTrace;
|
bool forTrace;
|
||||||
};
|
};
|
||||||
|
|
||||||
Promise*
|
Promise* offsetPromise(Context* con, bool forTrace = false) {
|
||||||
offset(Context* con, bool forTrace = false)
|
return new(con->zone) OffsetPromise(con, con->lastBlock, con->code.length(), forTrace);
|
||||||
{
|
|
||||||
return new(con->zone) Offset(con, con->lastBlock, con->code.length(), forTrace);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
@ -1626,7 +1528,7 @@ branch(Context* con, lir::TernaryOperation op)
|
|||||||
void
|
void
|
||||||
conditional(Context* con, int32_t branch, lir::Constant* target)
|
conditional(Context* con, int32_t branch, lir::Constant* target)
|
||||||
{
|
{
|
||||||
appendOffsetTask(con, target->value, offset(con));
|
appendOffsetTask(con, target->value, offsetPromise(con));
|
||||||
emit(con, branch);
|
emit(con, branch);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1845,7 +1747,7 @@ callC(Context* con, unsigned size UNUSED, lir::Constant* target)
|
|||||||
{
|
{
|
||||||
assert(con, size == TargetBytesPerWord);
|
assert(con, size == TargetBytesPerWord);
|
||||||
|
|
||||||
appendOffsetTask(con, target->value, offset(con));
|
appendOffsetTask(con, target->value, offsetPromise(con));
|
||||||
emit(con, bl(0));
|
emit(con, bl(0));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1855,7 +1757,7 @@ longCallC(Context* con, unsigned size UNUSED, lir::Constant* target)
|
|||||||
assert(con, size == TargetBytesPerWord);
|
assert(con, size == TargetBytesPerWord);
|
||||||
|
|
||||||
lir::Register tmp(4);
|
lir::Register tmp(4);
|
||||||
moveCR2(con, TargetBytesPerWord, target, &tmp, offset(con));
|
moveCR2(con, TargetBytesPerWord, target, &tmp, offsetPromise(con));
|
||||||
callR(con, TargetBytesPerWord, &tmp);
|
callR(con, TargetBytesPerWord, &tmp);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1865,7 +1767,7 @@ longJumpC(Context* con, unsigned size UNUSED, lir::Constant* target)
|
|||||||
assert(con, size == TargetBytesPerWord);
|
assert(con, size == TargetBytesPerWord);
|
||||||
|
|
||||||
lir::Register tmp(4); // a non-arg reg that we don't mind clobbering
|
lir::Register tmp(4); // a non-arg reg that we don't mind clobbering
|
||||||
moveCR2(con, TargetBytesPerWord, target, &tmp, offset(con));
|
moveCR2(con, TargetBytesPerWord, target, &tmp, offsetPromise(con));
|
||||||
jumpR(con, TargetBytesPerWord, &tmp);
|
jumpR(con, TargetBytesPerWord, &tmp);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1874,7 +1776,7 @@ jumpC(Context* con, unsigned size UNUSED, lir::Constant* target)
|
|||||||
{
|
{
|
||||||
assert(con, size == TargetBytesPerWord);
|
assert(con, size == TargetBytesPerWord);
|
||||||
|
|
||||||
appendOffsetTask(con, target->value, offset(con));
|
appendOffsetTask(con, target->value, offsetPromise(con));
|
||||||
emit(con, b(0));
|
emit(con, b(0));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2120,7 +2022,7 @@ class MyArchitecture: public Assembler::Architecture {
|
|||||||
}
|
}
|
||||||
|
|
||||||
virtual unsigned argumentFootprint(unsigned footprint) {
|
virtual unsigned argumentFootprint(unsigned footprint) {
|
||||||
return local::argumentFootprint(footprint);
|
return arm::argumentFootprint(footprint);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual bool argumentAlignment() {
|
virtual bool argumentAlignment() {
|
||||||
@ -2209,7 +2111,7 @@ class MyArchitecture: public Assembler::Architecture {
|
|||||||
unsigned targetParameterFootprint, void** ip,
|
unsigned targetParameterFootprint, void** ip,
|
||||||
void** stack)
|
void** stack)
|
||||||
{
|
{
|
||||||
local::nextFrame(&con, static_cast<uint32_t*>(start), size, footprint, link,
|
arm::nextFrame(&con, static_cast<uint32_t*>(start), size, footprint, link,
|
||||||
mostRecent, targetParameterFootprint, ip, stack);
|
mostRecent, targetParameterFootprint, ip, stack);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2796,7 +2698,7 @@ class MyAssembler: public Assembler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
virtual Promise* offset(bool forTrace) {
|
virtual Promise* offset(bool forTrace) {
|
||||||
return local::offset(&con, forTrace);
|
return arm::offsetPromise(&con, forTrace);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual Block* endBlock(bool startNew) {
|
virtual Block* endBlock(bool startNew) {
|
||||||
@ -2864,15 +2766,12 @@ Assembler* MyArchitecture::makeAssembler(Allocator* allocator, Zone* zone) {
|
|||||||
return new(zone) MyAssembler(this->con.s, allocator, zone, this);
|
return new(zone) MyAssembler(this->con.s, allocator, zone, this);
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace arm
|
||||||
|
|
||||||
namespace avian {
|
|
||||||
namespace codegen {
|
|
||||||
|
|
||||||
Assembler::Architecture*
|
Assembler::Architecture*
|
||||||
makeArchitectureArm(System* system, bool)
|
makeArchitectureArm(System* system, bool)
|
||||||
{
|
{
|
||||||
return new (allocate(system, sizeof(local::MyArchitecture))) local::MyArchitecture(system);
|
return new (allocate(system, sizeof(arm::MyArchitecture))) arm::MyArchitecture(system);
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace codegen
|
} // namespace codegen
|
||||||
|
39
src/codegen/arm/block.cpp
Normal file
39
src/codegen/arm/block.cpp
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
/* Copyright (c) 2008-2012, Avian Contributors
|
||||||
|
|
||||||
|
Permission to use, copy, modify, and/or distribute this software
|
||||||
|
for any purpose with or without fee is hereby granted, provided
|
||||||
|
that the above copyright notice and this permission notice appear
|
||||||
|
in all copies.
|
||||||
|
|
||||||
|
There is NO WARRANTY for this software. See license.txt for
|
||||||
|
details. */
|
||||||
|
|
||||||
|
#include "context.h"
|
||||||
|
#include "block.h"
|
||||||
|
|
||||||
|
namespace avian {
|
||||||
|
namespace codegen {
|
||||||
|
namespace arm {
|
||||||
|
|
||||||
|
void resolve(MyBlock*);
|
||||||
|
|
||||||
|
unsigned padding(MyBlock*, unsigned);
|
||||||
|
|
||||||
|
MyBlock::MyBlock(Context* context, unsigned offset):
|
||||||
|
context(context), next(0), poolOffsetHead(0), poolOffsetTail(0),
|
||||||
|
lastPoolOffsetTail(0), poolEventHead(0), poolEventTail(0),
|
||||||
|
lastEventOffset(0), offset(offset), start(~0), size(0)
|
||||||
|
{ }
|
||||||
|
|
||||||
|
unsigned MyBlock::resolve(unsigned start, Assembler::Block* next) {
|
||||||
|
this->start = start;
|
||||||
|
this->next = static_cast<MyBlock*>(next);
|
||||||
|
|
||||||
|
arm::resolve(this);
|
||||||
|
|
||||||
|
return start + size + padding(this, size);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace arm
|
||||||
|
} // namespace codegen
|
||||||
|
} // namespace avian
|
47
src/codegen/arm/block.h
Normal file
47
src/codegen/arm/block.h
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
/* Copyright (c) 2008-2012, Avian Contributors
|
||||||
|
|
||||||
|
Permission to use, copy, modify, and/or distribute this software
|
||||||
|
for any purpose with or without fee is hereby granted, provided
|
||||||
|
that the above copyright notice and this permission notice appear
|
||||||
|
in all copies.
|
||||||
|
|
||||||
|
There is NO WARRANTY for this software. See license.txt for
|
||||||
|
details. */
|
||||||
|
|
||||||
|
#ifndef AVIAN_CODEGEN_ASSEMBLER_ARM_BLOCK_H
|
||||||
|
#define AVIAN_CODEGEN_ASSEMBLER_ARM_BLOCK_H
|
||||||
|
|
||||||
|
#include <avian/vm/codegen/lir.h>
|
||||||
|
#include <avian/vm/codegen/assembler.h>
|
||||||
|
#include "alloc-vector.h"
|
||||||
|
|
||||||
|
namespace avian {
|
||||||
|
namespace codegen {
|
||||||
|
namespace arm {
|
||||||
|
|
||||||
|
class PoolEvent;
|
||||||
|
|
||||||
|
class MyBlock: public Assembler::Block {
|
||||||
|
public:
|
||||||
|
MyBlock(Context* context, unsigned offset);
|
||||||
|
|
||||||
|
virtual unsigned resolve(unsigned start, Assembler::Block* next);
|
||||||
|
|
||||||
|
Context* context;
|
||||||
|
MyBlock* next;
|
||||||
|
PoolOffset* poolOffsetHead;
|
||||||
|
PoolOffset* poolOffsetTail;
|
||||||
|
PoolOffset* lastPoolOffsetTail;
|
||||||
|
PoolEvent* poolEventHead;
|
||||||
|
PoolEvent* poolEventTail;
|
||||||
|
unsigned lastEventOffset;
|
||||||
|
unsigned offset;
|
||||||
|
unsigned start;
|
||||||
|
unsigned size;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace arm
|
||||||
|
} // namespace codegen
|
||||||
|
} // namespace avian
|
||||||
|
|
||||||
|
#endif // AVIAN_CODEGEN_ASSEMBLER_ARM_BLOCK_H
|
27
src/codegen/arm/context.cpp
Normal file
27
src/codegen/arm/context.cpp
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
/* Copyright (c) 2008-2012, Avian Contributors
|
||||||
|
|
||||||
|
Permission to use, copy, modify, and/or distribute this software
|
||||||
|
for any purpose with or without fee is hereby granted, provided
|
||||||
|
that the above copyright notice and this permission notice appear
|
||||||
|
in all copies.
|
||||||
|
|
||||||
|
There is NO WARRANTY for this software. See license.txt for
|
||||||
|
details. */
|
||||||
|
|
||||||
|
#include "context.h"
|
||||||
|
#include "block.h"
|
||||||
|
|
||||||
|
namespace avian {
|
||||||
|
namespace codegen {
|
||||||
|
namespace arm {
|
||||||
|
|
||||||
|
Context::Context(vm::System* s, vm::Allocator* a, vm::Zone* zone):
|
||||||
|
s(s), zone(zone), client(0), code(s, a, 1024), tasks(0), result(0),
|
||||||
|
firstBlock(new(zone) MyBlock(this, 0)),
|
||||||
|
lastBlock(firstBlock), poolOffsetHead(0), poolOffsetTail(0),
|
||||||
|
constantPool(0), constantPoolCount(0)
|
||||||
|
{ }
|
||||||
|
|
||||||
|
} // namespace arm
|
||||||
|
} // namespace codegen
|
||||||
|
} // namespace avian
|
108
src/codegen/arm/context.h
Normal file
108
src/codegen/arm/context.h
Normal file
@ -0,0 +1,108 @@
|
|||||||
|
/* Copyright (c) 2008-2012, Avian Contributors
|
||||||
|
|
||||||
|
Permission to use, copy, modify, and/or distribute this software
|
||||||
|
for any purpose with or without fee is hereby granted, provided
|
||||||
|
that the above copyright notice and this permission notice appear
|
||||||
|
in all copies.
|
||||||
|
|
||||||
|
There is NO WARRANTY for this software. See license.txt for
|
||||||
|
details. */
|
||||||
|
|
||||||
|
#ifndef AVIAN_CODEGEN_ASSEMBLER_ARM_CONTEXT_H
|
||||||
|
#define AVIAN_CODEGEN_ASSEMBLER_ARM_CONTEXT_H
|
||||||
|
|
||||||
|
#include <avian/vm/codegen/lir.h>
|
||||||
|
#include <avian/vm/codegen/assembler.h>
|
||||||
|
#include "alloc-vector.h"
|
||||||
|
|
||||||
|
namespace vm {
|
||||||
|
class System;
|
||||||
|
class Allocator;
|
||||||
|
class Zone;
|
||||||
|
} // namespace vm
|
||||||
|
|
||||||
|
namespace avian {
|
||||||
|
|
||||||
|
namespace util {
|
||||||
|
class Aborter;
|
||||||
|
} // namespace util
|
||||||
|
|
||||||
|
namespace codegen {
|
||||||
|
namespace arm {
|
||||||
|
|
||||||
|
class Task;
|
||||||
|
class MyBlock;
|
||||||
|
class PoolOffset;
|
||||||
|
class ConstantPoolEntry;
|
||||||
|
|
||||||
|
class Context {
|
||||||
|
public:
|
||||||
|
Context(vm::System* s, vm::Allocator* a, vm::Zone* zone);
|
||||||
|
|
||||||
|
vm::System* s;
|
||||||
|
vm::Zone* zone;
|
||||||
|
Assembler::Client* client;
|
||||||
|
vm::Vector code;
|
||||||
|
Task* tasks;
|
||||||
|
uint8_t* result;
|
||||||
|
MyBlock* firstBlock;
|
||||||
|
MyBlock* lastBlock;
|
||||||
|
PoolOffset* poolOffsetHead;
|
||||||
|
PoolOffset* poolOffsetTail;
|
||||||
|
ConstantPoolEntry* constantPool;
|
||||||
|
unsigned constantPoolCount;
|
||||||
|
};
|
||||||
|
|
||||||
|
class Task {
|
||||||
|
public:
|
||||||
|
Task(Task* next): next(next) { }
|
||||||
|
|
||||||
|
virtual void run(Context* con) = 0;
|
||||||
|
|
||||||
|
Task* next;
|
||||||
|
};
|
||||||
|
|
||||||
|
typedef void (*OperationType)(Context*);
|
||||||
|
|
||||||
|
typedef void (*UnaryOperationType)(Context*, unsigned, lir::Operand*);
|
||||||
|
|
||||||
|
typedef void (*BinaryOperationType)
|
||||||
|
(Context*, unsigned, lir::Operand*, unsigned, lir::Operand*);
|
||||||
|
|
||||||
|
typedef void (*TernaryOperationType)
|
||||||
|
(Context*, unsigned, lir::Operand*, lir::Operand*,
|
||||||
|
lir::Operand*);
|
||||||
|
|
||||||
|
typedef void (*BranchOperationType)
|
||||||
|
(Context*, lir::TernaryOperation, unsigned, lir::Operand*,
|
||||||
|
lir::Operand*, lir::Operand*);
|
||||||
|
|
||||||
|
class ArchitectureContext {
|
||||||
|
public:
|
||||||
|
ArchitectureContext(vm::System* s): s(s) { }
|
||||||
|
|
||||||
|
vm::System* s;
|
||||||
|
OperationType operations[lir::OperationCount];
|
||||||
|
UnaryOperationType unaryOperations[lir::UnaryOperationCount
|
||||||
|
* lir::OperandTypeCount];
|
||||||
|
BinaryOperationType binaryOperations
|
||||||
|
[lir::BinaryOperationCount * lir::OperandTypeCount * lir::OperandTypeCount];
|
||||||
|
TernaryOperationType ternaryOperations
|
||||||
|
[lir::NonBranchTernaryOperationCount * lir::OperandTypeCount];
|
||||||
|
BranchOperationType branchOperations
|
||||||
|
[lir::BranchOperationCount * lir::OperandTypeCount * lir::OperandTypeCount];
|
||||||
|
};
|
||||||
|
|
||||||
|
inline avian::util::Aborter* getAborter(Context* c) {
|
||||||
|
return c->s;
|
||||||
|
}
|
||||||
|
|
||||||
|
inline avian::util::Aborter* getAborter(ArchitectureContext* c) {
|
||||||
|
return c->s;
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace arm
|
||||||
|
} // namespace codegen
|
||||||
|
} // namespace avian
|
||||||
|
|
||||||
|
#endif // AVIAN_CODEGEN_ASSEMBLER_ARM_CONTEXT_H
|
Loading…
Reference in New Issue
Block a user