-/*
+/*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS kernel
* PURPOSE: Functions for creation and destruction of DCs
} GDI_DC_ATTR_ENTRY, *PGDI_DC_ATTR_ENTRY;
-PDC_ATTR
-FASTCALL
-AllocateDcAttr(VOID)
-{
- PTHREADINFO pti;
- PPROCESSINFO ppi;
- PDC_ATTR pDc_Attr;
- PGDI_DC_ATTR_FREELIST pGdiDcAttrFreeList;
- PGDI_DC_ATTR_ENTRY pGdiDcAttrEntry;
- int i;
-
- pti = PsGetCurrentThreadWin32Thread();
- if (pti->pgdiDcattr)
- {
- pDc_Attr = pti->pgdiDcattr; // Get the free one.
- pti->pgdiDcattr = NULL;
- return pDc_Attr;
- }
-
- ppi = PsGetCurrentProcessWin32Process();
-
- if (!ppi->pDCAttrList) // If set point is null, allocate new group.
- {
- pGdiDcAttrEntry = EngAllocUserMem(sizeof(GDI_DC_ATTR_ENTRY), 0);
-
- if (!pGdiDcAttrEntry)
- {
- DPRINT1("DcAttr Failed User Allocation!\n");
- return NULL;
- }
-
- DPRINT("AllocDcAttr User 0x%x\n",pGdiDcAttrEntry);
-
- pGdiDcAttrFreeList = ExAllocatePoolWithTag( PagedPool,
- sizeof(GDI_DC_ATTR_FREELIST),
- GDITAG_DC_FREELIST);
- if ( !pGdiDcAttrFreeList )
- {
- EngFreeUserMem(pGdiDcAttrEntry);
- return NULL;
- }
-
- RtlZeroMemory(pGdiDcAttrFreeList, sizeof(GDI_DC_ATTR_FREELIST));
-
- DPRINT("AllocDcAttr Ex 0x%x\n",pGdiDcAttrFreeList);
-
- InsertHeadList( &ppi->GDIDcAttrFreeList, &pGdiDcAttrFreeList->Entry);
-
- pGdiDcAttrFreeList->nEntries = GDIDCATTRFREE;
- // Start at the bottom up and set end of free list point.
- ppi->pDCAttrList = &pGdiDcAttrEntry->Attr[GDIDCATTRFREE-1];
- // Build the free attr list.
- for ( i = 0; i < GDIDCATTRFREE; i++)
- {
- pGdiDcAttrFreeList->AttrList[i] = &pGdiDcAttrEntry->Attr[i];
- }
- }
-
- pDc_Attr = ppi->pDCAttrList;
- pGdiDcAttrFreeList = (PGDI_DC_ATTR_FREELIST)ppi->GDIDcAttrFreeList.Flink;
-
- // Free the list when it is full!
- if ( pGdiDcAttrFreeList->nEntries-- == 1)
- { // No more free entries, so yank the list.
- RemoveEntryList( &pGdiDcAttrFreeList->Entry );
-
- ExFreePoolWithTag( pGdiDcAttrFreeList, GDITAG_DC_FREELIST );
-
- if ( IsListEmpty( &ppi->GDIDcAttrFreeList ) )
- {
- ppi->pDCAttrList = NULL;
- return pDc_Attr;
- }
-
- pGdiDcAttrFreeList = (PGDI_DC_ATTR_FREELIST)ppi->GDIDcAttrFreeList.Flink;
- }
-
- ppi->pDCAttrList = pGdiDcAttrFreeList->AttrList[pGdiDcAttrFreeList->nEntries-1];
-
- return pDc_Attr;
-}
-
-VOID
-FASTCALL
-FreeDcAttr(PDC_ATTR pDc_Attr)
+BOOL
+NTAPI
+DC_bAllocDcAttr(PDC pdc)
{
- PTHREADINFO pti;
- PPROCESSINFO ppi;
- PGDI_DC_ATTR_FREELIST pGdiDcAttrFreeList;
+ PPROCESSINFO ppi;
+ PDC_ATTR pdcattr;
- pti = PsGetCurrentThreadWin32Thread();
-
- if (!pti) return;
-
- if (!pti->pgdiDcattr)
- { // If it is null, just cache it for the next time.
- pti->pgdiDcattr = pDc_Attr;
- return;
- }
+ ppi = PsGetCurrentProcessWin32Process();
+ ASSERT(ppi);
- ppi = PsGetCurrentProcessWin32Process();
-
- pGdiDcAttrFreeList = (PGDI_DC_ATTR_FREELIST)ppi->GDIDcAttrFreeList.Flink;
-
- // We add to the list of free entries, so this will grows!
- if ( IsListEmpty(&ppi->GDIDcAttrFreeList) ||
- pGdiDcAttrFreeList->nEntries == GDIDCATTRFREE )
- {
- pGdiDcAttrFreeList = ExAllocatePoolWithTag( PagedPool,
- sizeof(GDI_DC_ATTR_FREELIST),
- GDITAG_DC_FREELIST);
- if ( !pGdiDcAttrFreeList )
- {
- return;
- }
- InsertHeadList( &ppi->GDIDcAttrFreeList, &pGdiDcAttrFreeList->Entry);
- pGdiDcAttrFreeList->nEntries = 0;
- }
- // Up count, save the entry and set end of free list point.
- ++pGdiDcAttrFreeList->nEntries; // Top Down...
- pGdiDcAttrFreeList->AttrList[pGdiDcAttrFreeList->nEntries-1] = pDc_Attr;
- ppi->pDCAttrList = pDc_Attr;
-
- return;
-}
+ pdcattr = GdiPoolAllocate(ppi->pPoolDcAttr);
+ if (!pdcattr)
+ {
+ DPRINT1("Could not allocate DC attr\n");
+ return FALSE;
+ }
-BOOL
-FASTCALL
-DC_AllocDcAttr(PDC pdc)
-{
- DC_AllocateDcAttr(pdc->BaseObject.hHmgr);
+ /* Copy the content from the kernel mode dc attr */
+ pdc->pdcattr = pdcattr;
*pdc->pdcattr = pdc->dcattr;
- return TRUE;
-}
-// CHECK against current head
-VOID
-FASTCALL
-DC_AllocateDcAttr(HDC hDC)
-{
- PVOID NewMem = NULL;
- PDC pDC;
- HANDLE Pid = NtCurrentProcess();
- ULONG MemSize = sizeof(DC_ATTR); //PAGE_SIZE it will allocate that size
+ /* Set the object attribute in the handle table */
+ GDIOBJ_vSetObjectAttr(&pdc->BaseObject, pdcattr);
- NTSTATUS Status = ZwAllocateVirtualMemory(Pid,
- &NewMem,
- 0,
- &MemSize,
- MEM_COMMIT|MEM_RESERVE,
- PAGE_READWRITE);
- {
- INT Index = GDI_HANDLE_GET_INDEX((HGDIOBJ)hDC);
- PGDI_TABLE_ENTRY Entry = &GdiHandleTable->Entries[Index];
- // FIXME: dc could have been deleted!!! use GDIOBJ_InsertUserData
- if (NT_SUCCESS(Status))
- {
- RtlZeroMemory(NewMem, MemSize);
- Entry->UserData = NewMem;
- DPRINT("DC_ATTR allocated! 0x%x\n",NewMem);
- }
- else
- {
- DPRINT("DC_ATTR not allocated!\n");
- }
- }
- pDC = DC_LockDc(hDC);
- ASSERT(pDC->pdcattr == &pDC->dcattr);
- if(NewMem)
- {
- pDC->pdcattr = NewMem; // Store pointer
- }
- DC_UnlockDc(pDC);
+ DPRINT("DC_AllocDcAttr: pdc=%p, pdc->pdcattr=%p\n", pdc, pdc->pdcattr);
+ return TRUE;
}
VOID
NTAPI
DC_vFreeDcAttr(PDC pdc)
{
- HANDLE Pid = NtCurrentProcess();
- INT Index;
- PGDI_TABLE_ENTRY pent;
+ PPROCESSINFO ppi;
if (pdc->pdcattr == &pdc->dcattr)
{
return;
}
- pdc->pdcattr = &pdc->dcattr;
+ /* Reset the object attribute in the handle table */
+ GDIOBJ_vSetObjectAttr(&pdc->BaseObject, NULL);
- Index = GDI_HANDLE_GET_INDEX(pdc->BaseObject.hHmgr);
- pent = &GdiHandleTable->Entries[Index];
- if(pent->UserData)
- {
- ULONG MemSize = sizeof(DC_ATTR);
- NTSTATUS Status = ZwFreeVirtualMemory(Pid,
- &pent->UserData,
- &MemSize,
- MEM_RELEASE);
- if (!NT_SUCCESS(Status))
- {
- DPRINT1("DC_FreeDC failed to free DC_ATTR 0x%p\n", pent->UserData);
- ASSERT(FALSE);
- }
- pent->UserData = NULL;
- }
-}
+ ppi = PsGetCurrentProcessWin32Process();
+ ASSERT(ppi);
+ GdiPoolFree(ppi->pPoolDcAttr, pdc->pdcattr);
-
-static
-VOID
-CopytoUserDcAttr(PDC dc, PDC_ATTR pdcattr)
-{
- NTSTATUS Status = STATUS_SUCCESS;
- dc->dcattr.mxWorldToDevice = dc->dclevel.mxWorldToDevice;
- dc->dcattr.mxDeviceToWorld = dc->dclevel.mxDeviceToWorld;
- dc->dcattr.mxWorldToPage = dc->dclevel.mxWorldToPage;
-
- _SEH2_TRY
- {
- ProbeForWrite(pdcattr, sizeof(DC_ATTR), 1);
- RtlCopyMemory(pdcattr, &dc->dcattr, sizeof(DC_ATTR));
- }
- _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
- {
- Status = _SEH2_GetExceptionCode();
- ASSERT(FALSE);
- }
- _SEH2_END;
-}
-
-// FIXME: wtf? 2 functions, where one has a typo in the name????
-BOOL
-FASTCALL
-DCU_SyncDcAttrtoUser(PDC dc)
-{
- PDC_ATTR pdcattr = dc->pdcattr;
-
- if (pdcattr == &dc->dcattr) return TRUE; // No need to copy self.
- ASSERT(pdcattr);
- CopytoUserDcAttr( dc, pdcattr);
- return TRUE;
-}
-// LOL! DCU_ Sync hDc Attr to User,,, need it speeled out for you?
-BOOL
-FASTCALL
-DCU_SynchDcAttrtoUser(HDC hDC)
-{
- BOOL Ret;
- PDC pDC = DC_LockDc ( hDC );
- if (!pDC) return FALSE;
- Ret = DCU_SyncDcAttrtoUser(pDC);
- DC_UnlockDc( pDC );
- return Ret;
+ /* Reset to kmode dcattr */
+ pdc->pdcattr = &pdc->dcattr;
}
-