HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
RE_OGLComputeGPU.h
Go to the documentation of this file.
1 /*
2  * PROPRIETARY INFORMATION. This software is proprietary to
3  * Side Effects Software Inc., and is not to be reproduced,
4  * transmitted, or disclosed in any way without written permission.
5  *
6  * NAME: RE_OGLComputeGPU.h ( RE Library, C++)
7  *
8  * COMMENTS:
9  * A high level interface to allow GP-GPU computing (general purpose
10  * computation on the GPU, or video card). This uses RE_OGLFramebuffer
11  * (output), RE_Textures (array input), and RE_Shaders (GLSL or Cg program)
12  * to perform the computation.
13  *
14  * Setting up the computation is relatively expensive, so this should only
15  * be used for large volumes of data.
16  *
17  * Once you have set up the program, output and input(s), you can change one
18  * or all of them for the next run. If you call setConstant() or setArray()
19  * with the same name as an existing constant or array, the data will be
20  * updated as long as the data format and size remains the same (otherwise
21  * another constant or texture will be created for it).
22  *
23  * You can use special macros to read from the input arrays (which are
24  * textures) using integer indices rather than floating point texture
25  * coords:
26  *
27  * IN_array_name // at current output pos.
28  * ABS_array_name (int_pos) // at an absolute position.
29  * REL_array_name (int_offset) // offset from current pos.
30  *
31  * (Note: 2D Arrays will have 2 pos / offset parms)
32  *
33  * You can use the first version to grab the corresponding input element
34  * only if it matches the output in size and dimensions (1d/2d). Otherwise,
35  * you'll get array bounds issues.
36  */
37 #ifndef RE_OGLComputeGPU_h
38 #define RE_OGLComputeGPU_h
39 
40 #include "RE_API.h"
41 #include "RE_Types.h"
42 #include <PXL/PXL_Common.h>
43 #include <IMG/IMG_FileTypes.h>
44 #include <UT/UT_ComputeGPU.h>
45 
46 class UT_String;
47 class re_GPUConstant;
48 class re_GPUInputArray;
49 class re_GPUFrameBuffer;
50 class re_GPUInputArrayProxy;
51 class re_GPUData;
52 class re_ProgramRun;
53 class re_GPUProgram;
54 class RE_Render;
55 
57 {
58 public:
59  ~RE_OGLComputeGPU() override;
60 
61  /// Initialize RE GPU implementation. This must be called on startup.
62  static void init();
63 
64  static void initStandalone(bool one_per_thread);
65 
66  static RE_Render * getRender();
67 
68  // 0. If you're doing multiple passes, you should set how many passes you
69  // wish to do. This is optional - it defaults to 1 pass.
70  // TODO: This is not supported yet.
71  void setNumPasses(int passes) override;
72 
73  // If enabled, your shader is using integer bit operations. Not all cards
74  // support this.
75  void needBitOps(bool enable) override;
76  bool needsBitOps() const override { return myBitOpsUsed; }
77 
78  // 1. Inputs to computation.
79  // You may rewrite to existing values to begin another computation.
80  // This class does not take ownership of the value array you pass in -
81  // you are responsible for deleting it, but do not do so until compute()
82  // has been called.
83  // The OpenGL texture size limits the maximum array size. 1D Arrays
84  // have a max of this size squared, 2D arrays must have both dimensions
85  // under this size (see RE_OGLRender::getMaxTextureSize()). setArray()
86  // will return nullptr if these limits are exceeeded.
87 
88  // Data types available for I/O
89  // - constants are usually int32's, float32's or matrices.
90  // - input and output arrays cannot be arrays of matrices (currently)
91 
92  // Constants are usually UT_GPU_FLOAT32, UT_GPU_(U)INT32 OR
93  // UT_GPU_MATRIX[n]. They can be a small array, but GLSL will not allow
94  // you to dynamically index them (ie, [x], only [1] or using fixed range
95  // loop variables like x=1 to 10). If you need to dynamically index,
96  // use an Array. Constant arrays are very lightweight, though.
97  void setConstant(const char *name,
99  int vectorsize,
100  const void *value,
101  int array_size = 1,
102  bool global_var = false) override;
103 
104  void * setArray(const char *name,
106  int vectorsize,
107  int size,
108  const void *values) override;
109 
110  void * setArray2D(const char *name,
112  int vectorsize,
113  int width,
114  int height,
115  const void *values) override; // in rows.
116 
117  // flat arrays to vectors (interleaves to 1,2,3,4, 1,2,3,4). Not all
118  // components need to be specified.
119  void * setArray(const char *name,
121  int vectorsize,
122  int size,
123  const void *values1,
124  const void *values2,
125  const void *values3 = nullptr,
126  const void *values4 = nullptr) override;
127 
128  void * setArray2D(const char *name,
130  int vectorsize,
131  int width,
132  int height,
133  const void *values1,
134  const void *values2,
135  const void *values3 = nullptr,
136  const void *values4 = nullptr) override;
137 
138  // 2. Output data.
139  // You can add multiple outputs, but they all must be the same size, type
140  // and vectorsize. 'dest_data' is where the results are written.
141 
142  void setOutputArray(const char *name,
144  int vectorsize,
145  int size,
146  void *dest_data) override;
147 
148  void setOutputArray2D(const char *name,
150  int vectorsize,
151  int width,
152  int height,
153  void *dest_data) override;
154 
155  // Convienience method to determine the size of the array you will need
156  // for an output buffer (or need to provide for an input buffer).
157  // 1D arrays only need to pass xsize.
158  int getDataByteSize(UT_GPUType type, int vectorsize,
159  int xsize, int ysize = 1) override;
160 
161  // 3. GLSL/Cg Program (false if it fails to compile)
162  // 'name' is arbitrary, for debug messages.
163  // 'program' is the actual program code.
164  // If 'auto_generate_framework' is true, this class prepends the GLSL
165  // constant and texture declarations (as named above), then
166  // 'void main(void) {', your code, and then '}' (so all you need to do is
167  // fill in the actual code). If non-nullptr, 'preamble_code' will be
168  // placed before the declarations.
169 
170  void setLanguage(UT_OGLComputeLanguage lang) override;
171 
172  bool setProgram(const char *name,
173  const char *program,
174  bool auto_generate_framework = true,
175  const char *preamble_code = nullptr,
176  const char *function_code = nullptr) override;
177 
178  // This allows you to define macros and symbols for preprocessing.
179  void defineSymbol(const char *symbol,
180  const char *value) override;
181 
182  // 4. Computation
183  // Runs the program on the inputs to produce the output. Returns a
184  // pointer to the result (in the output format and dimensions specified
185  // above). Returns false if an opengl error occured.
186  // Once you have called compute, you may begin another computation
187  // before fetching the results (just go back to step 1).
188 
189  // 'async_read' starts the DMA transfer of the results after the
190  // computation is finshed. Useful when you have more than one output,
191  // or more work to do between compute() and getResult(). Note
192  // that this call will block until the computation is done, so for long
193  // computations, you may want to take the latency hit. If pixel buffer
194  // objects are not supported, this is ignored.
195 
196  bool compute(UT_String &errors, bool async_read = false) override;
197 
198  // 5. Fetch Results
199  // Notify the engine that you'd like to use your results. With multiple
200  // active computations, this removes the oldest and another getResult()
201  // will begin fetching from the next oldest computation.
202  //
203  // Your results will be available _after_ this method is called. This
204  // returns false if your results could not be read.
205  bool getResults() override;
206 
207  // Alternatively, you can use a deferred scheme to retrive the data.
208  // 1. Call deferred fetch to grab a key to the results.
209  // 2. You can optionally call beginDeferredRead() some time afterward
210  // to start the asynchronouse read.
211  // 3. Call endDeferredRead() to ensure that all results have been read.
212  // The key is no longer valid after step 3.
213 
214  void *useDeferredFetch() override;
215 
216 private:
218 
219  /// Create a new RE_OGLComputeGPU object.
220  /// The caller takes ownership of the returned object and is responsible
221  /// for deleting it.
222  static UT_ComputeGPU *create();
223 
224  bool initFrameBuffers(RE_Render *r);
225 
226  re_ProgramRun *myProgram;
227  bool myProgramRunFlag;
228  bool myBitOpsUsed;
229 };
230 
232 {
233 public:
234  ~RE_OGLComputeGPUState() override;
235 
236  /// Initialize RE GPU implementation. This must be called on startup.
237  static void init();
238 
239  void initStandalone(bool one_per_thread = true) override;
240  void cleanupStandalone() override;
241  virtual RE_Render *getRender();
242  void getGLSLComputeDir(UT_String &dir) override;
243 
244  // Returns true if the graphics hardware has proper support to use this
245  // class.
246  bool hasGPUSupport() override;
247 
248  bool areBitOpsSupported() override;
249 
250  void beginDeferredRead(void *key) override;
251  bool endDeferredRead(void *key) override;
252  void cancelDeferredRead(void *key) override;
253 
254  // Returns true if texture rectangles must be used (because standard 2D
255  // textures do not support most higher formats on some hardware)
256  bool useTextureRectangles() override;
257 
258  // The largest sizes that this GPU can handle.
259  int getMaxArraySize() override;
260  int getMaxArraySize2D() override;
261 
262  // Clears all the GP-GPU allocated objects. You don't normally need to
263  // call this.
264  void reset() override;
265 
266  void restoreState() override;
267  void cleanupState() override;
268 
269 private:
271 };
272 
273 #endif
bool needsBitOps() const override
virtual void * setArray(const char *name, UT_GPUType type, int vectorsize, int size, const void *values)=0
#define RE_API
Definition: RE_API.h:10
virtual void * setArray2D(const char *name, UT_GPUType type, int vectorsize, int width, int height, const void *values)=0
virtual bool hasGPUSupport()
virtual int getMaxArraySize()
virtual bool areBitOpsSupported()
virtual void reset()
virtual int getMaxArraySize2D()
virtual void cleanupState()
static UT_ComputeGPU * create()
virtual bool compute(UT_String &errors, bool async_read=false)=0
virtual void setConstant(const char *name, UT_GPUType type, int vectorsize, const void *value, int array_size=1, bool global_var=false)=0
virtual void getGLSLComputeDir(UT_String &dir)
virtual void initStandalone(bool one_per_thread=true)
UT_GPUType
Definition: UT_ComputeGPU.h:42
GLint GLsizei GLsizei height
Definition: glcorearb.h:103
virtual void cancelDeferredRead(void *key)
virtual void restoreState()
virtual void defineSymbol(const char *symbol, const char *value)=0
virtual void setOutputArray2D(const char *name, UT_GPUType type, int vectorsize, int width, int height, void *dest_data)=0
GLuint const GLchar * name
Definition: glcorearb.h:786
virtual bool setProgram(const char *name, const char *program, bool auto_generate_framework=true, const char *preamble_code=0, const char *function_code=0)=0
virtual void needBitOps(bool enable)=0
virtual void cleanupStandalone()
virtual void setNumPasses(int passes)=0
virtual void setLanguage(UT_OGLComputeLanguage lang)=0
virtual bool endDeferredRead(void *key)
GLsizeiptr size
Definition: glcorearb.h:664
virtual void setOutputArray(const char *name, UT_GPUType type, int vectorsize, int size, void *dest_data)=0
virtual void beginDeferredRead(void *key)
virtual int getDataByteSize(UT_GPUType type, int vectorsize, int xsize, int ysize=1)=0
GLenum GLsizei GLsizei GLint * values
Definition: glcorearb.h:1602
GLint GLsizei width
Definition: glcorearb.h:103
Definition: core.h:1131
GLboolean r
Definition: glcorearb.h:1222
type
Definition: core.h:1059
virtual bool useTextureRectangles()
GLbitfield GLuint program
Definition: glcorearb.h:1931
virtual bool getResults()=0
virtual void * useDeferredFetch()=0