Home | History | Annotate | Download | only in gpu
      1 /*
      2  * Copyright 2011 Google Inc.
      3  *
      4  * Use of this source code is governed by a BSD-style license that can be
      5  * found in the LICENSE file.
      6  */
      7 
      8 #ifndef GrGpu_DEFINED
      9 #define GrGpu_DEFINED
     10 
     11 #include "GrDrawTarget.h"
     12 #include "GrClipMaskManager.h"
     13 #include "SkPath.h"
     14 
     15 class GrContext;
     16 class GrGpuObject;
     17 class GrIndexBufferAllocPool;
     18 class GrPath;
     19 class GrPathRenderer;
     20 class GrPathRendererChain;
     21 class GrStencilBuffer;
     22 class GrVertexBufferAllocPool;
     23 
     24 class GrGpu : public GrDrawTarget {
     25 public:
     26 
     27     /**
     28      * Additional blend coefficients for dual source blending, not exposed
     29      * through GrPaint/GrContext.
     30      */
     31     enum ExtendedBlendCoeffs {
     32         // source 2 refers to second output color when
     33         // using dual source blending.
     34         kS2C_GrBlendCoeff = kPublicGrBlendCoeffCount,
     35         kIS2C_GrBlendCoeff,
     36         kS2A_GrBlendCoeff,
     37         kIS2A_GrBlendCoeff,
     38 
     39         kTotalGrBlendCoeffCount
     40     };
     41 
     42     /**
     43      * Create an instance of GrGpu that matches the specified backend. If the requested backend is
     44      * not supported (at compile-time or run-time) this returns NULL. The context will not be
     45      * fully constructed and should not be used by GrGpu until after this function returns.
     46      */
     47     static GrGpu* Create(GrBackend, GrBackendContext, GrContext* context);
     48 
     49     ////////////////////////////////////////////////////////////////////////////
     50 
     51     GrGpu(GrContext* context);
     52     virtual ~GrGpu();
     53 
     54     GrContext* getContext() { return this->INHERITED::getContext(); }
     55     const GrContext* getContext() const { return this->INHERITED::getContext(); }
     56 
     57     /**
     58      * The GrGpu object normally assumes that no outsider is setting state
     59      * within the underlying 3D API's context/device/whatever. This call informs
     60      * the GrGpu that the state was modified and it shouldn't make assumptions
     61      * about the state.
     62      */
     63     void markContextDirty(uint32_t state = kAll_GrBackendState) {
     64         fResetBits |= state;
     65     }
     66 
     67     void unimpl(const char[]);
     68 
     69     /**
     70      * Creates a texture object. If desc width or height is not a power of
     71      * two but underlying API requires a power of two texture then srcData
     72      * will be embedded in a power of two texture. The extra width and height
     73      * is filled as though srcData were rendered clamped into the texture.
     74      * The exception is when using compressed data formats. In this case, the
     75      * desc width and height must be a multiple of the compressed format block
     76      * size otherwise this function returns NULL. Similarly, if the underlying
     77      * API requires a power of two texture and the source width and height are not
     78      * a power of two, then this function returns NULL.
     79      *
     80      * If kRenderTarget_TextureFlag is specified the GrRenderTarget is
     81      * accessible via GrTexture::asRenderTarget(). The texture will hold a ref
     82      * on the render target until the texture is destroyed. Compressed textures
     83      * cannot have the kRenderTarget_TextureFlag set.
     84      *
     85      * @param desc        describes the texture to be created.
     86      * @param srcData     texel data to load texture. Begins with full-size
     87      *                    palette data for paletted textures. For compressed
     88      *                    formats it contains the compressed pixel data. Otherwise,
     89      *                    it contains width*height texels. If NULL texture data
     90      *                    is uninitialized.
     91      * @param rowBytes    the number of bytes between consecutive rows. Zero
     92      *                    means rows are tightly packed. This field is ignored
     93      *                    for compressed formats.
     94      *
     95      * @return    The texture object if successful, otherwise NULL.
     96      */
     97     GrTexture* createTexture(const GrTextureDesc& desc,
     98                              const void* srcData, size_t rowBytes);
     99 
    100     /**
    101      * Implements GrContext::wrapBackendTexture
    102      */
    103     GrTexture* wrapBackendTexture(const GrBackendTextureDesc&);
    104 
    105     /**
    106      * Implements GrContext::wrapBackendTexture
    107      */
    108     GrRenderTarget* wrapBackendRenderTarget(const GrBackendRenderTargetDesc&);
    109 
    110     /**
    111      * Creates a vertex buffer.
    112      *
    113      * @param size    size in bytes of the vertex buffer
    114      * @param dynamic hints whether the data will be frequently changed
    115      *                by either GrVertexBuffer::map() or
    116      *                GrVertexBuffer::updateData().
    117      *
    118      * @return    The vertex buffer if successful, otherwise NULL.
    119      */
    120     GrVertexBuffer* createVertexBuffer(size_t size, bool dynamic);
    121 
    122     /**
    123      * Creates an index buffer.
    124      *
    125      * @param size    size in bytes of the index buffer
    126      * @param dynamic hints whether the data will be frequently changed
    127      *                by either GrIndexBuffer::map() or
    128      *                GrIndexBuffer::updateData().
    129      *
    130      * @return The index buffer if successful, otherwise NULL.
    131      */
    132     GrIndexBuffer* createIndexBuffer(size_t size, bool dynamic);
    133 
    134     /**
    135      * Creates a path object that can be stenciled using stencilPath(). It is
    136      * only legal to call this if the caps report support for path stenciling.
    137      */
    138     GrPath* createPath(const SkPath& path, const SkStrokeRec& stroke);
    139 
    140     /**
    141      * Returns an index buffer that can be used to render quads.
    142      * Six indices per quad: 0, 1, 2, 0, 2, 3, etc.
    143      * The max number of quads can be queried using GrIndexBuffer::maxQuads().
    144      * Draw with kTriangles_GrPrimitiveType
    145      * @ return the quad index buffer
    146      */
    147     const GrIndexBuffer* getQuadIndexBuffer() const;
    148 
    149     /**
    150      * Resolves MSAA.
    151      */
    152     void resolveRenderTarget(GrRenderTarget* target);
    153 
    154     /**
    155      * Gets a preferred 8888 config to use for writing/reading pixel data to/from a surface with
    156      * config surfaceConfig. The returned config must have at least as many bits per channel as the
    157      * readConfig or writeConfig param.
    158      */
    159     virtual GrPixelConfig preferredReadPixelsConfig(GrPixelConfig readConfig,
    160                                                     GrPixelConfig surfaceConfig) const {
    161         return readConfig;
    162     }
    163     virtual GrPixelConfig preferredWritePixelsConfig(GrPixelConfig writeConfig,
    164                                                      GrPixelConfig surfaceConfig) const {
    165         return writeConfig;
    166     }
    167 
    168     /**
    169      * Called before uploading writing pixels to a GrTexture when the src pixel config doesn't
    170      * match the texture's config.
    171      */
    172     virtual bool canWriteTexturePixels(const GrTexture*, GrPixelConfig srcConfig) const = 0;
    173 
    174     /**
    175      * OpenGL's readPixels returns the result bottom-to-top while the skia
    176      * API is top-to-bottom. Thus we have to do a y-axis flip. The obvious
    177      * solution is to have the subclass do the flip using either the CPU or GPU.
    178      * However, the caller (GrContext) may have transformations to apply and can
    179      * simply fold in the y-flip for free. On the other hand, the subclass may
    180      * be able to do it for free itself. For example, the subclass may have to
    181      * do memcpys to handle rowBytes that aren't tight. It could do the y-flip
    182      * concurrently.
    183      *
    184      * This function returns true if a y-flip is required to put the pixels in
    185      * top-to-bottom order and the subclass cannot do it for free.
    186      *
    187      * See read pixels for the params
    188      * @return true if calling readPixels with the same set of params will
    189      *              produce bottom-to-top data
    190      */
    191      virtual bool readPixelsWillPayForYFlip(GrRenderTarget* renderTarget,
    192                                             int left, int top,
    193                                             int width, int height,
    194                                             GrPixelConfig config,
    195                                             size_t rowBytes) const = 0;
    196      /**
    197       * This should return true if reading a NxM rectangle of pixels from a
    198       * render target is faster if the target has dimensons N and M and the read
    199       * rectangle has its top-left at 0,0.
    200       */
    201      virtual bool fullReadPixelsIsFasterThanPartial() const { return false; };
    202 
    203     /**
    204      * Reads a rectangle of pixels from a render target.
    205      *
    206      * @param renderTarget  the render target to read from. NULL means the
    207      *                      current render target.
    208      * @param left          left edge of the rectangle to read (inclusive)
    209      * @param top           top edge of the rectangle to read (inclusive)
    210      * @param width         width of rectangle to read in pixels.
    211      * @param height        height of rectangle to read in pixels.
    212      * @param config        the pixel config of the destination buffer
    213      * @param buffer        memory to read the rectangle into.
    214      * @param rowBytes      the number of bytes between consecutive rows. Zero
    215      *                      means rows are tightly packed.
    216      * @param invertY       buffer should be populated bottom-to-top as opposed
    217      *                      to top-to-bottom (skia's usual order)
    218      *
    219      * @return true if the read succeeded, false if not. The read can fail
    220      *              because of a unsupported pixel config or because no render
    221      *              target is currently set.
    222      */
    223     bool readPixels(GrRenderTarget* renderTarget,
    224                     int left, int top, int width, int height,
    225                     GrPixelConfig config, void* buffer, size_t rowBytes);
    226 
    227     /**
    228      * Updates the pixels in a rectangle of a texture.
    229      *
    230      * @param left          left edge of the rectangle to write (inclusive)
    231      * @param top           top edge of the rectangle to write (inclusive)
    232      * @param width         width of rectangle to write in pixels.
    233      * @param height        height of rectangle to write in pixels.
    234      * @param config        the pixel config of the source buffer
    235      * @param buffer        memory to read pixels from
    236      * @param rowBytes      number of bytes between consecutive rows. Zero
    237      *                      means rows are tightly packed.
    238      */
    239     bool writeTexturePixels(GrTexture* texture,
    240                             int left, int top, int width, int height,
    241                             GrPixelConfig config, const void* buffer,
    242                             size_t rowBytes);
    243 
    244     /**
    245      * Called to tell GrGpu that all GrGpuObjects have been lost and should
    246      * be abandoned. Overrides must call INHERITED::abandonResources().
    247      */
    248     virtual void abandonResources();
    249 
    250     /**
    251      * Called to tell GrGpu to release all GrGpuObjects. Overrides must call
    252      * INHERITED::releaseResources().
    253      */
    254     void releaseResources();
    255 
    256     /**
    257      * Add object to list of objects. Should only be called by GrGpuObject.
    258      * @param resource  the resource to add.
    259      */
    260     void insertObject(GrGpuObject* object);
    261 
    262     /**
    263      * Remove object from list of objects. Should only be called by GrGpuObject.
    264      * @param resource  the resource to remove.
    265      */
    266     void removeObject(GrGpuObject* object);
    267 
    268     // GrDrawTarget overrides
    269     virtual void clear(const SkIRect* rect,
    270                        GrColor color,
    271                        bool canIgnoreRect,
    272                        GrRenderTarget* renderTarget = NULL) SK_OVERRIDE;
    273 
    274     virtual void purgeResources() SK_OVERRIDE {
    275         // The clip mask manager can rebuild all its clip masks so just
    276         // get rid of them all.
    277         fClipMaskManager.releaseResources();
    278     }
    279 
    280     // After the client interacts directly with the 3D context state the GrGpu
    281     // must resync its internal state and assumptions about 3D context state.
    282     // Each time this occurs the GrGpu bumps a timestamp.
    283     // state of the 3D context
    284     // At 10 resets / frame and 60fps a 64bit timestamp will overflow in about
    285     // a billion years.
    286     typedef uint64_t ResetTimestamp;
    287 
    288     // This timestamp is always older than the current timestamp
    289     static const ResetTimestamp kExpiredTimestamp = 0;
    290     // Returns a timestamp based on the number of times the context was reset.
    291     // This timestamp can be used to lazily detect when cached 3D context state
    292     // is dirty.
    293     ResetTimestamp getResetTimestamp() const {
    294         return fResetTimestamp;
    295     }
    296 
    297     /**
    298      * These methods are called by the clip manager's setupClipping function
    299      * which (called as part of GrGpu's implementation of onDraw and
    300      * onStencilPath member functions.) The GrGpu subclass should flush the
    301      * stencil state to the 3D API in its implementation of flushGraphicsState.
    302      */
    303     void enableScissor(const SkIRect& rect) {
    304         fScissorState.fEnabled = true;
    305         fScissorState.fRect = rect;
    306     }
    307     void disableScissor() { fScissorState.fEnabled = false; }
    308 
    309     /**
    310      * Like the scissor methods above this is called by setupClipping and
    311      * should be flushed by the GrGpu subclass in flushGraphicsState. These
    312      * stencil settings should be used in place of those on the GrDrawState.
    313      * They have been adjusted to account for any interactions between the
    314      * GrDrawState's stencil settings and stencil clipping.
    315      */
    316     void setStencilSettings(const GrStencilSettings& settings) {
    317         fStencilSettings = settings;
    318     }
    319     void disableStencil() { fStencilSettings.setDisabled(); }
    320 
    321     // GrGpu subclass sets clip bit in the stencil buffer. The subclass is
    322     // free to clear the remaining bits to zero if masked clears are more
    323     // expensive than clearing all bits.
    324     virtual void clearStencilClip(const SkIRect& rect, bool insideClip) = 0;
    325 
    326     enum PrivateDrawStateStateBits {
    327         kFirstBit = (GrDrawState::kLastPublicStateBit << 1),
    328 
    329         kModifyStencilClip_StateBit = kFirstBit, // allows draws to modify
    330                                                  // stencil bits used for
    331                                                  // clipping.
    332     };
    333 
    334     void getPathStencilSettingsForFillType(SkPath::FillType fill, GrStencilSettings* outStencilSettings);
    335 
    336     enum DrawType {
    337         kDrawPoints_DrawType,
    338         kDrawLines_DrawType,
    339         kDrawTriangles_DrawType,
    340         kStencilPath_DrawType,
    341         kDrawPath_DrawType,
    342         kDrawPaths_DrawType,
    343     };
    344 
    345 protected:
    346     DrawType PrimTypeToDrawType(GrPrimitiveType type) {
    347         switch (type) {
    348             case kTriangles_GrPrimitiveType:
    349             case kTriangleStrip_GrPrimitiveType:
    350             case kTriangleFan_GrPrimitiveType:
    351                 return kDrawTriangles_DrawType;
    352             case kPoints_GrPrimitiveType:
    353                 return kDrawPoints_DrawType;
    354             case kLines_GrPrimitiveType:
    355             case kLineStrip_GrPrimitiveType:
    356                 return kDrawLines_DrawType;
    357             default:
    358                 SkFAIL("Unexpected primitive type");
    359                 return kDrawTriangles_DrawType;
    360         }
    361     }
    362 
    363     // prepares clip flushes gpu state before a draw
    364     bool setupClipAndFlushState(DrawType,
    365                                 const GrDeviceCoordTexture* dstCopy,
    366                                 GrDrawState::AutoRestoreEffects* are,
    367                                 const SkRect* devBounds);
    368 
    369     // Functions used to map clip-respecting stencil tests into normal
    370     // stencil funcs supported by GPUs.
    371     static GrStencilFunc ConvertStencilFunc(bool stencilInClip,
    372                                             GrStencilFunc func);
    373     static void ConvertStencilFuncAndMask(GrStencilFunc func,
    374                                           bool clipInStencil,
    375                                           unsigned int clipBit,
    376                                           unsigned int userBits,
    377                                           unsigned int* ref,
    378                                           unsigned int* mask);
    379 
    380     GrClipMaskManager           fClipMaskManager;
    381 
    382     struct GeometryPoolState {
    383         const GrVertexBuffer* fPoolVertexBuffer;
    384         int                   fPoolStartVertex;
    385 
    386         const GrIndexBuffer*  fPoolIndexBuffer;
    387         int                   fPoolStartIndex;
    388     };
    389     const GeometryPoolState& getGeomPoolState() {
    390         return fGeomPoolStateStack.back();
    391     }
    392 
    393     // The state of the scissor is controlled by the clip manager
    394     struct ScissorState {
    395         bool    fEnabled;
    396         SkIRect fRect;
    397     } fScissorState;
    398 
    399     // The final stencil settings to use as determined by the clip manager.
    400     GrStencilSettings fStencilSettings;
    401 
    402     // Helpers for setting up geometry state
    403     void finalizeReservedVertices();
    404     void finalizeReservedIndices();
    405 
    406 private:
    407     // GrDrawTarget overrides
    408     virtual bool onReserveVertexSpace(size_t vertexSize, int vertexCount, void** vertices) SK_OVERRIDE;
    409     virtual bool onReserveIndexSpace(int indexCount, void** indices) SK_OVERRIDE;
    410     virtual void releaseReservedVertexSpace() SK_OVERRIDE;
    411     virtual void releaseReservedIndexSpace() SK_OVERRIDE;
    412     virtual void onSetVertexSourceToArray(const void* vertexArray, int vertexCount) SK_OVERRIDE;
    413     virtual void onSetIndexSourceToArray(const void* indexArray, int indexCount) SK_OVERRIDE;
    414     virtual void releaseVertexArray() SK_OVERRIDE;
    415     virtual void releaseIndexArray() SK_OVERRIDE;
    416     virtual void geometrySourceWillPush() SK_OVERRIDE;
    417     virtual void geometrySourceWillPop(const GeometrySrcState& restoredState) SK_OVERRIDE;
    418 
    419 
    420     // called when the 3D context state is unknown. Subclass should emit any
    421     // assumed 3D context state and dirty any state cache.
    422     virtual void onResetContext(uint32_t resetBits) = 0;
    423 
    424     // overridden by backend-specific derived class to create objects.
    425     virtual GrTexture* onCreateTexture(const GrTextureDesc& desc,
    426                                        const void* srcData,
    427                                        size_t rowBytes) = 0;
    428     virtual GrTexture* onCreateCompressedTexture(const GrTextureDesc& desc,
    429                                                  const void* srcData) = 0;
    430     virtual GrTexture* onWrapBackendTexture(const GrBackendTextureDesc&) = 0;
    431     virtual GrRenderTarget* onWrapBackendRenderTarget(const GrBackendRenderTargetDesc&) = 0;
    432     virtual GrVertexBuffer* onCreateVertexBuffer(size_t size, bool dynamic) = 0;
    433     virtual GrIndexBuffer* onCreateIndexBuffer(size_t size, bool dynamic) = 0;
    434     virtual GrPath* onCreatePath(const SkPath& path, const SkStrokeRec&) = 0;
    435 
    436     // overridden by backend-specific derived class to perform the clear and
    437     // clearRect. NULL rect means clear whole target. If canIgnoreRect is
    438     // true, it is okay to perform a full clear instead of a partial clear
    439     virtual void onClear(const SkIRect* rect, GrColor color, bool canIgnoreRect) = 0;
    440 
    441     // overridden by backend-specific derived class to perform the draw call.
    442     virtual void onGpuDraw(const DrawInfo&) = 0;
    443 
    444     // overridden by backend-specific derived class to perform the path stenciling.
    445     virtual void onGpuStencilPath(const GrPath*, SkPath::FillType) = 0;
    446     virtual void onGpuDrawPath(const GrPath*, SkPath::FillType) = 0;
    447     virtual void onGpuDrawPaths(int, const GrPath**, const SkMatrix*,
    448                                 SkPath::FillType, SkStrokeRec::Style) = 0;
    449 
    450     // overridden by backend-specific derived class to perform the read pixels.
    451     virtual bool onReadPixels(GrRenderTarget* target,
    452                               int left, int top, int width, int height,
    453                               GrPixelConfig,
    454                               void* buffer,
    455                               size_t rowBytes) = 0;
    456 
    457     // overridden by backend-specific derived class to perform the texture update
    458     virtual bool onWriteTexturePixels(GrTexture* texture,
    459                                       int left, int top, int width, int height,
    460                                       GrPixelConfig config, const void* buffer,
    461                                       size_t rowBytes) = 0;
    462 
    463     // overridden by backend-specific derived class to perform the resolve
    464     virtual void onResolveRenderTarget(GrRenderTarget* target) = 0;
    465 
    466     // width and height may be larger than rt (if underlying API allows it).
    467     // Should attach the SB to the RT. Returns false if compatible sb could
    468     // not be created.
    469     virtual bool createStencilBufferForRenderTarget(GrRenderTarget*, int width, int height) = 0;
    470 
    471     // attaches an existing SB to an existing RT.
    472     virtual bool attachStencilBufferToRenderTarget(GrStencilBuffer*, GrRenderTarget*) = 0;
    473 
    474     // The GrGpu typically records the clients requested state and then flushes
    475     // deltas from previous state at draw time. This function does the
    476     // backend-specific flush of the state.
    477     // returns false if current state is unsupported.
    478     virtual bool flushGraphicsState(DrawType, const GrDeviceCoordTexture* dstCopy) = 0;
    479 
    480     // clears the entire stencil buffer to 0
    481     virtual void clearStencil() = 0;
    482 
    483     // Given a rt, find or create a stencil buffer and attach it
    484     bool attachStencilBufferToRenderTarget(GrRenderTarget* target);
    485 
    486     // GrDrawTarget overrides
    487     virtual void onDraw(const DrawInfo&) SK_OVERRIDE;
    488     virtual void onStencilPath(const GrPath*, SkPath::FillType) SK_OVERRIDE;
    489     virtual void onDrawPath(const GrPath*, SkPath::FillType,
    490                             const GrDeviceCoordTexture* dstCopy) SK_OVERRIDE;
    491     virtual void onDrawPaths(int, const GrPath**, const SkMatrix*,
    492                              SkPath::FillType, SkStrokeRec::Style,
    493                              const GrDeviceCoordTexture* dstCopy) SK_OVERRIDE;
    494 
    495     // readies the pools to provide vertex/index data.
    496     void prepareVertexPool();
    497     void prepareIndexPool();
    498 
    499     void resetContext() {
    500         // We call this because the client may have messed with the
    501         // stencil buffer. Perhaps we should detect whether it is a
    502         // internally created stencil buffer and if so skip the invalidate.
    503         fClipMaskManager.invalidateStencilMask();
    504         this->onResetContext(fResetBits);
    505         fResetBits = 0;
    506         ++fResetTimestamp;
    507     }
    508 
    509     void handleDirtyContext() {
    510         if (fResetBits) {
    511             this->resetContext();
    512         }
    513     }
    514 
    515     enum {
    516         kPreallocGeomPoolStateStackCnt = 4,
    517     };
    518     typedef SkTInternalLList<GrGpuObject> ObjectList;
    519     SkSTArray<kPreallocGeomPoolStateStackCnt, GeometryPoolState, true>  fGeomPoolStateStack;
    520     ResetTimestamp                                                      fResetTimestamp;
    521     uint32_t                                                            fResetBits;
    522     GrVertexBufferAllocPool*                                            fVertexPool;
    523     GrIndexBufferAllocPool*                                             fIndexPool;
    524     // counts number of uses of vertex/index pool in the geometry stack
    525     int                                                                 fVertexPoolUseCnt;
    526     int                                                                 fIndexPoolUseCnt;
    527     // these are mutable so they can be created on-demand
    528     mutable GrIndexBuffer*                                              fQuadIndexBuffer;
    529     // Used to abandon/release all resources created by this GrGpu. TODO: Move this
    530     // functionality to GrResourceCache.
    531     ObjectList                                                          fObjectList;
    532 
    533     typedef GrDrawTarget INHERITED;
    534 };
    535 
    536 #endif
    537