Home | History | Annotate | Download | only in d3d9
      1 #include "precompiled.h"
      2 //
      3 // Copyright (c) 2013 The ANGLE Project Authors. All rights reserved.
      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 // Query9.cpp: Defines the rx::Query9 class which implements rx::QueryImpl.
      9 
     10 
     11 #include "libGLESv2/renderer/d3d9/Query9.h"
     12 #include "libGLESv2/main.h"
     13 #include "libGLESv2/renderer/d3d9/renderer9_utils.h"
     14 #include "libGLESv2/renderer/d3d9/Renderer9.h"
     15 
     16 namespace rx
     17 {
     18 
     19 Query9::Query9(rx::Renderer9 *renderer, GLenum type) : QueryImpl(type)
     20 {
     21     mRenderer = renderer;
     22     mQuery = NULL;
     23 }
     24 
     25 Query9::~Query9()
     26 {
     27     SafeRelease(mQuery);
     28 }
     29 
     30 void Query9::begin()
     31 {
     32     if (mQuery == NULL)
     33     {
     34         if (FAILED(mRenderer->getDevice()->CreateQuery(D3DQUERYTYPE_OCCLUSION, &mQuery)))
     35         {
     36             return gl::error(GL_OUT_OF_MEMORY);
     37         }
     38     }
     39 
     40     HRESULT result = mQuery->Issue(D3DISSUE_BEGIN);
     41     UNUSED_ASSERTION_VARIABLE(result);
     42     ASSERT(SUCCEEDED(result));
     43 }
     44 
     45 void Query9::end()
     46 {
     47     ASSERT(mQuery);
     48 
     49     HRESULT result = mQuery->Issue(D3DISSUE_END);
     50     UNUSED_ASSERTION_VARIABLE(result);
     51     ASSERT(SUCCEEDED(result));
     52 
     53     mStatus = GL_FALSE;
     54     mResult = GL_FALSE;
     55 }
     56 
     57 GLuint Query9::getResult()
     58 {
     59     if (mQuery != NULL)
     60     {
     61         while (!testQuery())
     62         {
     63             Sleep(0);
     64             // explicitly check for device loss
     65             // some drivers seem to return S_FALSE even if the device is lost
     66             // instead of D3DERR_DEVICELOST like they should
     67             if (mRenderer->testDeviceLost(true))
     68             {
     69                 return gl::error(GL_OUT_OF_MEMORY, 0);
     70             }
     71         }
     72     }
     73 
     74     return mResult;
     75 }
     76 
     77 GLboolean Query9::isResultAvailable()
     78 {
     79     if (mQuery != NULL)
     80     {
     81         testQuery();
     82     }
     83 
     84     return mStatus;
     85 }
     86 
     87 GLboolean Query9::testQuery()
     88 {
     89     if (mQuery != NULL && mStatus != GL_TRUE)
     90     {
     91         DWORD numPixels = 0;
     92 
     93         HRESULT hres = mQuery->GetData(&numPixels, sizeof(DWORD), D3DGETDATA_FLUSH);
     94         if (hres == S_OK)
     95         {
     96             mStatus =  GL_TRUE;
     97 
     98             switch (getType())
     99             {
    100               case GL_ANY_SAMPLES_PASSED_EXT:
    101               case GL_ANY_SAMPLES_PASSED_CONSERVATIVE_EXT:
    102                 mResult = (numPixels > 0) ? GL_TRUE : GL_FALSE;
    103                 break;
    104               default:
    105                 ASSERT(false);
    106             }
    107         }
    108         else if (d3d9::isDeviceLostError(hres))
    109         {
    110             mRenderer->notifyDeviceLost();
    111             return gl::error(GL_OUT_OF_MEMORY, GL_TRUE);
    112         }
    113 
    114         return mStatus;
    115     }
    116 
    117     return GL_TRUE; // prevent blocking when query is null
    118 }
    119 
    120 bool Query9::isStarted() const
    121 {
    122     return (mQuery != NULL);
    123 }
    124 
    125 }
    126