• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2009 Apple Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
17  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24  */
25 
26 #ifndef RepatchBuffer_h
27 #define RepatchBuffer_h
28 
29 #if ENABLE(ASSEMBLER)
30 
31 #include <MacroAssembler.h>
32 #include <wtf/Noncopyable.h>
33 
34 namespace JSC {
35 
36 // RepatchBuffer:
37 //
38 // This class is used to modify code after code generation has been completed,
39 // and after the code has potentially already been executed.  This mechanism is
40 // used to apply optimizations to the code.
41 //
42 class RepatchBuffer {
43     typedef MacroAssemblerCodePtr CodePtr;
44 
45 public:
RepatchBuffer(CodeBlock * codeBlock)46     RepatchBuffer(CodeBlock* codeBlock)
47     {
48         JITCode& code = codeBlock->getJITCode();
49         m_start = code.start();
50         m_size = code.size();
51 
52         ExecutableAllocator::makeWritable(m_start, m_size);
53     }
54 
~RepatchBuffer()55     ~RepatchBuffer()
56     {
57         ExecutableAllocator::makeExecutable(m_start, m_size);
58     }
59 
relink(CodeLocationJump jump,CodeLocationLabel destination)60     void relink(CodeLocationJump jump, CodeLocationLabel destination)
61     {
62         MacroAssembler::repatchJump(jump, destination);
63     }
64 
relink(CodeLocationCall call,CodeLocationLabel destination)65     void relink(CodeLocationCall call, CodeLocationLabel destination)
66     {
67         MacroAssembler::repatchCall(call, destination);
68     }
69 
relink(CodeLocationCall call,FunctionPtr destination)70     void relink(CodeLocationCall call, FunctionPtr destination)
71     {
72         MacroAssembler::repatchCall(call, destination);
73     }
74 
relink(CodeLocationNearCall nearCall,CodePtr destination)75     void relink(CodeLocationNearCall nearCall, CodePtr destination)
76     {
77         MacroAssembler::repatchNearCall(nearCall, CodeLocationLabel(destination));
78     }
79 
relink(CodeLocationNearCall nearCall,CodeLocationLabel destination)80     void relink(CodeLocationNearCall nearCall, CodeLocationLabel destination)
81     {
82         MacroAssembler::repatchNearCall(nearCall, destination);
83     }
84 
repatch(CodeLocationDataLabel32 dataLabel32,int32_t value)85     void repatch(CodeLocationDataLabel32 dataLabel32, int32_t value)
86     {
87         MacroAssembler::repatchInt32(dataLabel32, value);
88     }
89 
repatch(CodeLocationDataLabelPtr dataLabelPtr,void * value)90     void repatch(CodeLocationDataLabelPtr dataLabelPtr, void* value)
91     {
92         MacroAssembler::repatchPointer(dataLabelPtr, value);
93     }
94 
relinkCallerToTrampoline(ReturnAddressPtr returnAddress,CodeLocationLabel label)95     void relinkCallerToTrampoline(ReturnAddressPtr returnAddress, CodeLocationLabel label)
96     {
97         relink(CodeLocationCall(CodePtr(returnAddress)), label);
98     }
99 
relinkCallerToTrampoline(ReturnAddressPtr returnAddress,CodePtr newCalleeFunction)100     void relinkCallerToTrampoline(ReturnAddressPtr returnAddress, CodePtr newCalleeFunction)
101     {
102         relinkCallerToTrampoline(returnAddress, CodeLocationLabel(newCalleeFunction));
103     }
104 
relinkCallerToFunction(ReturnAddressPtr returnAddress,FunctionPtr function)105     void relinkCallerToFunction(ReturnAddressPtr returnAddress, FunctionPtr function)
106     {
107         relink(CodeLocationCall(CodePtr(returnAddress)), function);
108     }
109 
relinkNearCallerToTrampoline(ReturnAddressPtr returnAddress,CodeLocationLabel label)110     void relinkNearCallerToTrampoline(ReturnAddressPtr returnAddress, CodeLocationLabel label)
111     {
112         relink(CodeLocationNearCall(CodePtr(returnAddress)), label);
113     }
114 
relinkNearCallerToTrampoline(ReturnAddressPtr returnAddress,CodePtr newCalleeFunction)115     void relinkNearCallerToTrampoline(ReturnAddressPtr returnAddress, CodePtr newCalleeFunction)
116     {
117         relinkNearCallerToTrampoline(returnAddress, CodeLocationLabel(newCalleeFunction));
118     }
119 
120 private:
121     void* m_start;
122     size_t m_size;
123 };
124 
125 } // namespace JSC
126 
127 #endif // ENABLE(ASSEMBLER)
128 
129 #endif // RepatchBuffer_h
130