Imported Upstream version 1.0.0
[platform/upstream/js.git] / js / src / assembler / assembler / MacroAssemblerCodeRef.h
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2  * vim: set ts=8 sw=4 et tw=79:
3  *
4  * ***** BEGIN LICENSE BLOCK *****
5  * Copyright (C) 2009 Apple Inc. All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
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.
15  *
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. 
27  * 
28  * ***** END LICENSE BLOCK ***** */
29
30 #ifndef MacroAssemblerCodeRef_h
31 #define MacroAssemblerCodeRef_h
32
33 #include "assembler/wtf/Platform.h"
34 #include "assembler/jit/ExecutableAllocator.h"
35
36 #if ENABLE_ASSEMBLER
37
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
45 // decorated.
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.
51 #else
52 #define ASSERT_VALID_CODE_POINTER(ptr) \
53     ASSERT(ptr)
54 #define ASSERT_VALID_CODE_OFFSET(offset) // Anything goes!
55 #endif
56
57 namespace JSC {
58
59 // FunctionPtr:
60 //
61 // FunctionPtr should be used to wrap pointers to C/C++ functions in JSC
62 // (particularly, the stub functions).
63 class FunctionPtr {
64 public:
65     FunctionPtr()
66         : m_value(0)
67     {
68     }
69
70     template<typename FunctionType>
71     explicit FunctionPtr(FunctionType* value)
72 #if WTF_COMPILER_RVCT
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))
76 #else
77         : m_value(reinterpret_cast<void*>(value))
78 #endif
79     {
80         ASSERT_VALID_CODE_POINTER(m_value);
81     }
82
83     void* value() const { return m_value; }
84     void* executableAddress() const { return m_value; }
85
86
87 private:
88     void* m_value;
89 };
90
91 // ReturnAddressPtr:
92 //
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 {
98 public:
99     ReturnAddressPtr()
100         : m_value(0)
101     {
102     }
103
104     explicit ReturnAddressPtr(void* value)
105         : m_value(value)
106     {
107         ASSERT_VALID_CODE_POINTER(m_value);
108     }
109
110     explicit ReturnAddressPtr(FunctionPtr function)
111         : m_value(function.value())
112     {
113         ASSERT_VALID_CODE_POINTER(m_value);
114     }
115
116     void* value() const { return m_value; }
117
118 private:
119     void* m_value;
120 };
121
122 // MacroAssemblerCodePtr:
123 //
124 // MacroAssemblerCodePtr should be used to wrap pointers to JIT generated code.
125 class MacroAssemblerCodePtr {
126 public:
127     MacroAssemblerCodePtr()
128         : m_value(0)
129     {
130     }
131
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)
136 #else
137         : m_value(value)
138 #endif
139     {
140         ASSERT_VALID_CODE_POINTER(m_value);
141     }
142
143     explicit MacroAssemblerCodePtr(ReturnAddressPtr ra)
144         : m_value(ra.value())
145     {
146         ASSERT_VALID_CODE_POINTER(m_value);
147     }
148
149     void* executableAddress() const {
150         return m_value;
151     }
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; }
155 #else
156     void* dataLocation() const { ASSERT_VALID_CODE_POINTER(m_value); return m_value; }
157 #endif
158
159     bool operator!()
160     {
161         return !m_value;
162     }
163
164     ptrdiff_t operator -(const MacroAssemblerCodePtr &other) const
165     {
166         JS_ASSERT(m_value);
167         return reinterpret_cast<uint8 *>(m_value) -
168                reinterpret_cast<uint8 *>(other.m_value);
169     }
170
171 private:
172     void* m_value;
173 };
174
175 // MacroAssemblerCodeRef:
176 //
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
179 // was allocated.
180 class MacroAssemblerCodeRef {
181 public:
182     MacroAssemblerCodeRef()
183         : m_size(0)
184     {
185     }
186
187     MacroAssemblerCodeRef(void* code, ExecutablePool* executablePool, size_t size)
188         : m_code(code)
189         , m_executablePool(executablePool)
190         , m_size(size)
191     {
192     }
193
194     MacroAssemblerCodePtr m_code;
195     ExecutablePool* m_executablePool;
196     size_t m_size;
197 };
198
199 } // namespace JSC
200
201 #endif // ENABLE(ASSEMBLER)
202
203 #endif // MacroAssemblerCodeRef_h