| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169 |
- #include "BsD3D9TimerQuery.h"
- #include "BsD3D9RenderSystem.h"
- #include "BsRenderStats.h"
- #include "BsDebug.h"
- namespace BansheeEngine
- {
- D3D9TimerQuery::D3D9TimerQuery()
- :mFinalized(false), mBeginQuery(nullptr), mFreqQuery(nullptr), mQueryIssued(false),
- mEndQuery(nullptr), mDisjointQuery(nullptr), mTimeDelta(0.0f), mDevice(nullptr)
- {
- createQuery();
- BS_INC_RENDER_STAT_CAT(ResCreated, RenderStatObject_Query);
- }
- D3D9TimerQuery::~D3D9TimerQuery()
- {
- releaseQuery();
- BS_INC_RENDER_STAT_CAT(ResDestroyed, RenderStatObject_Query);
- }
- void D3D9TimerQuery::createQuery()
- {
- mDevice = D3D9RenderSystem::getActiveD3D9Device();
- HRESULT hr = mDevice->CreateQuery(D3DQUERYTYPE_TIMESTAMPDISJOINT, &mDisjointQuery);
- if (hr != S_OK)
- {
- BS_EXCEPT(RenderingAPIException, "Failed to create a timer query.");
- }
- hr = mDevice->CreateQuery(D3DQUERYTYPE_TIMESTAMPFREQ, &mFreqQuery);
- if (hr != S_OK)
- {
- BS_EXCEPT(RenderingAPIException, "Failed to create a timer query.");
- }
- hr = mDevice->CreateQuery(D3DQUERYTYPE_TIMESTAMP, &mBeginQuery);
- if (hr != S_OK)
- {
- BS_EXCEPT(RenderingAPIException, "Failed to create a timer query.");
- }
- hr = mDevice->CreateQuery(D3DQUERYTYPE_TIMESTAMP, &mEndQuery);
- if (hr != S_OK)
- {
- BS_EXCEPT(RenderingAPIException, "Failed to create a timer query.");
- }
- }
- void D3D9TimerQuery::releaseQuery()
- {
- SAFE_RELEASE(mBeginQuery);
- SAFE_RELEASE(mEndQuery);
- SAFE_RELEASE(mDisjointQuery);
- SAFE_RELEASE(mFreqQuery);
- }
- bool D3D9TimerQuery::isQueryValid() const
- {
- return mDisjointQuery != nullptr && mBeginQuery != nullptr &&
- mEndQuery != nullptr && mFreqQuery != nullptr;
- }
- void D3D9TimerQuery::begin()
- {
- mQueryIssued = false;
- if (isQueryValid())
- {
- mDisjointQuery->Issue(D3DISSUE_BEGIN);
- mFreqQuery->Issue(D3DISSUE_END);
- mBeginQuery->Issue(D3DISSUE_END);
- }
- setActive(true);
- }
- void D3D9TimerQuery::end()
- {
- if (isQueryValid())
- {
- mEndQuery->Issue(D3DISSUE_END);
- mDisjointQuery->Issue(D3DISSUE_END);
- }
- mQueryIssued = true;
- mFinalized = false;
- }
- bool D3D9TimerQuery::isReady() const
- {
- if (!isQueryValid()) // Possibly device reset, in which case query is considered done if issued
- return mQueryIssued;
- if (!mQueryIssued)
- return false;
- BOOL queryData;
- return mDisjointQuery->GetData(&queryData, sizeof(BOOL), 0) == S_OK;
- }
- float D3D9TimerQuery::getTimeMs()
- {
- if(!mFinalized && isReady())
- {
- finalize();
- }
- return mTimeDelta;
- }
- void D3D9TimerQuery::finalize()
- {
- mFinalized = true;
- if (!isQueryValid())
- {
- mTimeDelta = 0.0f;
- return;
- }
- BOOL disjoint;
- mDisjointQuery->GetData(&disjoint, sizeof(BOOL), 0);
- if(!disjoint)
- {
- UINT64 frequency;
- mFreqQuery->GetData(&frequency, sizeof(UINT64), 0);
- UINT64 timeStart, timeEnd;
- mBeginQuery->GetData(&timeStart, sizeof(UINT64), 0);
- mEndQuery->GetData(&timeEnd, sizeof(UINT64), 0);
- UINT64 delta = timeEnd - timeStart;
- mTimeDelta = (delta/(float)frequency) * 1000.0f;
- }
- else
- {
- LOGWRN("Unrealiable GPU timer query detected.");
- }
- }
- void D3D9TimerQuery::notifyOnDeviceCreate(IDirect3DDevice9* d3d9Device)
- {
- if (d3d9Device == mDevice)
- createQuery();
- }
- void D3D9TimerQuery::notifyOnDeviceDestroy(IDirect3DDevice9* d3d9Device)
- {
- if (d3d9Device == mDevice)
- releaseQuery();
- }
- void D3D9TimerQuery::notifyOnDeviceLost(IDirect3DDevice9* d3d9Device)
- {
- if (d3d9Device == mDevice)
- releaseQuery();
- }
- void D3D9TimerQuery::notifyOnDeviceReset(IDirect3DDevice9* d3d9Device)
- {
- if (d3d9Device == mDevice)
- createQuery();
- }
- }
|