gpu_static_inst.hh revision 11692:e772fdcd3809
1/*
2 * Copyright (c) 2015 Advanced Micro Devices, Inc.
3 * All rights reserved.
4 *
5 * For use for simulation and test purposes only
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions are met:
9 *
10 * 1. Redistributions of source code must retain the above copyright notice,
11 * this list of conditions and the following disclaimer.
12 *
13 * 2. Redistributions in binary form must reproduce the above copyright notice,
14 * this list of conditions and the following disclaimer in the documentation
15 * and/or other materials provided with the distribution.
16 *
17 * 3. Neither the name of the copyright holder nor the names of its contributors
18 * may be used to endorse or promote products derived from this software
19 * without specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
22 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
25 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
29 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31 * POSSIBILITY OF SUCH DAMAGE.
32 *
33 * Author: Anthony Gutierrez
34 */
35
36#ifndef __GPU_STATIC_INST_HH__
37#define __GPU_STATIC_INST_HH__
38
39/*
40 * @file gpu_static_inst.hh
41 *
42 * Defines the base class representing static instructions for the GPU. The
43 * instructions are "static" because they contain no dynamic instruction
44 * information. GPUStaticInst corresponds to the StaticInst class for the CPU
45 * models.
46 */
47
48#include <cstdint>
49#include <string>
50
51#include "enums/GPUStaticInstFlags.hh"
52#include "enums/StorageClassType.hh"
53#include "gpu-compute/gpu_dyn_inst.hh"
54#include "gpu-compute/misc.hh"
55
56class BaseOperand;
57class BaseRegOperand;
58class Wavefront;
59
60class GPUStaticInst : public GPUStaticInstFlags
61{
62  public:
63    GPUStaticInst(const std::string &opcode);
64
65    void instNum(int num) { _instNum = num; }
66
67    int instNum() { return _instNum;  }
68
69    void ipdInstNum(int num) { _ipdInstNum = num; }
70
71    int ipdInstNum() const { return _ipdInstNum; }
72
73    virtual void execute(GPUDynInstPtr gpuDynInst) = 0;
74    virtual void generateDisassembly() = 0;
75    const std::string& disassemble();
76    virtual int getNumOperands() = 0;
77    virtual bool isCondRegister(int operandIndex) = 0;
78    virtual bool isScalarRegister(int operandIndex) = 0;
79    virtual bool isVectorRegister(int operandIndex) = 0;
80    virtual bool isSrcOperand(int operandIndex) = 0;
81    virtual bool isDstOperand(int operandIndex) = 0;
82    virtual int getOperandSize(int operandIndex) = 0;
83    virtual int getRegisterIndex(int operandIndex) = 0;
84    virtual int numDstRegOperands() = 0;
85    virtual int numSrcRegOperands() = 0;
86
87    virtual bool isValid() const = 0;
88
89    bool isALU() const { return _flags[ALU]; }
90    bool isBranch() const { return _flags[Branch]; }
91    bool isNop() const { return _flags[Nop]; }
92    bool isReturn() const { return _flags[Return]; }
93
94    bool
95    isUnconditionalJump() const
96    {
97        return _flags[UnconditionalJump];
98    }
99
100    bool isSpecialOp() const { return _flags[SpecialOp]; }
101    bool isWaitcnt() const { return _flags[Waitcnt]; }
102
103    bool isBarrier() const { return _flags[MemBarrier]; }
104    bool isMemFence() const { return _flags[MemFence]; }
105    bool isMemRef() const { return _flags[MemoryRef]; }
106    bool isFlat() const { return _flags[Flat]; }
107    bool isLoad() const { return _flags[Load]; }
108    bool isStore() const { return _flags[Store]; }
109
110    bool
111    isAtomic() const
112    {
113        return _flags[AtomicReturn] || _flags[AtomicNoReturn];
114    }
115
116    bool isAtomicNoRet() const { return _flags[AtomicNoReturn]; }
117    bool isAtomicRet() const { return _flags[AtomicReturn]; }
118
119    bool isScalar() const { return _flags[Scalar]; }
120    bool readsSCC() const { return _flags[ReadsSCC]; }
121    bool writesSCC() const { return _flags[WritesSCC]; }
122    bool readsVCC() const { return _flags[ReadsVCC]; }
123    bool writesVCC() const { return _flags[WritesVCC]; }
124
125    bool isAtomicAnd() const { return _flags[AtomicAnd]; }
126    bool isAtomicOr() const { return _flags[AtomicOr]; }
127    bool isAtomicXor() const { return _flags[AtomicXor]; }
128    bool isAtomicCAS() const { return _flags[AtomicCAS]; }
129    bool isAtomicExch() const { return _flags[AtomicExch]; }
130    bool isAtomicAdd() const { return _flags[AtomicAdd]; }
131    bool isAtomicSub() const { return _flags[AtomicSub]; }
132    bool isAtomicInc() const { return _flags[AtomicInc]; }
133    bool isAtomicDec() const { return _flags[AtomicDec]; }
134    bool isAtomicMax() const { return _flags[AtomicMax]; }
135    bool isAtomicMin() const { return _flags[AtomicMin]; }
136
137    bool
138    isArgLoad() const
139    {
140        return (_flags[KernArgSegment] || _flags[ArgSegment]) && _flags[Load];
141    }
142
143    bool
144    isGlobalMem() const
145    {
146        return _flags[MemoryRef] && (_flags[GlobalSegment] ||
147               _flags[PrivateSegment] || _flags[ReadOnlySegment] ||
148               _flags[SpillSegment]);
149    }
150
151    bool
152    isLocalMem() const
153    {
154        return _flags[MemoryRef] && _flags[GroupSegment];
155    }
156
157    bool isArgSeg() const { return _flags[ArgSegment]; }
158    bool isGlobalSeg() const { return _flags[GlobalSegment]; }
159    bool isGroupSeg() const { return _flags[GroupSegment]; }
160    bool isKernArgSeg() const { return _flags[KernArgSegment]; }
161    bool isPrivateSeg() const { return _flags[PrivateSegment]; }
162    bool isReadOnlySeg() const { return _flags[ReadOnlySegment]; }
163    bool isSpillSeg() const { return _flags[SpillSegment]; }
164
165    bool isWorkitemScope() const { return _flags[WorkitemScope]; }
166    bool isWavefrontScope() const { return _flags[WavefrontScope]; }
167    bool isWorkgroupScope() const { return _flags[WorkgroupScope]; }
168    bool isDeviceScope() const { return _flags[DeviceScope]; }
169    bool isSystemScope() const { return _flags[SystemScope]; }
170    bool isNoScope() const { return _flags[NoScope]; }
171
172    bool isRelaxedOrder() const { return _flags[RelaxedOrder]; }
173    bool isAcquire() const { return _flags[Acquire]; }
174    bool isRelease() const { return _flags[Release]; }
175    bool isAcquireRelease() const { return _flags[AcquireRelease]; }
176    bool isNoOrder() const { return _flags[NoOrder]; }
177
178    /**
179     * Coherence domain of a memory instruction. Only valid for
180     * machine ISA. The coherence domain specifies where it is
181     * possible to perform memory synchronization, e.g., acquire
182     * or release, from the shader kernel.
183     *
184     * isGloballyCoherent(): returns true if kernel is sharing memory
185     * with other work-items on the same device (GPU)
186     *
187     * isSystemCoherent(): returns true if kernel is sharing memory
188     * with other work-items on a different device (GPU) or the host (CPU)
189     */
190    bool isGloballyCoherent() const { return _flags[GloballyCoherent]; }
191    bool isSystemCoherent() const { return _flags[SystemCoherent]; }
192
193    virtual uint32_t instSize() = 0;
194
195    // only used for memory instructions
196    virtual void
197    initiateAcc(GPUDynInstPtr gpuDynInst)
198    {
199        fatal("calling initiateAcc() on a non-memory instruction.\n");
200    }
201
202    // only used for memory instructions
203    virtual void
204    completeAcc(GPUDynInstPtr gpuDynInst)
205    {
206        fatal("calling completeAcc() on a non-memory instruction.\n");
207    }
208
209    virtual uint32_t getTargetPc() { return 0; }
210
211    static uint64_t dynamic_id_count;
212
213    // For flat memory accesses
214    Enums::StorageClassType executed_as;
215
216    void setFlag(Flags flag) { _flags[flag] = true; }
217
218  protected:
219    virtual void
220    execLdAcq(GPUDynInstPtr gpuDynInst)
221    {
222        fatal("calling execLdAcq() on a non-load instruction.\n");
223    }
224
225    virtual void
226    execSt(GPUDynInstPtr gpuDynInst)
227    {
228        fatal("calling execLdAcq() on a non-load instruction.\n");
229    }
230
231    virtual void
232    execAtomic(GPUDynInstPtr gpuDynInst)
233    {
234        fatal("calling execAtomic() on a non-atomic instruction.\n");
235    }
236
237    virtual void
238    execAtomicAcq(GPUDynInstPtr gpuDynInst)
239    {
240        fatal("calling execAtomicAcq() on a non-atomic instruction.\n");
241    }
242
243    const std::string opcode;
244    std::string disassembly;
245    int _instNum;
246    /**
247     * Identifier of the immediate post-dominator instruction.
248     */
249    int _ipdInstNum;
250
251    std::bitset<Num_Flags> _flags;
252};
253
254class KernelLaunchStaticInst : public GPUStaticInst
255{
256  public:
257    KernelLaunchStaticInst() : GPUStaticInst("kernel_launch")
258    {
259        setFlag(Nop);
260        setFlag(Scalar);
261        setFlag(Acquire);
262        setFlag(SystemScope);
263        setFlag(GlobalSegment);
264    }
265
266    void
267    execute(GPUDynInstPtr gpuDynInst)
268    {
269        fatal("kernel launch instruction should not be executed\n");
270    }
271
272    void
273    generateDisassembly()
274    {
275        disassembly = opcode;
276    }
277
278    int getNumOperands() { return 0; }
279    bool isCondRegister(int operandIndex) { return false; }
280    bool isScalarRegister(int operandIndex) { return false; }
281    bool isVectorRegister(int operandIndex) { return false; }
282    bool isSrcOperand(int operandIndex) { return false; }
283    bool isDstOperand(int operandIndex) { return false; }
284    int getOperandSize(int operandIndex) { return 0; }
285    int getRegisterIndex(int operandIndex) { return 0; }
286    int numDstRegOperands() { return 0; }
287    int numSrcRegOperands() { return 0; }
288    bool isValid() const { return true; }
289    uint32_t instSize() { return 0; }
290};
291
292#endif // __GPU_STATIC_INST_HH__
293