diff --git a/compiler/runtime/OMRRelocationRecord.cpp b/compiler/runtime/OMRRelocationRecord.cpp new file mode 100644 index 00000000000..08b87e3e458 --- /dev/null +++ b/compiler/runtime/OMRRelocationRecord.cpp @@ -0,0 +1,358 @@ +/******************************************************************************* + * Copyright (c) 2000, 2022 IBM Corp. and others + * + * This program and the accompanying materials are made available under + * the terms of the Eclipse Public License 2.0 which accompanies this + * distribution and is available at https://www.eclipse.org/legal/epl-2.0/ + * or the Apache License, Version 2.0 which accompanies this distribution and + * is available at https://www.apache.org/licenses/LICENSE-2.0. + * + * This Source Code may also be made available under the following + * Secondary Licenses when the conditions for such availability set + * forth in the Eclipse Public License, v. 2.0 are satisfied: GNU + * General Public License, version 2 with the GNU Classpath + * Exception [1] and GNU General Public License, version 2 with the + * OpenJDK Assembly Exception [2]. + * + * [1] https://www.gnu.org/software/classpath/license.html + * [2] http://openjdk.java.net/legal/assembly-exception.html + * + * SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 OR GPL-2.0 WITH Classpath-exception-2.0 OR LicenseRef-GPL-2.0 WITH Assembly-exception + *******************************************************************************/ + +#include +#include "omrcfg.h" +#include "codegen/CodeGenerator.hpp" +#include "env/FrontEnd.hpp" +#include "codegen/Relocation.hpp" +#include "compile/ResolvedMethod.hpp" +#include "control/Options.hpp" +#include "control/Options_inlines.hpp" +#include "infra/Assert.hpp" +#include "env/jittypes.h" +#include "env/VMAccessCriticalSection.hpp" +#include "infra/SimpleRegex.hpp" +#include "runtime/CodeCache.hpp" +#include "runtime/CodeCacheManager.hpp" +#include "runtime/TRRelocationRecord.hpp" +#include "runtime/TRRelocationRuntime.hpp" +#include "runtime/TRRelocationTarget.hpp" + +#if defined(__IBMCPP__) && !defined(AIXPPC) && !defined(LINUXPPC) +#define ASM_CALL __cdecl +#else +#define ASM_CALL +#endif +#if defined(TR_HOST_S390) || defined(TR_HOST_X86) // gotten from RuntimeAssumptions.cpp, should common these up +extern "C" void _patchVirtualGuard(uint8_t *locationAddr, uint8_t *destinationAddr, int32_t smpFlag); +#else +extern "C" void ASM_CALL _patchVirtualGuard(uint8_t*, uint8_t*, uint32_t); +#endif + +uint8_t +OMR::RelocationRecordBinaryTemplate::type(TR::RelocationTarget *reloTarget) + { + return reloTarget->loadUnsigned8b(&_type); + } + +void +OMR::RelocationRecordBinaryTemplate::setSize(TR::RelocationTarget *reloTarget,uint16_t size) + { + return reloTarget->storeUnsigned16b(size, reinterpret_cast(&_size)); + } +void +OMR::RelocationRecordBinaryTemplate::setType(TR::RelocationTarget *reloTarget, uint8_t type) + { + return reloTarget->storeUnsigned8b(type,&_type); + } + +void +OMR::RelocationRecordBinaryTemplate::setFlags(TR::RelocationTarget *reloTarget,uint8_t flags) + { + return reloTarget->storeUnsigned8b(flags,&_flags); + } + + +TR::RelocationRecord * +OMR::RelocationRecord::self() + { + return static_cast(this); + } + +void +OMR::RelocationRecordGroup::setSize(TR::RelocationTarget *reloTarget,uintptr_t size) + { + reloTarget->storePointer((uint8_t *)size, (uint8_t *) _dataBuffer); + } + +uintptr_t +OMR::RelocationRecordGroup::size(TR::RelocationTarget *reloTarget) + { + return (uintptr_t)reloTarget->loadPointer((uint8_t *) _dataBuffer); + } + +TR::RelocationRecordBinaryTemplate * +OMR::RelocationRecordGroup::firstRecord(TR::RelocationTarget *reloTarget) + { + // first word of the group is a pointer size field for the entire group + return (TR::RelocationRecordBinaryTemplate *) (((uintptr_t *)_dataBuffer)+1); + } + +TR::RelocationRecordBinaryTemplate * +OMR::RelocationRecordGroup::pastLastRecord(TR::RelocationTarget *reloTarget) + { + return (TR::RelocationRecordBinaryTemplate *) ((uint8_t *)_dataBuffer + size(reloTarget)); + } + +int32_t +OMR::RelocationRecordGroup::applyRelocations(TR::RelocationRuntime *reloRuntime, + TR::RelocationTarget *reloTarget, + uint8_t *reloOrigin) + { + TR::RelocationRecordBinaryTemplate *recordPointer = firstRecord(reloTarget); + TR::RelocationRecordBinaryTemplate *endOfRecords = pastLastRecord(reloTarget); + + while (recordPointer < endOfRecords) + { + TR::RelocationRecord storage; + // Create a specific type of relocation record based on the information + // in the binary record pointed to by `recordPointer` + TR::RelocationRecord *reloRecord = TR::RelocationRecord::create(&storage, reloRuntime, reloTarget, recordPointer); + int32_t rc = handleRelocation(reloRuntime, reloTarget, reloRecord, reloOrigin); + if (rc != 0) + return rc; + + recordPointer = reloRecord->nextBinaryRecord(reloTarget); + } + + return 0; + } + +int32_t +OMR::RelocationRecordGroup::handleRelocation(TR::RelocationRuntime *reloRuntime, + TR::RelocationTarget *reloTarget, + TR::RelocationRecord *reloRecord, + uint8_t *reloOrigin) + { + reloRecord->preparePrivateData(reloRuntime, reloTarget); + return reloRecord->applyRelocationAtAllOffsets(reloRuntime, reloTarget, reloOrigin); + } + +#define FLAGS_RELOCATION_WIDE_OFFSETS 0x80 +#define FLAGS_RELOCATION_EIP_OFFSET 0x40 +#define FLAGS_RELOCATION_TYPE_MASK (TR::ExternalRelocationTargetKindMask) +#define FLAGS_RELOCATION_FLAG_MASK ((uint8_t) (FLAGS_RELOCATION_WIDE_OFFSETS | FLAGS_RELOCATION_EIP_OFFSET)) + +OMR::RelocationRecordAction +OMR::RelocationRecord::action(OMR::RelocationRuntime *reloRuntime) + { + return RelocationRecordAction::apply; + } + + +TR::RelocationRecord * +OMR::RelocationRecord::create(TR::RelocationRecord *storage, TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget, TR::RelocationRecordBinaryTemplate *record) + { + TR::RelocationRecord *reloRecord = NULL; + // based on the type of the relocation record, create an object of a particular variety of OMR::RelocationRecord object + uint8_t reloType = record->type(reloTarget); + switch (reloType) + { + // an example switch-case; the implementations is runtime-specific + case TR_ExternalRelocationTargetKind::TR_MethodCallAddress: + TR_UNIMPLEMENTED(); + /** Example implementation would be to implement relocations here / overload this file following extensible classes technology. + * For instance, if TR_MethodCallAddress is used in OtherProject, the line in OtherProjectRelocationRecord.cpp + * (which includes TRRelocationRecord.hpp or, when adjusted - RelocationRecord.hpp) would be: + * reloRecord =reinterpret_cast( new (storage) OtherProject::RelocationRecordMethodCallAddress(reloRuntime,record)); + * The current assumption is that if a relocation is common enough, it could be added to OMR directly + */ + break; + default: + // TODO: error condition + TR_UNIMPLEMENTED(); + exit(0); + } + + return reloRecord; + } + +void +OMR::RelocationRecord::clean(TR::RelocationTarget *reloTarget) + { + self()->setSize(reloTarget, 0); + self()->setType(reloTarget,(OMR::RelocationRecordType)_record->_type); + self()->setReloFlags(reloTarget, _record->_flags); + } + +int32_t +OMR::RelocationRecord::bytesInHeader(TR::RelocationTarget *reloTarget) + { + return OMR::RelocationRecord::getSizeOfAOTRelocationHeader(self()->type(reloTarget)); + } + +TR::RelocationRecordBinaryTemplate * +OMR::RelocationRecordBinaryTemplate::self() + { + return static_cast(this); + } + +TR::RelocationRecordBinaryTemplate * +OMR::RelocationRecord::nextBinaryRecord(TR::RelocationTarget *reloTarget) + { + return (TR::RelocationRecordBinaryTemplate*) (((uint8_t*)self()->_record) + self()->size(reloTarget)); + } + +void +OMR::RelocationRecord::setSize(TR::RelocationTarget *reloTarget, uint16_t size) + { + reloTarget->storeUnsigned16b(size,(uint8_t *) &_record->_size); + } + +uint16_t +OMR::RelocationRecord::size(TR::RelocationTarget *reloTarget) + { + return reloTarget->loadUnsigned16b((uint8_t *) &_record->_size); + } + + +void +OMR::RelocationRecord::setType(TR::RelocationTarget *reloTarget, OMR::RelocationRecordType type) + { + reloTarget->storeUnsigned8b(type, (uint8_t *) &_record->_type); + } + +OMR::RelocationRecordType +OMR::RelocationRecord::type(TR::RelocationTarget *reloTarget) + { + return (OMR::RelocationRecordType)_record->type(reloTarget); + } + + +void +OMR::RelocationRecord::setWideOffsets(TR::RelocationTarget *reloTarget) + { + self()->setFlag(reloTarget, FLAGS_RELOCATION_WIDE_OFFSETS); + } + +bool +OMR::RelocationRecord::wideOffsets(TR::RelocationTarget *reloTarget) + { + return (self()->flags(reloTarget) & FLAGS_RELOCATION_WIDE_OFFSETS) != 0; + } + +void +OMR::RelocationRecord::setPcRelative(TR::RelocationTarget *reloTarget) + { + self()->setFlag(reloTarget, FLAGS_RELOCATION_EIP_OFFSET); + } + +bool +OMR::RelocationRecord::pcRelative(TR::RelocationTarget *reloTarget) + { + return (self()->flags(reloTarget) & FLAGS_RELOCATION_EIP_OFFSET) != 0; + } + +void +OMR::RelocationRecord::setFlag(TR::RelocationTarget *reloTarget, uint8_t flag) + { + uint8_t flags = reloTarget->loadUnsigned8b((uint8_t *) &_record->_flags) | (flag & FLAGS_RELOCATION_FLAG_MASK); + reloTarget->storeUnsigned8b(flags, (uint8_t *) &_record->_flags); + } + +uint8_t +OMR::RelocationRecord::flags(TR::RelocationTarget *reloTarget) + { + return reloTarget->loadUnsigned8b((uint8_t *) &_record->_flags) & FLAGS_RELOCATION_FLAG_MASK; + } + +void +OMR::RelocationRecord::setReloFlags(TR::RelocationTarget *reloTarget, uint8_t reloFlags) + { + TR_ASSERT((reloFlags & ~FLAGS_RELOCATION_FLAG_MASK) == 0, "reloFlags bits overlap cross-platform flags bits\n"); + uint8_t crossPlatFlags = self()->flags(reloTarget); + uint8_t flags = crossPlatFlags | (reloFlags & ~FLAGS_RELOCATION_FLAG_MASK); + reloTarget->storeUnsigned8b(flags, (uint8_t *) &_record->_flags); + } + +uint8_t +OMR::RelocationRecord::reloFlags(TR::RelocationTarget *reloTarget) + { + return reloTarget->loadUnsigned8b((uint8_t *) &_record->_flags) & ~FLAGS_RELOCATION_FLAG_MASK; + } + +void +OMR::RelocationRecord::preparePrivateData(TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget) + { + /** + * Private data is used for caching computed data from what's stored in the record's binary representation + * and the current runtime state, to prevent computing this value at every offset where this value should + * be applied. + * + * This function can be used to query the value that should be inserted in the compiled code from the runtime + * just once, instead of repeating the querying process every time the value is required. + * The retrived value can be cached in _privateData field + */ + TR_UNIMPLEMENTED(); + } + +#undef FLAGS_RELOCATION_WIDE_OFFSETS +#undef FLAGS_RELOCATION_EIP_OFFSET +#undef FLAGS_RELOCATION_ORDERED_PAIR +#undef FLAGS_RELOCATION_TYPE_MASK +#undef FLAGS_RELOCATION_FLAG_MASK + + +bool +OMR::RelocationRecord::ignore(TR::RelocationRuntime *reloRuntime) + { + return false; + } + +int32_t +OMR::RelocationRecord::applyRelocationAtAllOffsets(TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget, uint8_t *reloOrigin) + { + if (self()->ignore(reloRuntime)) + { + return 0; + } + + if (self()->wideOffsets(reloTarget)) + { + int32_t *offsetsBase = (int32_t *) (((uint8_t*)_record) + self()->bytesInHeader(reloTarget)); + int32_t *endOfOffsets = (int32_t *) self()->nextBinaryRecord(reloTarget); + for (int32_t *offsetPtr = offsetsBase;offsetPtr < endOfOffsets; offsetPtr++) + { + int32_t offset = *offsetPtr; + uint8_t *reloLocation = reloOrigin + offset; + int32_t rc = self()->applyRelocation(reloRuntime, reloTarget, reloLocation); + if (rc != 0) + { + return rc; + } + } + } + else + { + int16_t *offsetsBase = (int16_t *) (((uint8_t*)_record) + self()->bytesInHeader(reloTarget)); + int16_t *endOfOffsets = (int16_t *) self()->nextBinaryRecord(reloTarget); + for (int16_t *offsetPtr = offsetsBase;offsetPtr < endOfOffsets; offsetPtr++) + { + int16_t offset = *offsetPtr; + uint8_t *reloLocation = reloOrigin + offset; + int32_t rc = self()->applyRelocation(reloRuntime, reloTarget, reloLocation); + if (rc != 0) + { + return rc; + } + } + } + return 0; + } + + +uint32_t OMR::RelocationRecord::_relocationRecordHeaderSizeTable[TR_NumExternalRelocationKinds] = + { + //This will be removed with further work on openJ9. + (uint32_t) -1, + }; diff --git a/compiler/runtime/OMRRelocationRecord.hpp b/compiler/runtime/OMRRelocationRecord.hpp new file mode 100644 index 00000000000..8425af02473 --- /dev/null +++ b/compiler/runtime/OMRRelocationRecord.hpp @@ -0,0 +1,234 @@ +/******************************************************************************* + * Copyright (c) 2000, 2022 IBM Corp. and others + * + * This program and the accompanying materials are made available under + * the terms of the Eclipse Public License 2.0 which accompanies this + * distribution and is available at https://www.eclipse.org/legal/epl-2.0/ + * or the Apache License, Version 2.0 which accompanies this distribution and + * is available at https://www.apache.org/licenses/LICENSE-2.0. + * + * This Source Code may also be made available under the following + * Secondary Licenses when the conditions for such availability set + * forth in the Eclipse Public License, v. 2.0 are satisfied: GNU + * General Public License, version 2 with the GNU Classpath + * Exception [1] and GNU General Public License, version 2 with the + * OpenJDK Assembly Exception [2]. + * + * [1] https://www.gnu.org/software/classpath/license.html + * [2] http://openjdk.java.net/legal/assembly-exception.html + * + * SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 OR GPL-2.0 WITH Classpath-exception-2.0 OR LicenseRef-GPL-2.0 WITH Assembly-exception + *******************************************************************************/ + +#ifndef OMR_RELOCATION_RECORD_INCL +#define OMR_RELOCATION_RECORD_INCL +/* + * The following #define(s) and typedef(s) must appear before any #includes in this file + */ +#ifndef OMR_RELOCATION_RECORD_CONNECTOR +#define OMR_RELOCATION_RECORD_CONNECTOR +namespace OMR { class RelocationRecord; } +namespace OMR { typedef OMR::RelocationRecord RelocationRecordConnector; } +#else + #error OMR::RelocationRecord expected to be a primary connector, but another connector is already defined +#endif + + +#ifndef OMR_RELOCATION_RECORD_BINARY_TEMPLATE_CONNECTOR +#define OMR_RELOCATION_RECORD_BINARY_TEMPLATE_CONNECTOR +namespace OMR { class RelocationRecordBinaryTemplate; } +namespace OMR { typedef OMR::RelocationRecordBinaryTemplate RelocationRecordBinaryTemplateConnector; } +#else + #error OMR::RelocationRecordBinaryTemplate expected to be a primary connector, but another connector is already defined +#endif + + +#include +#include "compile/Compilation.hpp" +#include "env/jittypes.h" +#include "infra/Link.hpp" +#include "infra/Flags.hpp" +#include "runtime/TRRelocationRuntime.hpp" +#include "runtime/Runtime.hpp" + +namespace TR { +class RelocationRuntime; +class RelocationTarget; +class RelocationRecord; +class RelocationRecordBinaryTemplate; +/** + * @brief RelocationRecords can specify a struct for caching all the related values + * for accellerating relocation application process through avoiding multiple computations + * of the same value when applying the relocation at different offsets. + */ +struct RelocationRecordMethodCallPrivateData + { + uintptr_t callTargetOffset; + }; +/** + * @brief This union is supposed to be a union of all possible PrivateData structs + * allowing RelocationRecords allocating enough space for all kinds of RelocationRecordPrivateData + */ +union RelocationRecordPrivateData + { + struct RelocationRecordMethodCallPrivateData; + }; + +} + +namespace OMR { typedef TR_ExternalRelocationTargetKind RelocationRecordType;} +namespace TR { typedef TR_ExternalRelocationTargetKind RelocationRecordType;} +namespace TR { class RelocationRecordBinaryTemplate;} +extern char* AOTcgDiagOn; + +// TR::RelocationRecord is the base class for all relocation records. It is used for all queries on relocation +// records as well as holding all the "wrapper" parts. These classes are an interface to the *BinaryTemplate +// classes which are simply structs that can be used to directly access the binary representation of the relocation +// records stored in the cache (*BinaryTemplate structs are defined near the end of this file after the +// RelocationRecord* classes. The RelocationRecord* classes permit virtual function calls access to the +// *BinaryTemplate classes and must access the binary structs via the _record field in the TR::RelocationRecord +// class. Most consumers should directly manipulate the TR::RelocationRecord* classes since they offer +// the most flexibility. +// No class that derives from TR::RelocationRecord should define any state: all state variables should be declared +// in TR::RelocationRecord or the constructor/decode() mechanisms will not work properly +// Relocation record classes for "real" relocation record types +// should be defined on the level of consuming project + +namespace OMR +{ + +class OMR_EXTENSIBLE RelocationRecordBinaryTemplate + { +public: + RelocationRecordBinaryTemplate(){}; + void setType(TR::RelocationTarget*, uint8_t kind); + void setSize(TR::RelocationTarget*, uint16_t size); + void setFlags(TR::RelocationTarget*, uint8_t flags); + uint8_t type(TR::RelocationTarget *reloTarget); + uint16_t _size; + uint8_t _type; + uint8_t _flags; +protected: + TR::RelocationRecordBinaryTemplate* self(); + }; + +enum RelocationRecordAction + { + ignore, + apply, + failCompilation + }; + +class OMR_EXTENSIBLE RelocationRecord + { +public: + RelocationRecord() {} + RelocationRecord(TR::RelocationRuntime *reloRuntime, TR::RelocationRecordBinaryTemplate *record) + { + _reloRuntime= reloRuntime; + _record =record; + } + + void * operator new (size_t s, RelocationRecord *p) { return p; } + char *name() { return "RelocationRecord"; } + + bool isValidationRecord() { return false; } + + /** + * @brief Using a pre-specified location (storage), create an instance of relocationRecord, + * as it is described by its serialized version RelocationRecordBinaryTemplate. The operation + * varies between architecture, hence RelocationTarget is made available + * + * @param storage - location where to create relocation record + * @param reloRuntime - class for manipulations on relocations + * @param reloTarget - class for performing operations on relocations on binary level + * @param recordPointer - pointer to a binary template - sequence of bytes describing the relocation + * @return TR::RelocationRecord* - pointer cast to the generic relocationRecord. + */ + static TR::RelocationRecord *create(TR::RelocationRecord *storage, TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget, TR::RelocationRecordBinaryTemplate *recordPointer); + + void clean(TR::RelocationTarget *reloTarget); + int32_t bytesInHeader(TR::RelocationTarget *reloTarget); + /** + * @brief This function is used to cache the values that are retrieved at run-time, during the code loading + * Sometimes, computing the values required for updating the code is non-trivial and might add extra cost. + * To avoid repeated computation, this function is used + * + * @param reloRuntime - a reference to relocation runtime to query the runtime for the required values + * @param reloTarget - a reference to the cross-platform API to store/load values at various machine dependent granularity + */ + void preparePrivateData(TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget); + + int32_t applyRelocationAtAllOffsets(TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget, uint8_t *relocationOrigin); + + int32_t applyRelocation(TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget, uint8_t *reloLocation) {return -1;} + int32_t applyRelocation(TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget, uint8_t *reloLocationHigh, uint8_t *reloLocationLow) {return -1;} + + TR::RelocationRecordBinaryTemplate *nextBinaryRecord(TR::RelocationTarget *reloTarget); + TR::RelocationRecordBinaryTemplate *binaryRecord(); + + void setSize(TR::RelocationTarget *reloTarget, uint16_t size); + uint16_t size(TR::RelocationTarget *reloTarget); + + void setType(TR::RelocationTarget *reloTarget, TR::RelocationRecordType type); + RelocationRecordType type(TR::RelocationTarget *reloTarget); + + void setWideOffsets(TR::RelocationTarget *reloTarget); + bool wideOffsets(TR::RelocationTarget *reloTarget); + + void setPcRelative(TR::RelocationTarget *reloTarget); + bool pcRelative(TR::RelocationTarget *reloTarget); + + void setFlag(TR::RelocationTarget *reloTarget, uint8_t flag); + uint8_t flags(TR::RelocationTarget *reloTarget); + + void setReloFlags(TR::RelocationTarget *reloTarget, uint8_t reloFlags); + uint8_t reloFlags(TR::RelocationTarget *reloTarget); + + TR::RelocationRuntime *_reloRuntime; + bool ignore(TR::RelocationRuntime *reloRuntime); + RelocationRecordAction action(RelocationRuntime *reloRuntime); + static uint32_t getSizeOfAOTRelocationHeader(TR_ExternalRelocationTargetKind k) + { + return _relocationRecordHeaderSizeTable[k]; + } + +protected: + TR::RelocationRecord* self(); + + TR::RelocationRecordPrivateData *privateData() + { + return &_privateData; + } + + TR::RelocationRecordBinaryTemplate *_record; + + TR::RelocationRecordPrivateData _privateData; + + static uint32_t _relocationRecordHeaderSizeTable[TR_NumExternalRelocationKinds]; + }; + + +class RelocationRecordGroup + { +public: + RelocationRecordGroup(TR::RelocationRecordBinaryTemplate *groupData) : _dataBuffer(groupData) {}; + + void setSize(TR::RelocationTarget *reloTarget, uintptr_t size); + uintptr_t size(TR::RelocationTarget *reloTarget); + + TR::RelocationRecordBinaryTemplate *firstRecord(TR::RelocationTarget *reloTarget); + TR::RelocationRecordBinaryTemplate *pastLastRecord(TR::RelocationTarget *reloTarget); + + int32_t applyRelocations(TR::RelocationRuntime *reloRuntime, + TR::RelocationTarget *reloTarget, + uint8_t *reloOrigin); +private: + int32_t handleRelocation(TR::RelocationRuntime *reloRuntime, TR::RelocationTarget *reloTarget, TR::RelocationRecord *reloRecord, uint8_t *reloOrigin); + + TR::RelocationRecordBinaryTemplate *_dataBuffer; + }; + +} //namespace OMR + +#endif // OMR_RELOCATION_RECORD_INCL diff --git a/compiler/runtime/TRRelocationRecord.hpp b/compiler/runtime/TRRelocationRecord.hpp new file mode 100644 index 00000000000..7260aec38c1 --- /dev/null +++ b/compiler/runtime/TRRelocationRecord.hpp @@ -0,0 +1,66 @@ +/******************************************************************************* + * Copyright (c) 2000, 2022 IBM Corp. and others + * + * This program and the accompanying materials are made available under + * the terms of the Eclipse Public License 2.0 which accompanies this + * distribution and is available at http://eclipse.org/legal/epl-2.0 + * or the Apache License, Version 2.0 which accompanies this distribution + * and is available at https://www.apache.org/licenses/LICENSE-2.0. + * + * This Source Code may also be made available under the following Secondary + * Licenses when the conditions for such availability set forth in the + * Eclipse Public License, v. 2.0 are satisfied: GNU General Public License, + * version 2 with the GNU Classpath Exception [1] and GNU General Public + * License, version 2 with the OpenJDK Assembly Exception [2]. + * + * [1] https://www.gnu.org/software/classpath/license.html + * [2] http://openjdk.java.net/legal/assembly-exception.html + * + * SPDX-License-Identifier: EPL-2.0 OR Apache-2.0 OR GPL-2.0 WITH Classpath-exception-2.0 OR LicenseRef-GPL-2.0 WITH Assembly-exception + *******************************************************************************/ + +#ifndef TR_RELOCATION_RECORD_INCL +#define TR_RELOCATION_RECORD_INCL + +#include "runtime/OMRRelocationRecord.hpp" + +namespace TR +{ +/** NOTE: This class is supposed to be inherited by RelocationRecord in consuming projects + * In the proper OMR extensible classes technology way, the file name should be RelocationRecord.hpp + * However, calling it this name shadows includes in production projects (e.g., in OpenJ9), + * so renaming this file happen when both projects are ready. + * See also: https://github.com/eclipse/omr/issues/5469 + */ +class OMR_EXTENSIBLE RelocationRecord: public OMR::RelocationRecordConnector + { +public: + RelocationRecord(TR::RelocationRuntime *reloRuntime, TR::RelocationRecordBinaryTemplate *record) + : OMR::RelocationRecordConnector(reloRuntime,record) + { } + + RelocationRecord(): OMR::RelocationRecordConnector() + { } + + + }; + +class OMR_EXTENSIBLE RelocationRecordBinaryTemplate: public OMR::RelocationRecordBinaryTemplateConnector + { +public: + RelocationRecordBinaryTemplate() + : OMR::RelocationRecordBinaryTemplateConnector() + { }; + }; + +class RelocationRecordGroup: public OMR::RelocationRecordGroup + { +public: + RelocationRecordGroup(TR::RelocationRecordBinaryTemplate *groupData) + : OMR::RelocationRecordGroup(groupData) + { }; + }; + +} // namespace TR + +#endif /* TR_RELOCATION_RECORD_INCL */