mirror of
https://github.com/AuxXxilium/linux_dsm_epyc7002.git
synced 2025-02-26 09:22:26 +07:00

Initial HIGHMEM support on ARC was introduced for PAE40 where the low memory (0x8000_0000 based) and high memory (0x1_0000_0000) were physically contiguous. So CONFIG_FLATMEM sufficed (despite a peipheral hole in the middle, which wasted a bit of struct page memory, but things worked). However w/o PAE, highmem was not possible and we could only reach ~1.75GB of DDR. Now there is a use case to access ~4GB of DDR w/o PAE40 The idea is to have low memory at canonical 0x8000_0000 and highmem at 0 so enire 4GB address space is available for physical addressing This needs additional platform/interconnect mapping to convert the non contiguous physical addresses into linear bus adresses. From Linux point of view, non contiguous divide means FLATMEM no longer works and DISCONTIGMEM is needed to track the pfns in the 2 regions. This scheme would also work for PAE40, only better in that we don't waste struct page memory for the peripheral hole. The DT description will be something like memory { ... reg = <0x80000000 0x200000000 /* 512MB: lowmem */ 0x00000000 0x10000000>; /* 256MB: highmem */ } Signed-off-by: Noam Camus <noamc@ezchip.com> Signed-off-by: Vineet Gupta <vgupta@synopsys.com>
114 lines
2.9 KiB
C
114 lines
2.9 KiB
C
/*
|
|
* Copyright (C) 2004, 2007-2010, 2011-2012 Synopsys, Inc. (www.synopsys.com)
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License version 2 as
|
|
* published by the Free Software Foundation.
|
|
*/
|
|
#ifndef __ASM_ARC_PAGE_H
|
|
#define __ASM_ARC_PAGE_H
|
|
|
|
#include <uapi/asm/page.h>
|
|
|
|
#ifndef __ASSEMBLY__
|
|
|
|
#define clear_page(paddr) memset((paddr), 0, PAGE_SIZE)
|
|
#define copy_page(to, from) memcpy((to), (from), PAGE_SIZE)
|
|
|
|
struct vm_area_struct;
|
|
struct page;
|
|
|
|
#define __HAVE_ARCH_COPY_USER_HIGHPAGE
|
|
|
|
void copy_user_highpage(struct page *to, struct page *from,
|
|
unsigned long u_vaddr, struct vm_area_struct *vma);
|
|
void clear_user_page(void *to, unsigned long u_vaddr, struct page *page);
|
|
|
|
#undef STRICT_MM_TYPECHECKS
|
|
|
|
#ifdef STRICT_MM_TYPECHECKS
|
|
/*
|
|
* These are used to make use of C type-checking..
|
|
*/
|
|
typedef struct {
|
|
unsigned long pte;
|
|
} pte_t;
|
|
typedef struct {
|
|
unsigned long pgd;
|
|
} pgd_t;
|
|
typedef struct {
|
|
unsigned long pgprot;
|
|
} pgprot_t;
|
|
|
|
#define pte_val(x) ((x).pte)
|
|
#define pgd_val(x) ((x).pgd)
|
|
#define pgprot_val(x) ((x).pgprot)
|
|
|
|
#define __pte(x) ((pte_t) { (x) })
|
|
#define __pgd(x) ((pgd_t) { (x) })
|
|
#define __pgprot(x) ((pgprot_t) { (x) })
|
|
|
|
#define pte_pgprot(x) __pgprot(pte_val(x))
|
|
|
|
#else /* !STRICT_MM_TYPECHECKS */
|
|
|
|
#ifdef CONFIG_ARC_HAS_PAE40
|
|
typedef unsigned long long pte_t;
|
|
#else
|
|
typedef unsigned long pte_t;
|
|
#endif
|
|
typedef unsigned long pgd_t;
|
|
typedef unsigned long pgprot_t;
|
|
|
|
#define pte_val(x) (x)
|
|
#define pgd_val(x) (x)
|
|
#define pgprot_val(x) (x)
|
|
#define __pte(x) (x)
|
|
#define __pgd(x) (x)
|
|
#define __pgprot(x) (x)
|
|
#define pte_pgprot(x) (x)
|
|
|
|
#endif
|
|
|
|
typedef pte_t * pgtable_t;
|
|
|
|
/*
|
|
* Use virt_to_pfn with caution:
|
|
* If used in pte or paddr related macros, it could cause truncation
|
|
* in PAE40 builds
|
|
* As a rule of thumb, only use it in helpers starting with virt_
|
|
* You have been warned !
|
|
*/
|
|
#define virt_to_pfn(kaddr) (__pa(kaddr) >> PAGE_SHIFT)
|
|
|
|
#define ARCH_PFN_OFFSET virt_to_pfn(CONFIG_LINUX_LINK_BASE)
|
|
|
|
#ifdef CONFIG_FLATMEM
|
|
#define pfn_valid(pfn) (((pfn) - ARCH_PFN_OFFSET) < max_mapnr)
|
|
#endif
|
|
|
|
/*
|
|
* __pa, __va, virt_to_page (ALERT: deprecated, don't use them)
|
|
*
|
|
* These macros have historically been misnamed
|
|
* virt here means link-address/program-address as embedded in object code.
|
|
* And for ARC, link-addr = physical address
|
|
*/
|
|
#define __pa(vaddr) ((unsigned long)(vaddr))
|
|
#define __va(paddr) ((void *)((unsigned long)(paddr)))
|
|
|
|
#define virt_to_page(kaddr) pfn_to_page(virt_to_pfn(kaddr))
|
|
#define virt_addr_valid(kaddr) pfn_valid(virt_to_pfn(kaddr))
|
|
|
|
/* Default Permissions for stack/heaps pages (Non Executable) */
|
|
#define VM_DATA_DEFAULT_FLAGS (VM_READ | VM_WRITE | VM_MAYREAD | VM_MAYWRITE)
|
|
|
|
#define WANT_PAGE_VIRTUAL 1
|
|
|
|
#include <asm-generic/memory_model.h> /* page_to_pfn, pfn_to_page */
|
|
#include <asm-generic/getorder.h>
|
|
|
|
#endif /* !__ASSEMBLY__ */
|
|
|
|
#endif
|