From patchwork Wed Mar 1 16:31:39 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ard Biesheuvel X-Patchwork-Id: 94722 Delivered-To: patch@linaro.org Received: by 10.182.3.34 with SMTP id 2csp1856969obz; Wed, 1 Mar 2017 08:31:54 -0800 (PST) X-Received: by 10.99.131.198 with SMTP id h189mr9842746pge.161.1488385914693; Wed, 01 Mar 2017 08:31:54 -0800 (PST) Return-Path: Received: from ml01.01.org (ml01.01.org. [198.145.21.10]) by mx.google.com with ESMTPS id m67si5045522pfb.0.2017.03.01.08.31.54 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Wed, 01 Mar 2017 08:31:54 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) client-ip=198.145.21.10; Authentication-Results: mx.google.com; dkim=neutral (body hash did not verify) header.i=@linaro.org; spf=pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) smtp.mailfrom=edk2-devel-bounces@lists.01.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=linaro.org Received: from [127.0.0.1] (localhost [IPv6:::1]) by ml01.01.org (Postfix) with ESMTP id 399A6821D5; Wed, 1 Mar 2017 08:31:54 -0800 (PST) X-Original-To: edk2-devel@lists.01.org Delivered-To: edk2-devel@lists.01.org Received: from mail-wr0-x234.google.com (mail-wr0-x234.google.com [IPv6:2a00:1450:400c:c0c::234]) (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 B3C41821D3 for ; Wed, 1 Mar 2017 08:31:52 -0800 (PST) Received: by mail-wr0-x234.google.com with SMTP id g10so34008402wrg.2 for ; Wed, 01 Mar 2017 08:31:52 -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=04MSbIgNcsOJKjlD4A5ILRUravY+reYyuGvD7qYTivg=; b=dJ48cffBF3/dI72Ynv1qCo7g9OcghMHAq479a0PrJg/Ka+GWZ+Owp0dcyDBqeUkfvT YmZHUCPfZcpciooAUZUkEmACZZChCgMIUaBSpbgdG25n56Asm1M8YGLcBNEPjDMjFZwy kZ3toJeoVSGQjtajnd7QyV4RKqu+yHjOjV+d0= 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=04MSbIgNcsOJKjlD4A5ILRUravY+reYyuGvD7qYTivg=; b=Y91p7g1/747YWW/I4hV+NadohepJ90s/X+noghfw9yhAisYzHf122QEFIukWbvL0NU k+nfL/O6ZRsBKHIzwAKhSSmA8u+i6xI+0ffStt6TJayz9ZKZQD+9/c/mUMObvrKzg9WP cSJWdqTkt5xXqsV3wagd8ult4Q+r9E3vuqVqHoH/rq8L1jC4M6rav2gvxsy8qY8HCoXW 20VrbPsRY++Wcs+P1QFJM2bRwkTOeKr7b+/ybWOozHOsAecOh5w056bxE0i14h6qeF8z Xbqp98kEF4Jh80Gjj5ODSI65Fs8rOEITNw8lm2l8B4dDhn9/frsKVyI8YaZcNSTsERgV pXCA== X-Gm-Message-State: AMke39nV5qs2VvYQC3oGNpKHzt5AQfGs8IiZu7HIg0zOf1gQLpAXvQmuy/zZqaoQ9u86uWBT X-Received: by 10.223.139.68 with SMTP id v4mr8646267wra.70.1488385911231; Wed, 01 Mar 2017 08:31:51 -0800 (PST) Received: from localhost.localdomain ([105.147.1.203]) by smtp.gmail.com with ESMTPSA id 11sm7275292wrb.10.2017.03.01.08.31.49 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Wed, 01 Mar 2017 08:31:50 -0800 (PST) From: Ard Biesheuvel To: edk2-devel@lists.01.org, leif.lindholm@linaro.org, lersek@redhat.com Date: Wed, 1 Mar 2017 16:31:39 +0000 Message-Id: <1488385903-30267-2-git-send-email-ard.biesheuvel@linaro.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> References: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> Subject: [edk2] [PATCH 1/5] ArmPkg/ArmMmuLib AARCH64: use correct return type for exported functions 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: , Cc: Ard Biesheuvel MIME-Version: 1.0 Errors-To: edk2-devel-bounces@lists.01.org Sender: "edk2-devel" The routines ArmConfigureMmu() and SetMemoryAttributes() [*] are declared as returning EFI_STATUS in the respective header files, so align the definitions with that. * SetMemoryAttributes() is declared in the wrong header (and defined in ArmMmuLib for AARCH64 and in CpuDxe for ARM) Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Ard Biesheuvel --- ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c | 52 ++++++++++---------- 1 file changed, 26 insertions(+), 26 deletions(-) -- 2.7.4 _______________________________________________ edk2-devel mailing list edk2-devel@lists.01.org https://lists.01.org/mailman/listinfo/edk2-devel Reviewed-by: Leif Lindholm diff --git a/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c b/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c index 2f8f99d44a31..df170d20a2c2 100644 --- a/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c +++ b/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c @@ -329,7 +329,7 @@ GetBlockEntryListFromAddress ( } STATIC -RETURN_STATUS +EFI_STATUS UpdateRegionMapping ( IN UINT64 *RootTable, IN UINT64 RegionStart, @@ -347,7 +347,7 @@ UpdateRegionMapping ( // Ensure the Length is aligned on 4KB boundary if ((RegionLength == 0) || ((RegionLength & (SIZE_4KB - 1)) != 0)) { ASSERT_EFI_ERROR (EFI_INVALID_PARAMETER); - return RETURN_INVALID_PARAMETER; + return EFI_INVALID_PARAMETER; } do { @@ -357,7 +357,7 @@ UpdateRegionMapping ( BlockEntry = GetBlockEntryListFromAddress (RootTable, RegionStart, &TableLevel, &BlockEntrySize, &LastBlockEntry); if (BlockEntry == NULL) { // GetBlockEntryListFromAddress() return NULL when it fails to allocate new pages from the Translation Tables - return RETURN_OUT_OF_RESOURCES; + return EFI_OUT_OF_RESOURCES; } if (TableLevel != 3) { @@ -385,11 +385,11 @@ UpdateRegionMapping ( } while ((RegionLength >= BlockEntrySize) && (BlockEntry <= LastBlockEntry)); } while (RegionLength != 0); - return RETURN_SUCCESS; + return EFI_SUCCESS; } STATIC -RETURN_STATUS +EFI_STATUS FillTranslationTable ( IN UINT64 *RootTable, IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryRegion @@ -446,7 +446,7 @@ GcdAttributeToPageAttribute ( return PageAttributes | TT_AF; } -RETURN_STATUS +EFI_STATUS SetMemoryAttributes ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, @@ -454,7 +454,7 @@ SetMemoryAttributes ( IN EFI_PHYSICAL_ADDRESS VirtualMask ) { - RETURN_STATUS Status; + EFI_STATUS Status; UINT64 *TranslationTable; UINT64 PageAttributes; UINT64 PageAttributeMask; @@ -480,18 +480,18 @@ SetMemoryAttributes ( Length, PageAttributes, PageAttributeMask); - if (RETURN_ERROR (Status)) { + if (EFI_ERROR (Status)) { return Status; } // Invalidate all TLB entries so changes are synced ArmInvalidateTlb (); - return RETURN_SUCCESS; + return EFI_SUCCESS; } STATIC -RETURN_STATUS +EFI_STATUS SetMemoryRegionAttribute ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, @@ -499,23 +499,23 @@ SetMemoryRegionAttribute ( IN UINT64 BlockEntryMask ) { - RETURN_STATUS Status; + EFI_STATUS Status; UINT64 *RootTable; RootTable = ArmGetTTBR0BaseAddress (); Status = UpdateRegionMapping (RootTable, BaseAddress, Length, Attributes, BlockEntryMask); - if (RETURN_ERROR (Status)) { + if (EFI_ERROR (Status)) { return Status; } // Invalidate all TLB entries so changes are synced ArmInvalidateTlb (); - return RETURN_SUCCESS; + return EFI_SUCCESS; } -RETURN_STATUS +EFI_STATUS ArmSetMemoryRegionNoExec ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length @@ -536,7 +536,7 @@ ArmSetMemoryRegionNoExec ( ~TT_ADDRESS_MASK_BLOCK_ENTRY); } -RETURN_STATUS +EFI_STATUS ArmClearMemoryRegionNoExec ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length @@ -554,7 +554,7 @@ ArmClearMemoryRegionNoExec ( Mask); } -RETURN_STATUS +EFI_STATUS ArmSetMemoryRegionReadOnly ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length @@ -567,7 +567,7 @@ ArmSetMemoryRegionReadOnly ( ~TT_ADDRESS_MASK_BLOCK_ENTRY); } -RETURN_STATUS +EFI_STATUS ArmClearMemoryRegionReadOnly ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length @@ -580,7 +580,7 @@ ArmClearMemoryRegionReadOnly ( ~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AP_MASK)); } -RETURN_STATUS +EFI_STATUS EFIAPI ArmConfigureMmu ( IN ARM_MEMORY_REGION_DESCRIPTOR *MemoryTable, @@ -594,11 +594,11 @@ ArmConfigureMmu ( UINTN T0SZ; UINTN RootTableEntryCount; UINT64 TCR; - RETURN_STATUS Status; + EFI_STATUS Status; if(MemoryTable == NULL) { ASSERT (MemoryTable != NULL); - return RETURN_INVALID_PARAMETER; + return EFI_INVALID_PARAMETER; } // Cover the entire GCD memory space @@ -632,7 +632,7 @@ ArmConfigureMmu ( } else { DEBUG ((EFI_D_ERROR, "ArmConfigureMmu: The MaxAddress 0x%lX is not supported by this MMU configuration.\n", MaxAddress)); ASSERT (0); // Bigger than 48-bit memory space are not supported - return RETURN_UNSUPPORTED; + return EFI_UNSUPPORTED; } } else if (ArmReadCurrentEL () == AARCH64_EL1) { // Due to Cortex-A57 erratum #822227 we must set TG1[1] == 1, regardless of EPD1. @@ -654,11 +654,11 @@ ArmConfigureMmu ( } else { DEBUG ((EFI_D_ERROR, "ArmConfigureMmu: The MaxAddress 0x%lX is not supported by this MMU configuration.\n", MaxAddress)); ASSERT (0); // Bigger than 48-bit memory space are not supported - return RETURN_UNSUPPORTED; + return EFI_UNSUPPORTED; } } else { ASSERT (0); // UEFI is only expected to run at EL2 and EL1, not EL3. - return RETURN_UNSUPPORTED; + return EFI_UNSUPPORTED; } // @@ -680,7 +680,7 @@ ArmConfigureMmu ( // Allocate pages for translation table TranslationTable = AllocatePages (1); if (TranslationTable == NULL) { - return RETURN_OUT_OF_RESOURCES; + return EFI_OUT_OF_RESOURCES; } // We set TTBR0 just after allocating the table to retrieve its location from the subsequent // functions without needing to pass this value across the functions. The MMU is only enabled @@ -719,7 +719,7 @@ ArmConfigureMmu ( DEBUG_CODE_END (); Status = FillTranslationTable (TranslationTable, MemoryTable); - if (RETURN_ERROR (Status)) { + if (EFI_ERROR (Status)) { goto FREE_TRANSLATION_TABLE; } MemoryTable++; @@ -739,7 +739,7 @@ ArmConfigureMmu ( ArmEnableDataCache (); ArmEnableMmu (); - return RETURN_SUCCESS; + return EFI_SUCCESS; FREE_TRANSLATION_TABLE: FreePages (TranslationTable, 1); From patchwork Wed Mar 1 16:31:40 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ard Biesheuvel X-Patchwork-Id: 94723 Delivered-To: patch@linaro.org Received: by 10.182.3.34 with SMTP id 2csp1857003obz; Wed, 1 Mar 2017 08:31:59 -0800 (PST) X-Received: by 10.98.72.88 with SMTP id v85mr9462043pfa.99.1488385918921; Wed, 01 Mar 2017 08:31:58 -0800 (PST) Return-Path: Received: from ml01.01.org (ml01.01.org. [198.145.21.10]) by mx.google.com with ESMTPS id b5si5024270pgg.42.2017.03.01.08.31.58 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Wed, 01 Mar 2017 08:31:58 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) client-ip=198.145.21.10; Authentication-Results: mx.google.com; dkim=neutral (body hash did not verify) header.i=@linaro.org; spf=pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) smtp.mailfrom=edk2-devel-bounces@lists.01.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=linaro.org Received: from [127.0.0.1] (localhost [IPv6:::1]) by ml01.01.org (Postfix) with ESMTP id 767FD821D8; Wed, 1 Mar 2017 08:31:58 -0800 (PST) X-Original-To: edk2-devel@lists.01.org Delivered-To: edk2-devel@lists.01.org Received: from mail-wr0-x231.google.com (mail-wr0-x231.google.com [IPv6:2a00:1450:400c:c0c::231]) (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 22AEF821D8 for ; Wed, 1 Mar 2017 08:31:56 -0800 (PST) Received: by mail-wr0-x231.google.com with SMTP id u108so34025597wrb.3 for ; Wed, 01 Mar 2017 08:31:56 -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=i9In8Tv2heexDl5CUBB1lkllb3Cxbq7TnAmZKQxGdfQ=; b=d0ge8ioLlS7uALukVVT+cB2sKIO/+SjdgEIRYZFnr8QZYGsVEpXLxsYAWU6PxaEYBq N4PA0+a8+26qHzV55qDCGKYcdT3i+oDrA9UxbO4OOUT437SgioAfqbubqUETFkrM7Rxd APzP0S+RgKEMT3noxzpYtPzX7/XxN98GuR0G0= 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=i9In8Tv2heexDl5CUBB1lkllb3Cxbq7TnAmZKQxGdfQ=; b=Lb3S90yfBGtfK8Vg7kG3qZhmsZfF8rJI9GQwv8mRd9MrzpMXU/bCjhWq4gPulRoAXX ZICP3xPpjZFvOpqVZPH153wY2rze/zE66RWEf1Y5VrHZHF9Mk3QZE1MQIv0smNANACRH Q4uoyLfPDYv6BsfjXhUADQ3TCJ4snruc/0Ry4HED9ZEWOwl9nxMOKOFV3bsps7R5WJAr KQOjdR7kmN+qKq0i6PWIKa7pSM5HOPCjJzQ73cJ3bfF6yVwkxvzhLgaVmEZcHd7dxjwf FQmL37p3IsXJWH60OyOtCtd8hsZvZ2ihbMnYT1UltbngvxlwKqjMvLkPcExPuBc3SlaC xIuQ== X-Gm-Message-State: AMke39kvPzuOsCbe8JsKBFbiIzt7M99EeKnIGzQIgjXfagRiy3HvNpSZG/po98hzOjyWLufe X-Received: by 10.223.171.229 with SMTP id s92mr8300969wrc.64.1488385913884; Wed, 01 Mar 2017 08:31:53 -0800 (PST) Received: from localhost.localdomain ([105.147.1.203]) by smtp.gmail.com with ESMTPSA id 11sm7275292wrb.10.2017.03.01.08.31.51 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Wed, 01 Mar 2017 08:31:53 -0800 (PST) From: Ard Biesheuvel To: edk2-devel@lists.01.org, leif.lindholm@linaro.org, lersek@redhat.com Date: Wed, 1 Mar 2017 16:31:40 +0000 Message-Id: <1488385903-30267-3-git-send-email-ard.biesheuvel@linaro.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> References: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> Subject: [edk2] [PATCH 2/5] ArmPkg: move ARM version of SetMemoryAttributes to ArmMmuLib 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: , Cc: Ard Biesheuvel MIME-Version: 1.0 Errors-To: edk2-devel-bounces@lists.01.org Sender: "edk2-devel" ... where it belongs, since AARCH64 already keeps it there, and non DXE users of ArmMmuLib (such as DxeIpl, for the non-executable stack) may need its functionality as well. While at it, rename SetMemoryAttributes to ArmSetMemoryAttributes, and make any functions that are not exported STATIC. Also, replace an explicit gBS->AllocatePages() call [which is DXE specific] with MemoryAllocationLib::AllocatePages(). Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Ard Biesheuvel --- ArmPkg/Drivers/CpuDxe/Arm/Mmu.c | 368 -------------------- ArmPkg/Drivers/CpuDxe/CpuDxe.h | 14 +- ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c | 2 +- ArmPkg/Include/Library/ArmMmuLib.h | 8 + ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c | 2 +- ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c | 368 ++++++++++++++++++++ 6 files changed, 379 insertions(+), 383 deletions(-) -- 2.7.4 _______________________________________________ edk2-devel mailing list edk2-devel@lists.01.org https://lists.01.org/mailman/listinfo/edk2-devel Reviewed-by: Leif Lindholm diff --git a/ArmPkg/Drivers/CpuDxe/Arm/Mmu.c b/ArmPkg/Drivers/CpuDxe/Arm/Mmu.c index 6322d301060e..b985dd743f02 100644 --- a/ArmPkg/Drivers/CpuDxe/Arm/Mmu.c +++ b/ArmPkg/Drivers/CpuDxe/Arm/Mmu.c @@ -343,374 +343,6 @@ SyncCacheConfig ( return EFI_SUCCESS; } - - -EFI_STATUS -UpdatePageEntries ( - IN EFI_PHYSICAL_ADDRESS BaseAddress, - IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask - ) -{ - EFI_STATUS Status; - UINT32 EntryValue; - UINT32 EntryMask; - UINT32 FirstLevelIdx; - UINT32 Offset; - UINT32 NumPageEntries; - UINT32 Descriptor; - UINT32 p; - UINT32 PageTableIndex; - UINT32 PageTableEntry; - UINT32 CurrentPageTableEntry; - VOID *Mva; - - volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable; - volatile ARM_PAGE_TABLE_ENTRY *PageTable; - - Status = EFI_SUCCESS; - - // EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone) - // EntryValue: values at bit positions specified by EntryMask - EntryMask = TT_DESCRIPTOR_PAGE_TYPE_MASK | TT_DESCRIPTOR_PAGE_AP_MASK; - if ((Attributes & EFI_MEMORY_XP) != 0) { - EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE_XN; - } else { - EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE; - } - - // Although the PI spec is unclear on this the GCD guarantees that only - // one Attribute bit is set at a time, so we can safely use a switch statement - if ((Attributes & EFI_MEMORY_UC) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; - // map to strongly ordered - EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0, C=0, B=0 - } else if ((Attributes & EFI_MEMORY_WC) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; - // map to normal non-cachable - EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 = 0x2, B=0, C=0 - } else if ((Attributes & EFI_MEMORY_WT) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; - // write through with no-allocate - EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0] = 0, C=1, B=0 - } else if ((Attributes & EFI_MEMORY_WB) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; - // write back (with allocate) - EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001, C=1, B=1 - } - - if ((Attributes & EFI_MEMORY_RO) != 0) { - EntryValue |= TT_DESCRIPTOR_PAGE_AP_RO_RO; - } else { - EntryValue |= TT_DESCRIPTOR_PAGE_AP_RW_RW; - } - - // Obtain page table base - FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress (); - - // Calculate number of 4KB page table entries to change - NumPageEntries = Length / TT_DESCRIPTOR_PAGE_SIZE; - - // Iterate for the number of 4KB pages to change - Offset = 0; - for(p = 0; p < NumPageEntries; p++) { - // Calculate index into first level translation table for page table value - - FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress + Offset) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT; - ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT); - - // Read the descriptor from the first level page table - Descriptor = FirstLevelTable[FirstLevelIdx]; - - // Does this descriptor need to be converted from section entry to 4K pages? - if (!TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(Descriptor)) { - Status = ConvertSectionToPages (FirstLevelIdx << TT_DESCRIPTOR_SECTION_BASE_SHIFT); - if (EFI_ERROR(Status)) { - // Exit for loop - break; - } - - // Re-read descriptor - Descriptor = FirstLevelTable[FirstLevelIdx]; - } - - // Obtain page table base address - PageTable = (ARM_PAGE_TABLE_ENTRY *)TT_DESCRIPTOR_PAGE_BASE_ADDRESS(Descriptor); - - // Calculate index into the page table - PageTableIndex = ((BaseAddress + Offset) & TT_DESCRIPTOR_PAGE_INDEX_MASK) >> TT_DESCRIPTOR_PAGE_BASE_SHIFT; - ASSERT (PageTableIndex < TRANSLATION_TABLE_PAGE_COUNT); - - // Get the entry - CurrentPageTableEntry = PageTable[PageTableIndex]; - - // Mask off appropriate fields - PageTableEntry = CurrentPageTableEntry & ~EntryMask; - - // Mask in new attributes and/or permissions - PageTableEntry |= EntryValue; - - if (VirtualMask != 0) { - // Make this virtual address point at a physical page - PageTableEntry &= ~VirtualMask; - } - - if (CurrentPageTableEntry != PageTableEntry) { - Mva = (VOID *)(UINTN)((((UINTN)FirstLevelIdx) << TT_DESCRIPTOR_SECTION_BASE_SHIFT) + (PageTableIndex << TT_DESCRIPTOR_PAGE_BASE_SHIFT)); - if ((CurrentPageTableEntry & TT_DESCRIPTOR_PAGE_CACHEABLE_MASK) == TT_DESCRIPTOR_PAGE_CACHEABLE_MASK) { - // The current section mapping is cacheable so Clean/Invalidate the MVA of the page - // Note assumes switch(Attributes), not ARMv7 possibilities - WriteBackInvalidateDataCacheRange (Mva, TT_DESCRIPTOR_PAGE_SIZE); - } - - // Only need to update if we are changing the entry - PageTable[PageTableIndex] = PageTableEntry; - ArmUpdateTranslationTableEntry ((VOID *)&PageTable[PageTableIndex], Mva); - } - - Status = EFI_SUCCESS; - Offset += TT_DESCRIPTOR_PAGE_SIZE; - - } // End first level translation table loop - - return Status; -} - - - -EFI_STATUS -UpdateSectionEntries ( - IN EFI_PHYSICAL_ADDRESS BaseAddress, - IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask - ) -{ - EFI_STATUS Status = EFI_SUCCESS; - UINT32 EntryMask; - UINT32 EntryValue; - UINT32 FirstLevelIdx; - UINT32 NumSections; - UINT32 i; - UINT32 CurrentDescriptor; - UINT32 Descriptor; - VOID *Mva; - volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable; - - // EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone) - // EntryValue: values at bit positions specified by EntryMask - - // Make sure we handle a section range that is unmapped - EntryMask = TT_DESCRIPTOR_SECTION_TYPE_MASK | TT_DESCRIPTOR_SECTION_XN_MASK | - TT_DESCRIPTOR_SECTION_AP_MASK; - EntryValue = TT_DESCRIPTOR_SECTION_TYPE_SECTION; - - // Although the PI spec is unclear on this the GCD guarantees that only - // one Attribute bit is set at a time, so we can safely use a switch statement - if ((Attributes & EFI_MEMORY_UC) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; - // map to strongly ordered - EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0, C=0, B=0 - } else if ((Attributes & EFI_MEMORY_WC) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; - // map to normal non-cachable - EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 = 0x2, B=0, C=0 - } else if ((Attributes & EFI_MEMORY_WT) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; - // write through with no-allocate - EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0] = 0, C=1, B=0 - } else if ((Attributes & EFI_MEMORY_WB) != 0) { - // modify cacheability attributes - EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; - // write back (with allocate) - EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001, C=1, B=1 - } - - if ((Attributes & EFI_MEMORY_RO) != 0) { - EntryValue |= TT_DESCRIPTOR_SECTION_AP_RO_RO; - } else { - EntryValue |= TT_DESCRIPTOR_SECTION_AP_RW_RW; - } - - if ((Attributes & EFI_MEMORY_XP) != 0) { - EntryValue |= TT_DESCRIPTOR_SECTION_XN_MASK; - } - - // obtain page table base - FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress (); - - // calculate index into first level translation table for start of modification - FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT; - ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT); - - // calculate number of 1MB first level entries this applies to - NumSections = Length / TT_DESCRIPTOR_SECTION_SIZE; - - // iterate through each descriptor - for(i=0; i> TT_DESCRIPTOR_SECTION_BASE_SHIFT; - ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT); - - // Get section attributes and convert to page attributes - SectionDescriptor = FirstLevelTable[FirstLevelIdx]; - PageDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (SectionDescriptor, FALSE); - - // Allocate a page table for the 4KB entries (we use up a full page even though we only need 1KB) - Status = gBS->AllocatePages (AllocateAnyPages, EfiBootServicesData, 1, &PageTableAddr); - if (EFI_ERROR(Status)) { - return Status; - } - - PageTable = (volatile ARM_PAGE_TABLE_ENTRY *)(UINTN)PageTableAddr; - - // Write the page table entries out - for (Index = 0; Index < TRANSLATION_TABLE_PAGE_COUNT; Index++) { - PageTable[Index] = TT_DESCRIPTOR_PAGE_BASE_ADDRESS(BaseAddress + (Index << 12)) | PageDescriptor; - } - - // Flush d-cache so descriptors make it back to uncached memory for subsequent table walks - WriteBackInvalidateDataCacheRange ((VOID *)(UINTN)PageTableAddr, TT_DESCRIPTOR_PAGE_SIZE); - - // Formulate page table entry, Domain=0, NS=0 - PageTableDescriptor = (((UINTN)PageTableAddr) & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) | TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE; - - // Write the page table entry out, replacing section entry - FirstLevelTable[FirstLevelIdx] = PageTableDescriptor; - - return EFI_SUCCESS; -} - - - -EFI_STATUS -SetMemoryAttributes ( - IN EFI_PHYSICAL_ADDRESS BaseAddress, - IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask - ) -{ - EFI_STATUS Status; - UINT64 ChunkLength; - BOOLEAN FlushTlbs; - - FlushTlbs = FALSE; - while (Length > 0) { - if ((BaseAddress % TT_DESCRIPTOR_SECTION_SIZE == 0) && - Length >= TT_DESCRIPTOR_SECTION_SIZE) { - - ChunkLength = Length - Length % TT_DESCRIPTOR_SECTION_SIZE; - - DEBUG ((DEBUG_PAGE | DEBUG_INFO, - "SetMemoryAttributes(): MMU section 0x%lx length 0x%lx to %lx\n", - BaseAddress, ChunkLength, Attributes)); - - Status = UpdateSectionEntries (BaseAddress, ChunkLength, Attributes, - VirtualMask); - - FlushTlbs = TRUE; - } else { - - // - // Process page by page until the next section boundary, but only if - // we have more than a section's worth of area to deal with after that. - // - ChunkLength = TT_DESCRIPTOR_SECTION_SIZE - - (BaseAddress % TT_DESCRIPTOR_SECTION_SIZE); - if (ChunkLength + TT_DESCRIPTOR_SECTION_SIZE > Length) { - ChunkLength = Length; - } - - DEBUG ((DEBUG_PAGE | DEBUG_INFO, - "SetMemoryAttributes(): MMU page 0x%lx length 0x%lx to %lx\n", - BaseAddress, ChunkLength, Attributes)); - - Status = UpdatePageEntries (BaseAddress, ChunkLength, Attributes, - VirtualMask); - } - - if (EFI_ERROR (Status)) { - break; - } - - BaseAddress += ChunkLength; - Length -= ChunkLength; - } - - if (FlushTlbs) { - ArmInvalidateTlb (); - } - return Status; -} - UINT64 EfiAttributeToArmAttribute ( IN UINT64 EfiAttributes diff --git a/ArmPkg/Drivers/CpuDxe/CpuDxe.h b/ArmPkg/Drivers/CpuDxe/CpuDxe.h index a46db8d25754..a0f71e69ec09 100644 --- a/ArmPkg/Drivers/CpuDxe/CpuDxe.h +++ b/ArmPkg/Drivers/CpuDxe/CpuDxe.h @@ -19,6 +19,7 @@ #include #include +#include #include #include #include @@ -112,11 +113,6 @@ SyncCacheConfig ( IN EFI_CPU_ARCH_PROTOCOL *CpuProtocol ); -EFI_STATUS -ConvertSectionToPages ( - IN EFI_PHYSICAL_ADDRESS BaseAddress - ); - /** * Publish ARM Processor Data table in UEFI SYSTEM Table. * @param HobStart Pointer to the beginning of the HOB List from PEI. @@ -132,14 +128,6 @@ PublishArmProcessorTable( VOID ); -EFI_STATUS -SetMemoryAttributes ( - IN EFI_PHYSICAL_ADDRESS BaseAddress, - IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask - ); - // The ARM Attributes might be defined on 64-bit (case of the long format description table) UINT64 EfiAttributeToArmAttribute ( diff --git a/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c b/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c index 0f36a058407a..d0a3fedd3aa7 100644 --- a/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c +++ b/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c @@ -210,7 +210,7 @@ CpuSetMemoryAttributes ( if (EFI_ERROR (Status) || (RegionArmAttributes != ArmAttributes) || ((BaseAddress + Length) > (RegionBaseAddress + RegionLength))) { - return SetMemoryAttributes (BaseAddress, Length, EfiAttributes, 0); + return ArmSetMemoryAttributes (BaseAddress, Length, EfiAttributes, 0); } else { return EFI_SUCCESS; } diff --git a/ArmPkg/Include/Library/ArmMmuLib.h b/ArmPkg/Include/Library/ArmMmuLib.h index c1d43872d548..d3a302fa8125 100644 --- a/ArmPkg/Include/Library/ArmMmuLib.h +++ b/ArmPkg/Include/Library/ArmMmuLib.h @@ -62,4 +62,12 @@ ArmReplaceLiveTranslationEntry ( IN UINT64 Value ); +EFI_STATUS +ArmSetMemoryAttributes ( + IN EFI_PHYSICAL_ADDRESS BaseAddress, + IN UINT64 Length, + IN UINT64 Attributes, + IN EFI_PHYSICAL_ADDRESS VirtualMask + ); + #endif diff --git a/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c b/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c index df170d20a2c2..77f108971f3e 100644 --- a/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c +++ b/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c @@ -447,7 +447,7 @@ GcdAttributeToPageAttribute ( } EFI_STATUS -SetMemoryAttributes ( +ArmSetMemoryAttributes ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, IN UINT64 Attributes, diff --git a/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c b/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c index 4b6f4ce392b7..93980d6d12db 100644 --- a/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c +++ b/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c @@ -16,6 +16,7 @@ #include #include #include +#include #include #include #include @@ -36,6 +37,12 @@ #define ID_MMFR0_SHR_IMP_HW_COHERENT 1 #define ID_MMFR0_SHR_IGNORED 0xf +// First Level Descriptors +typedef UINT32 ARM_FIRST_LEVEL_DESCRIPTOR; + +// Second Level Descriptors +typedef UINT32 ARM_PAGE_TABLE_ENTRY; + UINTN EFIAPI ArmReadIdMmfr0 ( @@ -406,6 +413,367 @@ ArmConfigureMmu ( return RETURN_SUCCESS; } +STATIC +EFI_STATUS +ConvertSectionToPages ( + IN EFI_PHYSICAL_ADDRESS BaseAddress + ) +{ + UINT32 FirstLevelIdx; + UINT32 SectionDescriptor; + UINT32 PageTableDescriptor; + UINT32 PageDescriptor; + UINT32 Index; + + volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable; + volatile ARM_PAGE_TABLE_ENTRY *PageTable; + + DEBUG ((EFI_D_PAGE, "Converting section at 0x%x to pages\n", (UINTN)BaseAddress)); + + // Obtain page table base + FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress (); + + // Calculate index into first level translation table for start of modification + FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT; + ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT); + + // Get section attributes and convert to page attributes + SectionDescriptor = FirstLevelTable[FirstLevelIdx]; + PageDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (SectionDescriptor, FALSE); + + // Allocate a page table for the 4KB entries (we use up a full page even though we only need 1KB) + PageTable = (volatile ARM_PAGE_TABLE_ENTRY *)AllocatePages (1); + if (PageTable == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + // Write the page table entries out + for (Index = 0; Index < TRANSLATION_TABLE_PAGE_COUNT; Index++) { + PageTable[Index] = TT_DESCRIPTOR_PAGE_BASE_ADDRESS(BaseAddress + (Index << 12)) | PageDescriptor; + } + + // Flush d-cache so descriptors make it back to uncached memory for subsequent table walks + WriteBackInvalidateDataCacheRange ((VOID *)PageTable, TT_DESCRIPTOR_PAGE_SIZE); + + // Formulate page table entry, Domain=0, NS=0 + PageTableDescriptor = (((UINTN)PageTable) & TT_DESCRIPTOR_SECTION_PAGETABLE_ADDRESS_MASK) | TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE; + + // Write the page table entry out, replacing section entry + FirstLevelTable[FirstLevelIdx] = PageTableDescriptor; + + return EFI_SUCCESS; +} + +STATIC +EFI_STATUS +UpdatePageEntries ( + IN EFI_PHYSICAL_ADDRESS BaseAddress, + IN UINT64 Length, + IN UINT64 Attributes, + IN EFI_PHYSICAL_ADDRESS VirtualMask + ) +{ + EFI_STATUS Status; + UINT32 EntryValue; + UINT32 EntryMask; + UINT32 FirstLevelIdx; + UINT32 Offset; + UINT32 NumPageEntries; + UINT32 Descriptor; + UINT32 p; + UINT32 PageTableIndex; + UINT32 PageTableEntry; + UINT32 CurrentPageTableEntry; + VOID *Mva; + + volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable; + volatile ARM_PAGE_TABLE_ENTRY *PageTable; + + Status = EFI_SUCCESS; + + // EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone) + // EntryValue: values at bit positions specified by EntryMask + EntryMask = TT_DESCRIPTOR_PAGE_TYPE_MASK | TT_DESCRIPTOR_PAGE_AP_MASK; + if ((Attributes & EFI_MEMORY_XP) != 0) { + EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE_XN; + } else { + EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE; + } + + // Although the PI spec is unclear on this the GCD guarantees that only + // one Attribute bit is set at a time, so we can safely use a switch statement + if ((Attributes & EFI_MEMORY_UC) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; + // map to strongly ordered + EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0, C=0, B=0 + } else if ((Attributes & EFI_MEMORY_WC) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; + // map to normal non-cachable + EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 = 0x2, B=0, C=0 + } else if ((Attributes & EFI_MEMORY_WT) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; + // write through with no-allocate + EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0] = 0, C=1, B=0 + } else if ((Attributes & EFI_MEMORY_WB) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK; + // write back (with allocate) + EntryValue |= TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001, C=1, B=1 + } + + if ((Attributes & EFI_MEMORY_RO) != 0) { + EntryValue |= TT_DESCRIPTOR_PAGE_AP_RO_RO; + } else { + EntryValue |= TT_DESCRIPTOR_PAGE_AP_RW_RW; + } + + // Obtain page table base + FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress (); + + // Calculate number of 4KB page table entries to change + NumPageEntries = Length / TT_DESCRIPTOR_PAGE_SIZE; + + // Iterate for the number of 4KB pages to change + Offset = 0; + for(p = 0; p < NumPageEntries; p++) { + // Calculate index into first level translation table for page table value + + FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress + Offset) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT; + ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT); + + // Read the descriptor from the first level page table + Descriptor = FirstLevelTable[FirstLevelIdx]; + + // Does this descriptor need to be converted from section entry to 4K pages? + if (!TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(Descriptor)) { + Status = ConvertSectionToPages (FirstLevelIdx << TT_DESCRIPTOR_SECTION_BASE_SHIFT); + if (EFI_ERROR(Status)) { + // Exit for loop + break; + } + + // Re-read descriptor + Descriptor = FirstLevelTable[FirstLevelIdx]; + } + + // Obtain page table base address + PageTable = (ARM_PAGE_TABLE_ENTRY *)TT_DESCRIPTOR_PAGE_BASE_ADDRESS(Descriptor); + + // Calculate index into the page table + PageTableIndex = ((BaseAddress + Offset) & TT_DESCRIPTOR_PAGE_INDEX_MASK) >> TT_DESCRIPTOR_PAGE_BASE_SHIFT; + ASSERT (PageTableIndex < TRANSLATION_TABLE_PAGE_COUNT); + + // Get the entry + CurrentPageTableEntry = PageTable[PageTableIndex]; + + // Mask off appropriate fields + PageTableEntry = CurrentPageTableEntry & ~EntryMask; + + // Mask in new attributes and/or permissions + PageTableEntry |= EntryValue; + + if (VirtualMask != 0) { + // Make this virtual address point at a physical page + PageTableEntry &= ~VirtualMask; + } + + if (CurrentPageTableEntry != PageTableEntry) { + Mva = (VOID *)(UINTN)((((UINTN)FirstLevelIdx) << TT_DESCRIPTOR_SECTION_BASE_SHIFT) + (PageTableIndex << TT_DESCRIPTOR_PAGE_BASE_SHIFT)); + if ((CurrentPageTableEntry & TT_DESCRIPTOR_PAGE_CACHEABLE_MASK) == TT_DESCRIPTOR_PAGE_CACHEABLE_MASK) { + // The current section mapping is cacheable so Clean/Invalidate the MVA of the page + // Note assumes switch(Attributes), not ARMv7 possibilities + WriteBackInvalidateDataCacheRange (Mva, TT_DESCRIPTOR_PAGE_SIZE); + } + + // Only need to update if we are changing the entry + PageTable[PageTableIndex] = PageTableEntry; + ArmUpdateTranslationTableEntry ((VOID *)&PageTable[PageTableIndex], Mva); + } + + Status = EFI_SUCCESS; + Offset += TT_DESCRIPTOR_PAGE_SIZE; + + } // End first level translation table loop + + return Status; +} + +STATIC +EFI_STATUS +UpdateSectionEntries ( + IN EFI_PHYSICAL_ADDRESS BaseAddress, + IN UINT64 Length, + IN UINT64 Attributes, + IN EFI_PHYSICAL_ADDRESS VirtualMask + ) +{ + EFI_STATUS Status = EFI_SUCCESS; + UINT32 EntryMask; + UINT32 EntryValue; + UINT32 FirstLevelIdx; + UINT32 NumSections; + UINT32 i; + UINT32 CurrentDescriptor; + UINT32 Descriptor; + VOID *Mva; + volatile ARM_FIRST_LEVEL_DESCRIPTOR *FirstLevelTable; + + // EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone) + // EntryValue: values at bit positions specified by EntryMask + + // Make sure we handle a section range that is unmapped + EntryMask = TT_DESCRIPTOR_SECTION_TYPE_MASK | TT_DESCRIPTOR_SECTION_XN_MASK | + TT_DESCRIPTOR_SECTION_AP_MASK; + EntryValue = TT_DESCRIPTOR_SECTION_TYPE_SECTION; + + // Although the PI spec is unclear on this the GCD guarantees that only + // one Attribute bit is set at a time, so we can safely use a switch statement + if ((Attributes & EFI_MEMORY_UC) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; + // map to strongly ordered + EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_STRONGLY_ORDERED; // TEX[2:0] = 0, C=0, B=0 + } else if ((Attributes & EFI_MEMORY_WC) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; + // map to normal non-cachable + EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_NON_CACHEABLE; // TEX [2:0]= 001 = 0x2, B=0, C=0 + } else if ((Attributes & EFI_MEMORY_WT) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; + // write through with no-allocate + EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC; // TEX [2:0] = 0, C=1, B=0 + } else if ((Attributes & EFI_MEMORY_WB) != 0) { + // modify cacheability attributes + EntryMask |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK; + // write back (with allocate) + EntryValue |= TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_BACK_ALLOC; // TEX [2:0] = 001, C=1, B=1 + } + + if ((Attributes & EFI_MEMORY_RO) != 0) { + EntryValue |= TT_DESCRIPTOR_SECTION_AP_RO_RO; + } else { + EntryValue |= TT_DESCRIPTOR_SECTION_AP_RW_RW; + } + + if ((Attributes & EFI_MEMORY_XP) != 0) { + EntryValue |= TT_DESCRIPTOR_SECTION_XN_MASK; + } + + // obtain page table base + FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress (); + + // calculate index into first level translation table for start of modification + FirstLevelIdx = TT_DESCRIPTOR_SECTION_BASE_ADDRESS(BaseAddress) >> TT_DESCRIPTOR_SECTION_BASE_SHIFT; + ASSERT (FirstLevelIdx < TRANSLATION_TABLE_SECTION_COUNT); + + // calculate number of 1MB first level entries this applies to + NumSections = Length / TT_DESCRIPTOR_SECTION_SIZE; + + // iterate through each descriptor + for(i=0; i 0) { + if ((BaseAddress % TT_DESCRIPTOR_SECTION_SIZE == 0) && + Length >= TT_DESCRIPTOR_SECTION_SIZE) { + + ChunkLength = Length - Length % TT_DESCRIPTOR_SECTION_SIZE; + + DEBUG ((DEBUG_PAGE | DEBUG_INFO, + "SetMemoryAttributes(): MMU section 0x%lx length 0x%lx to %lx\n", + BaseAddress, ChunkLength, Attributes)); + + Status = UpdateSectionEntries (BaseAddress, ChunkLength, Attributes, + VirtualMask); + + FlushTlbs = TRUE; + } else { + + // + // Process page by page until the next section boundary, but only if + // we have more than a section's worth of area to deal with after that. + // + ChunkLength = TT_DESCRIPTOR_SECTION_SIZE - + (BaseAddress % TT_DESCRIPTOR_SECTION_SIZE); + if (ChunkLength + TT_DESCRIPTOR_SECTION_SIZE > Length) { + ChunkLength = Length; + } + + DEBUG ((DEBUG_PAGE | DEBUG_INFO, + "SetMemoryAttributes(): MMU page 0x%lx length 0x%lx to %lx\n", + BaseAddress, ChunkLength, Attributes)); + + Status = UpdatePageEntries (BaseAddress, ChunkLength, Attributes, + VirtualMask); + } + + if (EFI_ERROR (Status)) { + break; + } + + BaseAddress += ChunkLength; + Length -= ChunkLength; + } + + if (FlushTlbs) { + ArmInvalidateTlb (); + } + return Status; +} + RETURN_STATUS ArmSetMemoryRegionNoExec ( IN EFI_PHYSICAL_ADDRESS BaseAddress, From patchwork Wed Mar 1 16:31:41 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ard Biesheuvel X-Patchwork-Id: 94724 Delivered-To: patch@linaro.org Received: by 10.182.3.34 with SMTP id 2csp1857015obz; Wed, 1 Mar 2017 08:32:00 -0800 (PST) X-Received: by 10.99.55.85 with SMTP id g21mr7307737pgn.65.1488385920494; Wed, 01 Mar 2017 08:32:00 -0800 (PST) Return-Path: Received: from ml01.01.org (ml01.01.org. [198.145.21.10]) by mx.google.com with ESMTPS id e5si5027523pgg.25.2017.03.01.08.32.00 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Wed, 01 Mar 2017 08:32:00 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) client-ip=198.145.21.10; Authentication-Results: mx.google.com; dkim=neutral (body hash did not verify) header.i=@linaro.org; spf=pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) smtp.mailfrom=edk2-devel-bounces@lists.01.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=linaro.org Received: from [127.0.0.1] (localhost [IPv6:::1]) by ml01.01.org (Postfix) with ESMTP id ACCED821DC; Wed, 1 Mar 2017 08:31:58 -0800 (PST) X-Original-To: edk2-devel@lists.01.org Delivered-To: edk2-devel@lists.01.org Received: from mail-wm0-x236.google.com (mail-wm0-x236.google.com [IPv6:2a00:1450:400c:c09::236]) (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 3B167821D4 for ; Wed, 1 Mar 2017 08:31:57 -0800 (PST) Received: by mail-wm0-x236.google.com with SMTP id u199so40818082wmd.1 for ; Wed, 01 Mar 2017 08:31:57 -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=2mbrcYlKyLj6RdTjUN/QJcGcwnPNy0JaFEaC8njBOjA=; b=Vaeb/hfI6jMEUSiZVI3rgDGIWB95fatx2AZ27J1AYPuCoNblB+v21sLJgb8t1mcoCP L2ekaYUJHgVbpxsf0a69LmJz94BS8rgoiGDwtl4QZXbpSvDJuXUgA1SPF8l4kamOc6w/ yjrJFIgxMGMv0VTSwKOkggspoXBni1+KIs0Dc= 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=2mbrcYlKyLj6RdTjUN/QJcGcwnPNy0JaFEaC8njBOjA=; b=C/io/KlRmdvHu5TNQUpGKqaHp9k2nEn0XOMtuxUi/Kvp1k71cBh0/dgUdulIV5pYRz a8fERprKFs/iY+IwM5K89lGAScGSj0snF3Y9UTGYFpnZ5YvTuebLcI6MR41Wy3aA7ij4 5ik6WARYiIliULC4Sz1ILl88Dt8vS7/e1vN3gnw7mLrJG4QJN8y2j7VKb+LWMAGMO7rQ YqlIn9MlP4QxIB540pYBuqkI764yOdBsvsnuSDeRUAI2eyC64Qa5qj/UQyV4w1ER5hbr VR7s261vg3vUjh9DDmEow4EyyWEmRg+NHd9jLkjJsFkLeMqFcnkxblCKNhamSB6gLuqi sGUA== X-Gm-Message-State: AMke39lhOCHThhxChzqOl8xmzAQai2wM5/8l1uN03AaLl37X6h+4o69NUV8l3sM9vmAfSiM/ X-Received: by 10.28.66.11 with SMTP id p11mr4516420wma.38.1488385915707; Wed, 01 Mar 2017 08:31:55 -0800 (PST) Received: from localhost.localdomain ([105.147.1.203]) by smtp.gmail.com with ESMTPSA id 11sm7275292wrb.10.2017.03.01.08.31.54 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Wed, 01 Mar 2017 08:31:55 -0800 (PST) From: Ard Biesheuvel To: edk2-devel@lists.01.org, leif.lindholm@linaro.org, lersek@redhat.com Date: Wed, 1 Mar 2017 16:31:41 +0000 Message-Id: <1488385903-30267-4-git-send-email-ard.biesheuvel@linaro.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> References: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> Subject: [edk2] [PATCH 3/5] ArmPkg/ArmMmuLib: remove VirtualMask arg from ArmSetMemoryAttributes 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: , Cc: Ard Biesheuvel MIME-Version: 1.0 Errors-To: edk2-devel-bounces@lists.01.org Sender: "edk2-devel" We no longer make use of the ArmMmuLib 'feature' to create aliased memory ranges with mismatched attributes, and in fact, it was only wired up in the ARM version to begin with. So remove the VirtualMask argument from ArmSetMemoryAttributes()'s prototype, and remove the dead code that referred to it. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Ard Biesheuvel --- ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c | 2 +- ArmPkg/Include/Library/ArmMmuLib.h | 3 +-- ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c | 3 +-- ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c | 25 +++++--------------- 4 files changed, 9 insertions(+), 24 deletions(-) -- 2.7.4 _______________________________________________ edk2-devel mailing list edk2-devel@lists.01.org https://lists.01.org/mailman/listinfo/edk2-devel Reviewed-by: Leif Lindholm diff --git a/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c b/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c index d0a3fedd3aa7..8150486217cf 100644 --- a/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c +++ b/ArmPkg/Drivers/CpuDxe/CpuMmuCommon.c @@ -210,7 +210,7 @@ CpuSetMemoryAttributes ( if (EFI_ERROR (Status) || (RegionArmAttributes != ArmAttributes) || ((BaseAddress + Length) > (RegionBaseAddress + RegionLength))) { - return ArmSetMemoryAttributes (BaseAddress, Length, EfiAttributes, 0); + return ArmSetMemoryAttributes (BaseAddress, Length, EfiAttributes); } else { return EFI_SUCCESS; } diff --git a/ArmPkg/Include/Library/ArmMmuLib.h b/ArmPkg/Include/Library/ArmMmuLib.h index d3a302fa8125..fb7fd006417c 100644 --- a/ArmPkg/Include/Library/ArmMmuLib.h +++ b/ArmPkg/Include/Library/ArmMmuLib.h @@ -66,8 +66,7 @@ EFI_STATUS ArmSetMemoryAttributes ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask + IN UINT64 Attributes ); #endif diff --git a/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c b/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c index 77f108971f3e..8bd1c6fad95f 100644 --- a/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c +++ b/ArmPkg/Library/ArmMmuLib/AArch64/ArmMmuLibCore.c @@ -450,8 +450,7 @@ EFI_STATUS ArmSetMemoryAttributes ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask + IN UINT64 Attributes ) { EFI_STATUS Status; diff --git a/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c b/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c index 93980d6d12db..1112660b434e 100644 --- a/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c +++ b/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c @@ -469,8 +469,7 @@ EFI_STATUS UpdatePageEntries ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask + IN UINT64 Attributes ) { EFI_STATUS Status; @@ -575,11 +574,6 @@ UpdatePageEntries ( // Mask in new attributes and/or permissions PageTableEntry |= EntryValue; - if (VirtualMask != 0) { - // Make this virtual address point at a physical page - PageTableEntry &= ~VirtualMask; - } - if (CurrentPageTableEntry != PageTableEntry) { Mva = (VOID *)(UINTN)((((UINTN)FirstLevelIdx) << TT_DESCRIPTOR_SECTION_BASE_SHIFT) + (PageTableIndex << TT_DESCRIPTOR_PAGE_BASE_SHIFT)); if ((CurrentPageTableEntry & TT_DESCRIPTOR_PAGE_CACHEABLE_MASK) == TT_DESCRIPTOR_PAGE_CACHEABLE_MASK) { @@ -606,8 +600,7 @@ EFI_STATUS UpdateSectionEntries ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask + IN UINT64 Attributes ) { EFI_STATUS Status = EFI_SUCCESS; @@ -680,7 +673,7 @@ UpdateSectionEntries ( // has this descriptor already been coverted to pages? if (TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(CurrentDescriptor)) { // forward this 1MB range to page table function instead - Status = UpdatePageEntries ((FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT, TT_DESCRIPTOR_SECTION_SIZE, Attributes, VirtualMask); + Status = UpdatePageEntries ((FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT, TT_DESCRIPTOR_SECTION_SIZE, Attributes); } else { // still a section entry @@ -689,9 +682,6 @@ UpdateSectionEntries ( // mask in new attributes and/or permissions Descriptor |= EntryValue; - if (VirtualMask != 0) { - Descriptor &= ~VirtualMask; - } if (CurrentDescriptor != Descriptor) { Mva = (VOID *)(UINTN)(((UINTN)FirstLevelTable) << TT_DESCRIPTOR_SECTION_BASE_SHIFT); @@ -717,8 +707,7 @@ EFI_STATUS ArmSetMemoryAttributes ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length, - IN UINT64 Attributes, - IN EFI_PHYSICAL_ADDRESS VirtualMask + IN UINT64 Attributes ) { EFI_STATUS Status; @@ -736,8 +725,7 @@ ArmSetMemoryAttributes ( "SetMemoryAttributes(): MMU section 0x%lx length 0x%lx to %lx\n", BaseAddress, ChunkLength, Attributes)); - Status = UpdateSectionEntries (BaseAddress, ChunkLength, Attributes, - VirtualMask); + Status = UpdateSectionEntries (BaseAddress, ChunkLength, Attributes); FlushTlbs = TRUE; } else { @@ -756,8 +744,7 @@ ArmSetMemoryAttributes ( "SetMemoryAttributes(): MMU page 0x%lx length 0x%lx to %lx\n", BaseAddress, ChunkLength, Attributes)); - Status = UpdatePageEntries (BaseAddress, ChunkLength, Attributes, - VirtualMask); + Status = UpdatePageEntries (BaseAddress, ChunkLength, Attributes); } if (EFI_ERROR (Status)) { From patchwork Wed Mar 1 16:31:42 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ard Biesheuvel X-Patchwork-Id: 94725 Delivered-To: patch@linaro.org Received: by 10.182.3.34 with SMTP id 2csp1857030obz; Wed, 1 Mar 2017 08:32:03 -0800 (PST) X-Received: by 10.99.115.8 with SMTP id o8mr9693728pgc.36.1488385923101; Wed, 01 Mar 2017 08:32:03 -0800 (PST) Return-Path: Received: from ml01.01.org (ml01.01.org. [198.145.21.10]) by mx.google.com with ESMTPS id l3si4993292pgl.298.2017.03.01.08.32.02 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Wed, 01 Mar 2017 08:32:03 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) client-ip=198.145.21.10; Authentication-Results: mx.google.com; dkim=neutral (body hash did not verify) header.i=@linaro.org; spf=pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 198.145.21.10 as permitted sender) smtp.mailfrom=edk2-devel-bounces@lists.01.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=linaro.org Received: from [127.0.0.1] (localhost [IPv6:::1]) by ml01.01.org (Postfix) with ESMTP id E36DE821E0; Wed, 1 Mar 2017 08:31:59 -0800 (PST) X-Original-To: edk2-devel@lists.01.org Delivered-To: edk2-devel@lists.01.org Received: from mail-wm0-x234.google.com (mail-wm0-x234.google.com [IPv6:2a00:1450:400c:c09::234]) (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 1238A821DF for ; Wed, 1 Mar 2017 08:31:59 -0800 (PST) Received: by mail-wm0-x234.google.com with SMTP id v186so114699748wmd.0 for ; Wed, 01 Mar 2017 08:31:59 -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=fcoPYGDZW1eh3Su3cCDfh0ExnK0mhtSmuisbusR7zIc=; b=av+33MgrMB09juEz3yXUkaqkChtfetHTu8peqWZqAmk98sFEfNyv/CAo+xBk9GmnDz hsCZlwy+ynW6vzmpUGr4CxpbP9Pa5Qm6PFqbGv3B+X9hEa3ZZo8yH+CurfYVoa3lOGhZ SUkzdrP7bFk3PAmCMb+wXx5IaEzOuWXF4Li9g= 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=fcoPYGDZW1eh3Su3cCDfh0ExnK0mhtSmuisbusR7zIc=; b=cKSC7NgozdWGY5Unt49QdxSiKlor0/mKoFeScjkzHdze/J6dJQWMqIs3HkmtTIwVfG VgEzxlxBVLjmS0oj3uWPz3fuUwur1xZuKyucg8yXBjWVFpnCTzhUaop1TP29uIcyVjrA loymj2xMgOnh83h5WTn7mLDMjWIYToZGVGtdtrtuRBmVvxZQc/XKmwVIl5gqCYg54dDp rZnV1XqosA+qWY7l4gk4MPslh795urvItszRlvjua4BMWnRCHJQne+9b7bB7POyW4rFg CX3lDJIQPZei7GNioymv6lZMNvLDOEyQRM/UCbn0M8WK7nkwEJIBoMfGOLU/Y6uOCvkR Xlqg== X-Gm-Message-State: AMke39kN/3Mpheq64M1uYScygTtr8eTogrTXjc7oMn8nZj1QfA0tSrOInrglSinGSZ2aUYr6 X-Received: by 10.28.109.214 with SMTP id b83mr4155916wmi.21.1488385917612; Wed, 01 Mar 2017 08:31:57 -0800 (PST) Received: from localhost.localdomain ([105.147.1.203]) by smtp.gmail.com with ESMTPSA id 11sm7275292wrb.10.2017.03.01.08.31.55 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Wed, 01 Mar 2017 08:31:56 -0800 (PST) From: Ard Biesheuvel To: edk2-devel@lists.01.org, leif.lindholm@linaro.org, lersek@redhat.com Date: Wed, 1 Mar 2017 16:31:42 +0000 Message-Id: <1488385903-30267-5-git-send-email-ard.biesheuvel@linaro.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> References: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> Subject: [edk2] [PATCH 4/5] ArmPkg/ArmMmuLib ARM: implement memory permission control routines 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: , Cc: Ard Biesheuvel MIME-Version: 1.0 Errors-To: edk2-devel-bounces@lists.01.org Sender: "edk2-devel" Now that we have the prerequisite functionality available in ArmMmuLib, wire it up into ArmSetMemoryRegionNoExec, ArmClearMemoryRegionNoExec, ArmSetMemoryRegionReadOnly and ArmClearMemoryRegionReadOnly. This is used by the non-executable stack feature that is configured by DxeIpl. NOTE: The current implementation will not combine RO and XP attributes, i.e., setting/clearing a region no-exec will unconditionally clear the read-only attribute, and vice versa. Currently, we only use ArmSetMemoryRegionNoExec(), so for now, we should be able to live with this. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Ard Biesheuvel --- ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) -- 2.7.4 _______________________________________________ edk2-devel mailing list edk2-devel@lists.01.org https://lists.01.org/mailman/listinfo/edk2-devel diff --git a/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c b/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c index 1112660b434e..55601328d93e 100644 --- a/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c +++ b/ArmPkg/Library/ArmMmuLib/Arm/ArmMmuLibCore.c @@ -761,40 +761,40 @@ ArmSetMemoryAttributes ( return Status; } -RETURN_STATUS +EFI_STATUS ArmSetMemoryRegionNoExec ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length ) { - return RETURN_UNSUPPORTED; + return ArmSetMemoryAttributes (BaseAddress, Length, EFI_MEMORY_XP); } -RETURN_STATUS +EFI_STATUS ArmClearMemoryRegionNoExec ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length ) { - return RETURN_UNSUPPORTED; + return ArmSetMemoryAttributes (BaseAddress, Length, 0); } -RETURN_STATUS +EFI_STATUS ArmSetMemoryRegionReadOnly ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length ) { - return RETURN_UNSUPPORTED; + return ArmSetMemoryAttributes (BaseAddress, Length, EFI_MEMORY_RO); } -RETURN_STATUS +EFI_STATUS ArmClearMemoryRegionReadOnly ( IN EFI_PHYSICAL_ADDRESS BaseAddress, IN UINT64 Length ) { - return RETURN_UNSUPPORTED; + return ArmSetMemoryAttributes (BaseAddress, Length, 0); } RETURN_STATUS From patchwork Wed Mar 1 16:31:43 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Ard Biesheuvel X-Patchwork-Id: 94726 Delivered-To: patch@linaro.org Received: by 10.182.3.34 with SMTP id 2csp1857047obz; Wed, 1 Mar 2017 08:32:06 -0800 (PST) X-Received: by 10.98.73.155 with SMTP id r27mr9814416pfi.52.1488385926064; Wed, 01 Mar 2017 08:32:06 -0800 (PST) Return-Path: Received: from ml01.01.org (ml01.01.org. [2001:19d0:306:5::1]) by mx.google.com with ESMTPS id l15si5036502pln.91.2017.03.01.08.32.05 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Wed, 01 Mar 2017 08:32:06 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 2001:19d0:306:5::1 as permitted sender) client-ip=2001:19d0:306:5::1; Authentication-Results: mx.google.com; dkim=neutral (body hash did not verify) header.i=@linaro.org; spf=pass (google.com: best guess record for domain of edk2-devel-bounces@lists.01.org designates 2001:19d0:306:5::1 as permitted sender) smtp.mailfrom=edk2-devel-bounces@lists.01.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=linaro.org Received: from [127.0.0.1] (localhost [IPv6:::1]) by ml01.01.org (Postfix) with ESMTP id 2461D821DB; Wed, 1 Mar 2017 08:32:02 -0800 (PST) X-Original-To: edk2-devel@lists.01.org Delivered-To: edk2-devel@lists.01.org Received: from mail-wm0-x234.google.com (mail-wm0-x234.google.com [IPv6:2a00:1450:400c:c09::234]) (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 C9435821D4 for ; Wed, 1 Mar 2017 08:32:00 -0800 (PST) Received: by mail-wm0-x234.google.com with SMTP id v186so114700459wmd.0 for ; Wed, 01 Mar 2017 08:32:00 -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=7L3GPok8HXjBuP1QK/rSnJTC3EyBSeRssRffYuMLbvQ=; b=Tbs6Rzp9AgTk0aoUdL3vS4sGxrymPS2Lf6/xP6J7VZVlwromXRswpubF7UORfOHVUS lEzk3XfhE0cksUvZIP4/XWhvEvAuFiFI0ApNDVMPP5+0zi5ebk9mmBnNOXaN2OnryptH +xR31Wom7tte4bSUQz7zyn2mAvaDpaqyVKCBE= 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=7L3GPok8HXjBuP1QK/rSnJTC3EyBSeRssRffYuMLbvQ=; b=LXQA3Os/GpVkXnNbepbspiFlGK7198yV0aT23DBG98cujK/NpXbEBefxRy0l5k9KP/ oDvk0m0NlvgElgrA/1QlaLc10kn17YRhWD58//LO1qzrQSk/IG40hMPKTVFh50cnnfVK TSUpPHwOPnVscyFfs3wHR3foNOydqArmlHVRZz34QCRHFGMThFJWK9yu1XEzqtYgK9cg gRwZdsl4pKBkYIJISDqOQeK/fDdRGwVBusGzcpAKvY9I6cJgCgI9E1eQHPFBiZBsMhJX Hl6czFCewz2EuSwvEM0rHkHnRWLLSPzvfQodSKvuFwTHhfSzP57fHJxJ5Y7HwJWkIaO3 Oz+Q== X-Gm-Message-State: AMke39mge3pXSFfmqerIr1DlbR4CYFwzU+fZP/6gS4WcV7t5ndnnvCHaRipH099IrXSvwqAB X-Received: by 10.28.133.203 with SMTP id h194mr4149838wmd.122.1488385919333; Wed, 01 Mar 2017 08:31:59 -0800 (PST) Received: from localhost.localdomain ([105.147.1.203]) by smtp.gmail.com with ESMTPSA id 11sm7275292wrb.10.2017.03.01.08.31.57 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Wed, 01 Mar 2017 08:31:58 -0800 (PST) From: Ard Biesheuvel To: edk2-devel@lists.01.org, leif.lindholm@linaro.org, lersek@redhat.com Date: Wed, 1 Mar 2017 16:31:43 +0000 Message-Id: <1488385903-30267-6-git-send-email-ard.biesheuvel@linaro.org> X-Mailer: git-send-email 2.7.4 In-Reply-To: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> References: <1488385903-30267-1-git-send-email-ard.biesheuvel@linaro.org> Subject: [edk2] [PATCH 5/5] ArmVirtPkg: enable non-executable DXE stack for all platforms 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: , Cc: Ard Biesheuvel MIME-Version: 1.0 Errors-To: edk2-devel-bounces@lists.01.org Sender: "edk2-devel" Now that ARM has grown support for managing memory permissions in ArmMmuLib, we can enable the non-executable DXE stack for all virt platforms. Note that this is not [entirely] redundant: the non-executable stack is configured before DxeCore is invoked. The image and memory protection features configured during DXE only take affect when the CPU arch protocol implementation is registered. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Ard Biesheuvel --- ArmVirtPkg/ArmVirt.dsc.inc | 5 +++++ ArmVirtPkg/ArmVirtQemu.dsc | 2 -- ArmVirtPkg/ArmVirtQemuKernel.dsc | 2 -- 3 files changed, 5 insertions(+), 4 deletions(-) -- 2.7.4 _______________________________________________ edk2-devel mailing list edk2-devel@lists.01.org https://lists.01.org/mailman/listinfo/edk2-devel Reviewed-by: Laszlo Ersek diff --git a/ArmVirtPkg/ArmVirt.dsc.inc b/ArmVirtPkg/ArmVirt.dsc.inc index acfb71d3ff6c..e2d3dcce7945 100644 --- a/ArmVirtPkg/ArmVirt.dsc.inc +++ b/ArmVirtPkg/ArmVirt.dsc.inc @@ -386,6 +386,11 @@ [PcdsFixedAtBuild.common] # gEfiMdeModulePkgTokenSpaceGuid.PcdDxeNxMemoryProtectionPolicy|0xC000000000007FD1 + # + # Enable the non-executable DXE stack. (This gets set up by DxeIpl) + # + gEfiMdeModulePkgTokenSpaceGuid.PcdSetNxForStack|TRUE + [PcdsFixedAtBuild.ARM] gEmbeddedTokenSpaceGuid.PcdPrePiCpuMemorySize|40 diff --git a/ArmVirtPkg/ArmVirtQemu.dsc b/ArmVirtPkg/ArmVirtQemu.dsc index 615e1fca4877..477dfdcfc764 100644 --- a/ArmVirtPkg/ArmVirtQemu.dsc +++ b/ArmVirtPkg/ArmVirtQemu.dsc @@ -152,8 +152,6 @@ [PcdsFixedAtBuild.common] gEmbeddedTokenSpaceGuid.PcdPrePiCpuIoSize|16 [PcdsFixedAtBuild.AARCH64] - gEfiMdeModulePkgTokenSpaceGuid.PcdSetNxForStack|TRUE - # KVM limits it IPA space to 40 bits (1 TB), so there is no need to # support anything bigger, even if the host hardware does gEmbeddedTokenSpaceGuid.PcdPrePiCpuMemorySize|40 diff --git a/ArmVirtPkg/ArmVirtQemuKernel.dsc b/ArmVirtPkg/ArmVirtQemuKernel.dsc index e4902690123c..fd39c2802a85 100644 --- a/ArmVirtPkg/ArmVirtQemuKernel.dsc +++ b/ArmVirtPkg/ArmVirtQemuKernel.dsc @@ -163,8 +163,6 @@ [PcdsFixedAtBuild.AARCH64] # gEmbeddedTokenSpaceGuid.PcdPrePiCpuIoSize|16 - gEfiMdeModulePkgTokenSpaceGuid.PcdSetNxForStack|TRUE - # KVM limits it IPA space to 40 bits (1 TB), so there is no need to # support anything bigger, even if the host hardware does gEmbeddedTokenSpaceGuid.PcdPrePiCpuMemorySize|40