a323b5375a5c902a7ec987da658e865ad95f2019
[WebKit-https.git] / Source / JavaScriptCore / jit / JITStubRoutine.h
1 /*
2  * Copyright (C) 2012-2018 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 #pragma once
27
28 #if ENABLE(JIT)
29
30 #include "ExecutableAllocator.h"
31 #include "MacroAssemblerCodeRef.h"
32
33 namespace JSC {
34
35 class JITStubRoutineSet;
36 class VM;
37
38 // This is a base-class for JIT stub routines, and also the class you want
39 // to instantiate directly if you have a routine that does not need any
40 // help from the GC. If in doubt, use one of the other stub routines. But
41 // if you know for sure that the stub routine cannot be on the stack while
42 // someone triggers a stub routine reset, then using this will speed up
43 // memory reclamation. One case where a stub routine satisfies this
44 // condition is if it doesn't make any calls, to either C++ or JS code. In
45 // such a routine you know that it cannot be on the stack when anything
46 // interesting happens.
47 // See GCAwareJITStubRoutine.h for the other stub routines.
48 class JITStubRoutine {
49     WTF_MAKE_NONCOPYABLE(JITStubRoutine);
50     WTF_MAKE_FAST_ALLOCATED;
51 public:
52     JITStubRoutine(const MacroAssemblerCodeRef& code)
53         : m_code(code)
54         , m_refCount(1)
55     {
56     }
57     
58     // Use this if you want to pass a CodePtr to someone who insists on taking
59     // a RefPtr<JITStubRoutine>.
60     static Ref<JITStubRoutine> createSelfManagedRoutine(
61         MacroAssemblerCodePtr rawCodePointer)
62     {
63         return adoptRef(*new JITStubRoutine(MacroAssemblerCodeRef::createSelfManagedCodeRef(rawCodePointer)));
64     }
65     
66     virtual ~JITStubRoutine();
67     virtual void aboutToDie() { }
68     
69     // MacroAssemblerCodeRef is copyable, but at the cost of reference
70     // counting churn. Returning a reference is a good way of reducing
71     // the churn.
72     const MacroAssemblerCodeRef& code() const { return m_code; }
73     
74     static MacroAssemblerCodePtr asCodePtr(Ref<JITStubRoutine>&& stubRoutine)
75     {
76         MacroAssemblerCodePtr result = stubRoutine->code().code();
77         ASSERT(!!result);
78         return result;
79     }
80     
81     void ref()
82     {
83         m_refCount++;
84     }
85     
86     void deref()
87     {
88         if (--m_refCount)
89             return;
90         observeZeroRefCount();
91     }
92     
93     // Helpers for the GC to determine how to deal with marking JIT stub
94     // routines.
95     uintptr_t startAddress() const { return m_code.executableMemory()->startAsInteger(); }
96     uintptr_t endAddress() const { return m_code.executableMemory()->endAsInteger(); }
97     static uintptr_t addressStep() { return jitAllocationGranule; }
98     
99     static bool passesFilter(uintptr_t address)
100     {
101         return isJITPC(bitwise_cast<void*>(address));
102     }
103     
104     // Return true if you are still valid after. Return false if you are now invalid. If you return
105     // false, you will usually not do any clearing because the idea is that you will simply be
106     // destroyed.
107     virtual bool visitWeak(VM&);
108
109 protected:
110     virtual void observeZeroRefCount();
111
112     MacroAssemblerCodeRef m_code;
113     unsigned m_refCount;
114 };
115
116 // Helper for the creation of simple stub routines that need no help from the GC.
117 #define FINALIZE_CODE_FOR_STUB(codeBlock, patchBuffer, ...) \
118     (adoptRef(new JITStubRoutine(FINALIZE_CODE_FOR((codeBlock), (patchBuffer), __VA_ARGS__))))
119
120 } // namespace JSC
121
122 #endif // ENABLE(JIT)