ZONE_DMA, ZONE_NORMAL, ZONE_HIGHMEM (미완성)

구본규 2013.10.15 13:04 조회 수 : 32766

스터디 중 자주 나오는 'zone'에 대한 개념에 대한 정리가 잘 되지 않아 조사하는 중입니다.

'zone이란 무엇이고, zone type에 따라 나누는 이유는 무엇이고 각각은 어떻게 사용되는가?'에 대한 답을 찾아 보고자 합니다.


kernel에서 사용하는 zone type은 열거형으로 include/linux/mmzone.h 에 선언되어 있습니다.


enum zone_type {
#ifdef CONFIG_ZONE_DMA
	/*
	 * ZONE_DMA is used when there are devices that are not able
	 * to do DMA to all of addressable memory (ZONE_NORMAL). Then we
	 * carve out the portion of memory that is needed for these devices.
	 * The range is arch specific.
	 *
	 * Some examples
	 *
	 * Architecture		Limit
	 * ---------------------------
	 * parisc, ia64, sparc	<4G
	 * s390			<2G
	 * arm			Various
	 * alpha		Unlimited or 0-16MB.
	 *
	 * i386, x86_64 and multiple other arches
	 * 			<16M.
	 */
	ZONE_DMA,
#endif
#ifdef CONFIG_ZONE_DMA32
	/*
	 * x86_64 needs two ZONE_DMAs because it supports devices that are
	 * only able to do DMA to the lower 16M but also 32 bit devices that
	 * can only do DMA areas below 4G.
	 */
	ZONE_DMA32,
#endif
	/*
	 * Normal addressable memory is in ZONE_NORMAL. DMA operations can be
	 * performed on pages in ZONE_NORMAL if the DMA devices support
	 * transfers to all addressable memory.
	 */
	ZONE_NORMAL,
#ifdef CONFIG_HIGHMEM
	/*
	 * A memory area that is only addressable by the kernel through
	 * mapping portions into its own address space. This is for example
	 * used by i386 to allow the kernel to address the memory beyond
	 * 900MB. The kernel will set up special mappings (page
	 * table entries on i386) for each page that the kernel needs to
	 * access.
	 */
	ZONE_HIGHMEM,
#endif
	ZONE_MOVABLE,
	__MAX_NR_ZONES
};



위 파일에서 CONFIG_DMA 가 들어갔을 때 ZONE_DMA가 선언되는데,

comment를 살펴보면 i386은 16MB 영역이지만, arm은 'Various(여러가지)'입니다.


Documentation/arm/memory.txt를 보면 dma에서 사용하는 VA 영역이 나타나 있습니다.


Start        End        Use
--------------------------------------------------------------------------
...
ffc00000    ffefffff    DMA memory mapping region.  Memory returned
                by the dma_alloc_xxx functions will be
                dynamically mapped here.

ff000000    ffbfffff    Reserved for future expansion of DMA
                mapping region.
...


메일링 리스트 중 Russell King의 답장에서 ARM의 memory 정책에 대한 내용을 찾을 수 있습니다.

https://lkml.org/lkml/2011/7/6/249


Date	Wed, 6 Jul 2011 18:15:42 +0100
From	Russell King - ARM Linux <>
Subject	Re: [PATCH 6/8] drivers: add Contiguous Memory Allocator


On Wed, Jul 06, 2011 at 11:19:00AM -0500, Christoph Lameter wrote:
> What I described is the basic memory architecture of Linux. I am not that
> familiar with ARM and the issue discussed here. Only got involved because
> ZONE_DMA was mentioned. The nature of ZONE_DMA is often misunderstood.
> 
> The allocation of the memory banks for the Samsung devices has to fit
> somehow into one of these zones. Its probably best to put the memory banks
> into ZONE_NORMAL and not have any dependency on ZONE_DMA at all.

Let me teach you about the ARM memory management on Linux.

Firstly, lets go over the structure of zones in Linux.  There are three
zones - ZONE_DMA, ZONE_NORMAL and ZONE_HIGHMEM.  These zones are filled
in that order.  So, ZONE_DMA starts at zero.  Following on from ZONE_DMA
is ZONE_NORMAL memory, and lastly ZONE_HIGHMEM.

At boot, we pass all memory over to the kernel as follows:

1. If there is no DMA zone, then we pass all low memory over as ZONE_NORMAL.

2. If there is a DMA zone, by default we pass all low memory as ZONE_DMA.
   This is required so drivers which use GFP_DMA can work.

   Platforms with restricted DMA requirements can modify that layout to
   move memory from ZONE_DMA into ZONE_NORMAL, thereby restricting the
   upper address which the kernel allocators will give for GFP_DMA
   allocations.

3. In either case, any high memory as ZONE_HIGHMEM if configured (or memory
   is truncated if not.)

So, when we have (eg) a platform where only the _even_ MBs of memory are
DMA-able, we have a 1MB DMA zone at the beginning of system memory, and
everything else in ZONE_NORMAL.  This means GFP_DMA will return either
memory from the first 1MB or fail if it can't.  This is the behaviour we
desire.

Normal allocations will come from ZONE_NORMAL _first_ and then try ZONE_DMA
if there's no other alternative.  This is the same desired behaviour as
x86.

So, ARM is no different from x86, with the exception that the 16MB DMA
zone due to ISA ends up being different sizes on ARM depending on our
restrictions.


CONFIG_DMA가 정의 안 되어 있으면 ZONE_NORMAL로,

정의되어 있으면 일반적으로 lowmem이 ZONE_DMA로 들어갑니다.


vexpress에서는 CONFIG_DMA와 CONFIG_HIGHMEM이 모두 꺼져 있어 모두 ZONE_NORMAL로 들어갔지만,

다른 시스템에서 CONFIG_DMA와 CONFIG_HIGHMEM을 켜놓고 빌드한 결과 ZONE_DMA와 ZONE_HIGHMEN만 생성되었습니다.



코드는 다음에 이어서 정리하겠습니다.

번호 제목 글쓴이 날짜 조회 수
공지 [공지] 커널 스터디 관련 Q&A 게시판 입니다. [5] woos 2016.04.09 2194
1745 setup.c 파일의 cacheid_init 함수 [1] file HyunGyu 2013.11.05 72264
1744 Vol.1의 CMPS ~ CVTPD2PS 입니다. 늦어서 죄송합니다. file 지현구 2007.03.10 64199
1743 as86(1) - Linux man page 입니다. 김민석 2010.04.30 36679
1742 lilo.c에서 !! 관한 토론? [6] 오시리스 2011.07.25 34354
1741 [ARM중] 1차 분석 복습 [5] file 홍문화 2011.08.08 33707
» ZONE_DMA, ZONE_NORMAL, ZONE_HIGHMEM (미완성) 구본규 2013.10.15 32766
1739 fork() 함수가 리턴을 두번하는 이유 설명 [2] 커널B조 2016.05.07 30223
1738 task_struct 구조체입니다. [1] file 아폴로 2013.04.30 29853
1737 ARM 프로세서 모드 [7] 홍문화 2011.06.08 26499
1736 BIOS 를 통하여 PCI configuration space를 액세스하는 방법 지현구 2007.08.12 22864
1735 파이프라인과 익셉션의 관계 관련 블로그 주소입니다. 이한울 2012.05.26 22081
1734 buildroot 사용법 [1] 구본규 2012.07.20 20240
1733 [x86] 스터디때 나왔던 cpu_dev 문제 [2] file pororo 2012.02.19 18429
1732 페이지 테이블에 주소 변환 정보가 채워지는 원리 [16] 홍문화 2011.07.12 16325
1731 odroid bootlog 입니다 박장운 2010.08.14 15560
1730 명령어 정리 - 늦어서 죄송.. 송형주 2007.03.09 14524
1729 Linux booting 과정 (start_kernel() 함수 전까지) 관련 참고자료들 모음 file 지현구 2007.04.27 14328
1728 분석 환경 구축 실습 [11] file 권석민 2013.05.19 14204
1727 [x86] 가족번호 [2] pororo 2012.02.27 13912
1726 LVM에 대해 간략하게 정리했습니다. [2] file 조성진 2013.05.07 13825
XE Login