From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail-wm0-x22f.google.com (mail-wm0-x22f.google.com [IPv6:2a00:1450:400c:c09::22f]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by ml01.01.org (Postfix) with ESMTPS id 159C582101 for ; Sun, 26 Feb 2017 10:30:45 -0800 (PST) Received: by mail-wm0-x22f.google.com with SMTP id v77so46916493wmv.1 for ; Sun, 26 Feb 2017 10:30:45 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=CTgLr8j5GyFzE9yopzHD+EE4qc7FWQ0xFUNPbEhDlB4=; b=jmIbt36CSpJrWYwXByi0K6om0n8pNZeJ4Y6LRTJE0x+v5K3jiaRZ9qvdmWZWrgyLfP WmucBCLtvdN8g/yMBwrNQrgAo0ZnITnA5nkOPOxLOovtndO0V6hqWGBEmcTNnz5j8RFy sbkwSuvh46nlV38ufDhNPGzRkQq+KyXxUSUMg= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=CTgLr8j5GyFzE9yopzHD+EE4qc7FWQ0xFUNPbEhDlB4=; b=OhscTH724KPuCpTBIF91Q/C691Fm8/TmFT1anYlTsbBtcGioPJ6OUTHx8llwj819EE Myaq8D5iP2o1FAE6mBDjhXWjmDSzsYdVbuYKTZtWrkbRWr+A1WlKkBZ5/q7bK9eHmrSu Hv3sb0IFlGXciy2Ln8FYU5IRQUdsQVyZEzRYVdlgZBjC6xoya7HTbRs+lp60Twmf4s8E Gp+re0YXYUY4C9m3P7Vb0vXth77fYPCrRTmoixMsGkAn/b8f4fD0s0CEv2Itlwv3IQH2 UpNckrwRamgxjaXDFGdj3oz3n1P1I7yjabIASfR7RE+M8Jb0qX3mpIlCmdAMWGOIzYST Y7TQ== X-Gm-Message-State: AMke39lROnxrLVkx9OWQ1EClicDECP5fr4JHulw5m5qxgkUfj0OyW+xgJ+5A6e9IRBWzc7kL X-Received: by 10.28.66.11 with SMTP id p11mr11630394wma.38.1488133843544; Sun, 26 Feb 2017 10:30:43 -0800 (PST) Received: from localhost.localdomain ([105.149.201.216]) by smtp.gmail.com with ESMTPSA id s103sm4499474wrc.6.2017.02.26.10.30.40 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Sun, 26 Feb 2017 10:30:42 -0800 (PST) From: Ard Biesheuvel To: edk2-devel@lists.01.org, jiewen.yao@intel.com, leif.lindholm@linaro.org Cc: afish@apple.com, michael.d.kinney@intel.com, liming.gao@Intel.com, lersek@redhat.com, feng.tian@intel.com, star.zeng@intel.com, Ard Biesheuvel Date: Sun, 26 Feb 2017 18:30:03 +0000 Message-Id: <1488133805-4773-5-git-send-email-ard.biesheuvel@linaro.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1488133805-4773-1-git-send-email-ard.biesheuvel@linaro.org> References: <1488133805-4773-1-git-send-email-ard.biesheuvel@linaro.org> Subject: [PATCH v3 4/6] MdeModulePkg/DxeCore: use separate lock for pool allocations X-BeenThere: edk2-devel@lists.01.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: EDK II Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sun, 26 Feb 2017 18:30:45 -0000 In preparation of adding memory permission attribute management to the pool allocator, split off the locking of the pool metadata into a separate lock. This is an improvement in itself, given that pool allocation can only interfere with the page allocation bookkeeping if pool pages are allocated or released. But it is also required to ensure that the permission attribute management does not deadlock, given that it may trigger page table splits leading to additional page tables being allocated. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Ard Biesheuvel --- MdeModulePkg/Core/Dxe/Mem/Pool.c | 53 ++++++++++++++++---- 1 file changed, 43 insertions(+), 10 deletions(-) diff --git a/MdeModulePkg/Core/Dxe/Mem/Pool.c b/MdeModulePkg/Core/Dxe/Mem/Pool.c index 7afd2d312c1d..410615e0dee9 100644 --- a/MdeModulePkg/Core/Dxe/Mem/Pool.c +++ b/MdeModulePkg/Core/Dxe/Mem/Pool.c @@ -15,6 +15,8 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. #include "DxeMain.h" #include "Imem.h" +STATIC EFI_LOCK mPoolMemoryLock = EFI_INITIALIZE_LOCK_VARIABLE (TPL_NOTIFY); + #define POOL_FREE_SIGNATURE SIGNATURE_32('p','f','r','0') typedef struct { UINT32 Signature; @@ -239,13 +241,13 @@ CoreInternalAllocatePool ( // // Acquire the memory lock and make the allocation // - Status = CoreAcquireLockOrFail (&gMemoryLock); + Status = CoreAcquireLockOrFail (&mPoolMemoryLock); if (EFI_ERROR (Status)) { return EFI_OUT_OF_RESOURCES; } *Buffer = CoreAllocatePoolI (PoolType, Size); - CoreReleaseMemoryLock (); + CoreReleaseLock (&mPoolMemoryLock); return (*Buffer != NULL) ? EFI_SUCCESS : EFI_OUT_OF_RESOURCES; } @@ -289,6 +291,23 @@ CoreAllocatePool ( return Status; } +STATIC +VOID * +CoreAllocatePoolPagesI ( + IN EFI_MEMORY_TYPE PoolType, + IN UINTN NoPages, + IN UINTN Granularity + ) +{ + VOID *Buffer; + + CoreAcquireMemoryLock (); + Buffer = CoreAllocatePoolPages (PoolType, NoPages, Granularity); + CoreReleaseMemoryLock (); + + return Buffer; +} + /** Internal function to allocate pool of a particular type. Caller must have the memory lock held @@ -317,7 +336,7 @@ CoreAllocatePoolI ( UINTN NoPages; UINTN Granularity; - ASSERT_LOCKED (&gMemoryLock); + ASSERT_LOCKED (&mPoolMemoryLock); if (PoolType == EfiACPIReclaimMemory || PoolType == EfiACPIMemoryNVS || @@ -355,7 +374,7 @@ CoreAllocatePoolI ( if (Index >= SIZE_TO_LIST (Granularity)) { NoPages = EFI_SIZE_TO_PAGES(Size) + EFI_SIZE_TO_PAGES (Granularity) - 1; NoPages &= ~(UINTN)(EFI_SIZE_TO_PAGES (Granularity) - 1); - Head = CoreAllocatePoolPages (PoolType, NoPages, Granularity); + Head = CoreAllocatePoolPagesI (PoolType, NoPages, Granularity); goto Done; } @@ -383,7 +402,7 @@ CoreAllocatePoolI ( // // Get another page // - NewPage = CoreAllocatePoolPages(PoolType, EFI_SIZE_TO_PAGES (Granularity), Granularity); + NewPage = CoreAllocatePoolPagesI (PoolType, EFI_SIZE_TO_PAGES (Granularity), Granularity); if (NewPage == NULL) { goto Done; } @@ -486,9 +505,9 @@ CoreInternalFreePool ( return EFI_INVALID_PARAMETER; } - CoreAcquireMemoryLock (); + CoreAcquireLock (&mPoolMemoryLock); Status = CoreFreePoolI (Buffer, PoolType); - CoreReleaseMemoryLock (); + CoreReleaseLock (&mPoolMemoryLock); return Status; } @@ -525,6 +544,19 @@ CoreFreePool ( return Status; } +STATIC +VOID +CoreFreePoolPagesI ( + IN EFI_MEMORY_TYPE PoolType, + IN EFI_PHYSICAL_ADDRESS Memory, + IN UINTN NoPages + ) +{ + CoreAcquireMemoryLock (); + CoreFreePoolPages (Memory, NoPages); + CoreReleaseMemoryLock (); +} + /** Internal function to free a pool entry. Caller must have the memory lock held @@ -573,7 +605,7 @@ CoreFreePoolI ( // ASSERT (Tail->Signature == POOL_TAIL_SIGNATURE); ASSERT (Head->Size == Tail->Size); - ASSERT_LOCKED (&gMemoryLock); + ASSERT_LOCKED (&mPoolMemoryLock); if (Tail->Signature != POOL_TAIL_SIGNATURE) { return EFI_INVALID_PARAMETER; @@ -624,7 +656,7 @@ CoreFreePoolI ( // NoPages = EFI_SIZE_TO_PAGES(Size) + EFI_SIZE_TO_PAGES (Granularity) - 1; NoPages &= ~(UINTN)(EFI_SIZE_TO_PAGES (Granularity) - 1); - CoreFreePoolPages ((EFI_PHYSICAL_ADDRESS) (UINTN) Head, NoPages); + CoreFreePoolPagesI (Pool->MemoryType, (EFI_PHYSICAL_ADDRESS) (UINTN) Head, NoPages); } else { @@ -680,7 +712,8 @@ CoreFreePoolI ( // // Free the page // - CoreFreePoolPages ((EFI_PHYSICAL_ADDRESS) (UINTN)NewPage, EFI_SIZE_TO_PAGES (Granularity)); + CoreFreePoolPagesI (Pool->MemoryType, (EFI_PHYSICAL_ADDRESS) (UINTN)NewPage, + EFI_SIZE_TO_PAGES (Granularity)); } } } -- 2.7.4