1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2 * vim: set ts=8 sw=4 et tw=79:
4 * ***** BEGIN LICENSE BLOCK *****
5 * Copyright (C) 2009 Apple Inc. All rights reserved.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
16 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
20 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
21 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
22 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
23 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
24 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 * ***** END LICENSE BLOCK ***** */
30 #ifndef MacroAssemblerCodeRef_h
31 #define MacroAssemblerCodeRef_h
33 #include "assembler/wtf/Platform.h"
34 #include "assembler/jit/ExecutableAllocator.h"
38 // ASSERT_VALID_CODE_POINTER checks that ptr is a non-null pointer, and that it is a valid
39 // instruction address on the platform (for example, check any alignment requirements).
40 #if WTF_CPU_ARM_THUMB2
41 // ARM/thumb instructions must be 16-bit aligned, but all code pointers to be loaded
42 // into the processor are decorated with the bottom bit set, indicating that this is
43 // thumb code (as oposed to 32-bit traditional ARM). The first test checks for both
44 // decorated and undectorated null, and the second test ensures that the pointer is
46 #define ASSERT_VALID_CODE_POINTER(ptr) \
47 ASSERT(reinterpret_cast<intptr_t>(ptr) & ~1); \
48 ASSERT(reinterpret_cast<intptr_t>(ptr) & 1)
49 #define ASSERT_VALID_CODE_OFFSET(offset) \
50 ASSERT(!(offset & 1)) // Must be multiple of 2.
52 #define ASSERT_VALID_CODE_POINTER(ptr) \
54 #define ASSERT_VALID_CODE_OFFSET(offset) // Anything goes!
61 // FunctionPtr should be used to wrap pointers to C/C++ functions in JSC
62 // (particularly, the stub functions).
70 template<typename FunctionType>
71 explicit FunctionPtr(FunctionType* value)
73 // RVTC compiler needs C-style cast as it fails with the following error
74 // Error: #694: reinterpret_cast cannot cast away const or other type qualifiers
75 : m_value((void*)(value))
77 : m_value(reinterpret_cast<void*>(value))
80 ASSERT_VALID_CODE_POINTER(m_value);
83 void* value() const { return m_value; }
84 void* executableAddress() const { return m_value; }
93 // ReturnAddressPtr should be used to wrap return addresses generated by processor
94 // 'call' instructions exectued in JIT code. We use return addresses to look up
95 // exception and optimization information, and to repatch the call instruction
96 // that is the source of the return address.
97 class ReturnAddressPtr {
104 explicit ReturnAddressPtr(void* value)
107 ASSERT_VALID_CODE_POINTER(m_value);
110 explicit ReturnAddressPtr(FunctionPtr function)
111 : m_value(function.value())
113 ASSERT_VALID_CODE_POINTER(m_value);
116 void* value() const { return m_value; }
122 // MacroAssemblerCodePtr:
124 // MacroAssemblerCodePtr should be used to wrap pointers to JIT generated code.
125 class MacroAssemblerCodePtr {
127 MacroAssemblerCodePtr()
132 explicit MacroAssemblerCodePtr(void* value)
133 #if WTF_CPU_ARM_THUMB2
134 // Decorate the pointer as a thumb code pointer.
135 : m_value(reinterpret_cast<char*>(value) + 1)
140 ASSERT_VALID_CODE_POINTER(m_value);
143 explicit MacroAssemblerCodePtr(ReturnAddressPtr ra)
144 : m_value(ra.value())
146 ASSERT_VALID_CODE_POINTER(m_value);
149 void* executableAddress() const {
152 #if WTF_CPU_ARM_THUMB2
153 // To use this pointer as a data address remove the decoration.
154 void* dataLocation() const { ASSERT_VALID_CODE_POINTER(m_value); return reinterpret_cast<char*>(m_value) - 1; }
156 void* dataLocation() const { ASSERT_VALID_CODE_POINTER(m_value); return m_value; }
164 ptrdiff_t operator -(const MacroAssemblerCodePtr &other) const
167 return reinterpret_cast<uint8 *>(m_value) -
168 reinterpret_cast<uint8 *>(other.m_value);
175 // MacroAssemblerCodeRef:
177 // A reference to a section of JIT generated code. A CodeRef consists of a
178 // pointer to the code, and a ref pointer to the pool from within which it
180 class MacroAssemblerCodeRef {
182 MacroAssemblerCodeRef()
187 MacroAssemblerCodeRef(void* code, ExecutablePool* executablePool, size_t size)
189 , m_executablePool(executablePool)
194 MacroAssemblerCodePtr m_code;
195 ExecutablePool* m_executablePool;
201 #endif // ENABLE(ASSEMBLER)
203 #endif // MacroAssemblerCodeRef_h