qxl-wddm-dod: Use rendering offload thread

Instead of sending drawable commands down from presentation
callback, collect drawables objects and pass them to dedicated
thread for processing. This reduce peak load of presentation
callback.

Signed-off-by: Javier Celaya <javier.celaya@flexvdi.com>
Signed-off-by: Yuri Benditovich <yuri.benditovich@daynix.com>
Acked-by: Frediano Ziglio <fziglio@redhat.com>
This commit is contained in:
yuri.benditovich@daynix.com 2017-04-01 19:40:29 +03:00 committed by Frediano Ziglio
parent 7ca13f4f48
commit 0987a61bff
2 changed files with 28 additions and 38 deletions

View File

@ -3786,19 +3786,16 @@ QxlDevice::ExecutePresentDisplayOnly(
NTSTATUS Status = STATUS_SUCCESS; NTSTATUS Status = STATUS_SUCCESS;
SIZE_T sizeMoves = NumMoves*sizeof(D3DKMT_MOVE_RECT); QXLDrawable **pDrawables = new (NonPagedPoolNx) QXLDrawable *[NumDirtyRects + NumMoves + 1];
SIZE_T sizeRects = NumDirtyRects*sizeof(RECT); UINT nIndex = 0;
SIZE_T size = sizeof(DoPresentMemory) + sizeMoves + sizeRects;
DoPresentMemory* ctx = reinterpret_cast<DoPresentMemory*> if (!pDrawables)
(new (NonPagedPoolNx) BYTE[size]);
if (!ctx)
{ {
return STATUS_NO_MEMORY; return STATUS_NO_MEMORY;
} }
RtlZeroMemory(ctx,size); DoPresentMemory ctx[1];
RtlZeroMemory(ctx, sizeof(ctx));
ctx->DstAddr = DstAddr; ctx->DstAddr = DstAddr;
ctx->DstBitPerPixel = DstBitPerPixel; ctx->DstBitPerPixel = DstBitPerPixel;
@ -3824,6 +3821,7 @@ QxlDevice::ExecutePresentDisplayOnly(
PMDL mdl = IoAllocateMdl((PVOID)SrcAddr, sizeToMap, FALSE, FALSE, NULL); PMDL mdl = IoAllocateMdl((PVOID)SrcAddr, sizeToMap, FALSE, FALSE, NULL);
if(!mdl) if(!mdl)
{ {
delete[] pDrawables;
return STATUS_INSUFFICIENT_RESOURCES; return STATUS_INSUFFICIENT_RESOURCES;
} }
@ -3840,6 +3838,7 @@ QxlDevice::ExecutePresentDisplayOnly(
{ {
Status = GetExceptionCode(); Status = GetExceptionCode();
IoFreeMdl(mdl); IoFreeMdl(mdl);
delete[] pDrawables;
return Status; return Status;
} }
@ -3853,6 +3852,7 @@ QxlDevice::ExecutePresentDisplayOnly(
Status = STATUS_INSUFFICIENT_RESOURCES; Status = STATUS_INSUFFICIENT_RESOURCES;
MmUnlockPages(mdl); MmUnlockPages(mdl);
IoFreeMdl(mdl); IoFreeMdl(mdl);
delete[] pDrawables;
return Status; return Status;
} }
@ -3860,23 +3860,6 @@ QxlDevice::ExecutePresentDisplayOnly(
ctx->Mdl = mdl; ctx->Mdl = mdl;
} }
BYTE* rects = reinterpret_cast<BYTE*>(ctx+1);
// copy moves and update pointer
if (Moves)
{
memcpy(rects,Moves,sizeMoves);
ctx->Moves = reinterpret_cast<D3DKMT_MOVE_RECT*>(rects);
rects += sizeMoves;
}
// copy dirty rects and update pointer
if (DirtyRect)
{
memcpy(rects,DirtyRect,sizeRects);
ctx->DirtyRect = reinterpret_cast<RECT*>(rects);
}
// Set up destination blt info // Set up destination blt info
BLT_INFO DstBltInfo; BLT_INFO DstBltInfo;
DstBltInfo.pBits = ctx->DstAddr; DstBltInfo.pBits = ctx->DstAddr;
@ -3918,7 +3901,9 @@ QxlDevice::ExecutePresentDisplayOnly(
DbgPrint(TRACE_LEVEL_INFORMATION, ("--- %d SourcePoint.x = %ld, SourcePoint.y = %ld, DestRect.bottom = %ld, DestRect.left = %ld, DestRect.right = %ld, DestRect.top = %ld\n", DbgPrint(TRACE_LEVEL_INFORMATION, ("--- %d SourcePoint.x = %ld, SourcePoint.y = %ld, DestRect.bottom = %ld, DestRect.left = %ld, DestRect.right = %ld, DestRect.top = %ld\n",
i , pSourcePoint->x, pSourcePoint->y, pDestRect->bottom, pDestRect->left, pDestRect->right, pDestRect->top)); i , pSourcePoint->x, pSourcePoint->y, pDestRect->bottom, pDestRect->left, pDestRect->right, pDestRect->top));
CopyBits(*pDestRect, *pSourcePoint); pDrawables[nIndex] = PrepareCopyBits(*pDestRect, *pSourcePoint);
if (pDrawables[nIndex]) nIndex++;
} }
// Copy all the dirty rects from source image to video frame buffer. // Copy all the dirty rects from source image to video frame buffer.
@ -3932,11 +3917,13 @@ QxlDevice::ExecutePresentDisplayOnly(
DbgPrint(TRACE_LEVEL_INFORMATION, ("--- %d pDirtyRect->bottom = %ld, pDirtyRect->left = %ld, pDirtyRect->right = %ld, pDirtyRect->top = %ld\n", DbgPrint(TRACE_LEVEL_INFORMATION, ("--- %d pDirtyRect->bottom = %ld, pDirtyRect->left = %ld, pDirtyRect->right = %ld, pDirtyRect->top = %ld\n",
i, pDirtyRect->bottom, pDirtyRect->left, pDirtyRect->right, pDirtyRect->top)); i, pDirtyRect->bottom, pDirtyRect->left, pDirtyRect->right, pDirtyRect->top));
BltBits(&DstBltInfo, pDrawables[nIndex] = PrepareBltBits(&DstBltInfo,
&SrcBltInfo, &SrcBltInfo,
1, 1,
pDirtyRect, pDirtyRect,
&sourcePoint); &sourcePoint);
if (pDrawables[nIndex]) nIndex++;
} }
// Unmap unmap and unlock the pages. // Unmap unmap and unlock the pages.
@ -3945,7 +3932,10 @@ QxlDevice::ExecutePresentDisplayOnly(
MmUnlockPages(ctx->Mdl); MmUnlockPages(ctx->Mdl);
IoFreeMdl(ctx->Mdl); IoFreeMdl(ctx->Mdl);
} }
delete [] reinterpret_cast<BYTE*>(ctx);
pDrawables[nIndex] = NULL;
PostToWorkerThread(pDrawables);
return STATUS_SUCCESS; return STATUS_SUCCESS;
} }
@ -4360,7 +4350,7 @@ VOID QxlDevice::SetImageId(InternalImage *internal,
} }
} }
void QxlDevice::CopyBits(const RECT& rect, const POINT& sourcePoint) QXLDrawable *QxlDevice::PrepareCopyBits(const RECT& rect, const POINT& sourcePoint)
{ {
PAGED_CODE(); PAGED_CODE();
QXLDrawable *drawable; QXLDrawable *drawable;
@ -4369,18 +4359,18 @@ void QxlDevice::CopyBits(const RECT& rect, const POINT& sourcePoint)
if (!(drawable = Drawable(QXL_COPY_BITS, &rect, NULL, 0))) { if (!(drawable = Drawable(QXL_COPY_BITS, &rect, NULL, 0))) {
DbgPrint(TRACE_LEVEL_ERROR, ("Cannot get Drawable.\n")); DbgPrint(TRACE_LEVEL_ERROR, ("Cannot get Drawable.\n"));
return; return NULL;
} }
drawable->u.copy_bits.src_pos.x = sourcePoint.x; drawable->u.copy_bits.src_pos.x = sourcePoint.x;
drawable->u.copy_bits.src_pos.y = sourcePoint.y; drawable->u.copy_bits.src_pos.y = sourcePoint.y;
PushDrawable(drawable);
DbgPrint(TRACE_LEVEL_VERBOSE, ("<--- %s\n", __FUNCTION__)); DbgPrint(TRACE_LEVEL_VERBOSE, ("<--- %s\n", __FUNCTION__));
return drawable;
} }
VOID QxlDevice::BltBits ( QXLDrawable *QxlDevice::PrepareBltBits (
BLT_INFO* pDst, BLT_INFO* pDst,
CONST BLT_INFO* pSrc, CONST BLT_INFO* pSrc,
UINT NumRects, UINT NumRects,
@ -4403,7 +4393,7 @@ VOID QxlDevice::BltBits (
if (!(drawable = Drawable(QXL_DRAW_COPY, pRects, NULL, 0))) { if (!(drawable = Drawable(QXL_DRAW_COPY, pRects, NULL, 0))) {
DbgPrint(TRACE_LEVEL_ERROR, ("Cannot get Drawable.\n")); DbgPrint(TRACE_LEVEL_ERROR, ("Cannot get Drawable.\n"));
return; return NULL;
} }
CONST RECT* pRect = &pRects[0]; CONST RECT* pRect = &pRects[0];
@ -4476,9 +4466,9 @@ VOID QxlDevice::BltBits (
drawable->surfaces_rects[0].top, drawable->surfaces_rects[0].bottom, drawable->surfaces_rects[0].top, drawable->surfaces_rects[0].bottom,
drawable->u.copy.src_bitmap)); drawable->u.copy.src_bitmap));
PushDrawable(drawable);
DbgPrint(TRACE_LEVEL_VERBOSE, ("<--- %s\n", __FUNCTION__)); DbgPrint(TRACE_LEVEL_VERBOSE, ("<--- %s\n", __FUNCTION__));
return drawable;
} }
VOID QxlDevice::PutBytesAlign(QXLDataChunk **chunk_ptr, UINT8 **now_ptr, VOID QxlDevice::PutBytesAlign(QXLDataChunk **chunk_ptr, UINT8 **now_ptr,

View File

@ -495,12 +495,12 @@ public:
BOOLEAN IsBIOSCompatible() { return FALSE; } BOOLEAN IsBIOSCompatible() { return FALSE; }
protected: protected:
NTSTATUS GetModeList(DXGK_DISPLAY_INFORMATION* pDispInfo); NTSTATUS GetModeList(DXGK_DISPLAY_INFORMATION* pDispInfo);
VOID BltBits (BLT_INFO* pDst, QXLDrawable *PrepareBltBits (BLT_INFO* pDst,
CONST BLT_INFO* pSrc, CONST BLT_INFO* pSrc,
UINT NumRects, UINT NumRects,
_In_reads_(NumRects) CONST RECT *pRects, _In_reads_(NumRects) CONST RECT *pRects,
POINT* pSourcePoint); POINT* pSourcePoint);
void CopyBits(const RECT& rect, const POINT& sourcePoint); QXLDrawable *PrepareCopyBits(const RECT& rect, const POINT& sourcePoint);
QXLDrawable *Drawable(UINT8 type, QXLDrawable *Drawable(UINT8 type,
CONST RECT *area, CONST RECT *area,
CONST RECT *clip, CONST RECT *clip,