각 OS별로 각 SQL 버전에서 지원하는 최대 메모리 입니다.
정리 해놓으면 좋을 듯 하여 올려 둡니다.


Windows Server (32bit )

OS

 

WINDOWS(32BIt)

 2003(SP2)

 2003(R2)

2008

STD

ENT

STD

ENT

STD

ENT

OS (Max CPU soket)

4

8

4

8

4

8

OS (Max Memory)

4

64

4

64

4

64

SQL SERVER
(32BIT Max Memory)

STD

2K(SP4)

4

64

4

64

4

64

2K5(OS MAX)

4

64

4

64

4

64

2K8(OS MAX)

4

64

4

64

4

64

2K8(R2)  64GB(MAX)

4

64

4

64

4

64

ENT

2K(SP4)

4

64

4

64

4

64

2K5(OS MAX)

4

64

4

64

4

64

2K8(OS MAX)

4

64

4

64

4

64

2K8(R2) 2048GB(MAX)

4

64

4

64

4

64

 

Windows Server (64bit )

OS

WINDOWS(64BIT)

 2003(SP2)

 2003(R2)

2008

  2008(R2)

STD

ENT

STD

ENT

STD

ENT

STD

ENT

OS (Max CPU soket)

4

8

4

8

4

8

4

8

OS (Max Memory)

32

1024

32

1024

32

1024

32

2048

SQL SERVER
(32BIT Max Memory)

STD

2K(SP4)

-

-

-

-

-

-

-

-

2K5(OS MAX)

32

64

32

64

32

64

32

64

2K8(OS MAX)

32

64

32

64

32

64

32

64

2K8(R2) 64GB(MAX)

32

64

32

64

32

64

32

64

ENT

2K(SP4)

-

-

-

-

-

-

-

-

2K5(OS MAX)

32

64

32

64

32

64

32

64

2K8(OS MAX)

32

64

32

64

32

64

32

64

2K8(R2) 2048GB(MAX)

32

64

32

64

32

64

32

64

SQL SERVER
(64BIT Max Memory)

STD

2K5(OS MAX)

32

1024

32

1024

32

1024

32

2048

2K8(OS MAX)

32

1024

32

1024

32

1024

32

2048

2K8(R2)   64GB(MAX)

32

64

32

64

32

64

32

64

ENT

2K5(OS MAX)

32

1024

32

1024

32

1024

32

2048

2K8(OS MAX)

32

1024

32

1024

32

1024

32

2048

2K8(R2) 2048GB(MAX)

32

1024

32

1024

32

1024

32

2048

 

 

※참고
STD              :     Standard version
ENT              :     Enterprise version
OS MAX        :     OS 가 지원하는 최대 메모리



참고 링크

http://technet.microsoft.com/ko-kr/windowsserver/bb430827.aspx
http://msdn.microsoft.com/ko-kr/library/ms143506.aspx
http://msdn.microsoft.com/ko-kr/library/ms143506(v=SQL.100).aspx
http://msdn.microsoft.com/ko-kr/library/ms143506(v=SQL.90).aspx
http://support.microsoft.com/kb/918035/ko
http://technet.microsoft.com/ko-kr/library/cc917618(en-us).aspx

신고
Posted by blushine

요즘 출시되는 인텔의 제온, AMD의 옵테론 프로세스는 64bit(x64)를 기본적으로 지원되고 있고 있으며SQL Server 2005부터는 x64 를 지원하고 있습니다.(IA64 SQL Server 2000도 지원함)

 

기존 x86 AWE메모리의 한계와 IA64 도입에 대한 높은 도입 비용으로 인해 x64 환경이 점차 늘어나고 있는 상황입니다.

32bit에서 4GB이상의 메모리를 사용하기 위해서는 AWE 옵션을 Enable해서 64GB까지 사용할 수 있지만,


AWE
로 확장된 메모리 영역은 데이터&인덱스 페이지로만 구성되기에 다른 영역의 메모리는 기존처럼 2GB(/3GB 추가시 3GB) 공간만을 사용할 수 밖에 없습니다.

AWE에서 확장된 메모리를 map, unmap을 하기 위한 Window도 이 2GB에 포함되기에 잠금, 플랜 캐쉬, 연결, 쓰레드 스택에 대해 메모리 부족현상이 발생할 수 있습니다.


이러한 x86의 한계를 근본적으로 해결해 줄 수 있는 것이 64bit 시스템입니다.

또한 x64의 경우는 IA64보다 현저히 저렴하게 구성할 수 있기에 적은 투자비용으로 위와 같은 문제를 해결 할 수 있습니다.

 

기존의 여러 개의 SQL Server 2000으로 구성된 DB를 메모리 제한이 없는 SQL server 2005 x64 standard edition으로 Scale-up을 계획하시거나 사용 중이시라면 주의하게 살펴봐야 할 것 중에 하나는 바로 “Lock pages in memory” 정책의 활성화 여부입니다.

 

Standard edition(x64) 은 “Lock pages in memory” 정책을 지원하지 않습니다.(x86 Standard는 “Lock pages in memory” 정책 지원함)

 

이 정책이 뭐길래~ edition에 따라 지원 여부가 달라질까요?

BOL에서는 Lock pages in memory 정책을 아래와 같이 설명 하고 있습니다.

정책은 데이터를 실제 메모리에 유지하는 프로세스를 사용하여 시스템이 디스크의 가상 메모리로 데이터를 페이징하지 않도록 방지할 있는 계정을 결정합니다. SQL Server에서는 Lock Pages in Memory 옵션이 기본적으로 OFF 설정됩니다. 시스템 관리자 권한이 있으면 Windows 그룹 정책 도구(gpedit.msc) 사용하여 수동으로 옵션을 설정하고 SQL Server 실행 중인 계정에 사용 권한을 할당할 있습니다.

Lock Pages in Memory 옵션 설정하는 방법은 방법: Lock Pages in Memory 옵션 설정(Windows) 참조하십시오.

반드시 필요한 것은 아니지만 64비트 운영 체제를 사용하는 경우 메모리의 페이지를 잠그는 것이 좋습니다. 32비트 운영 체제의 경우 SQL Server 맞게 AWE 구성하기 전에 Lock pages in memory 권한을 얻어야 합니다.

 

x64환경에서 제공하는 거의 무한대의 VAS영역으로 인해서 프로세스의 Working Set paged out될 가능성이 x86환경보다 높습니다.

그리고 이러한 paged out SQL Server서비스가 올라가 있는 장비에서 발생한다면 SQL Server는 아래와 같은 메시지와 함께 성능적인 문제가 발생할 것입니다.

 

Enterprise edition이라면 이 정책을 사용하여 문제를 해결 할 수 있지만, Standard edition에서는 이러한 문제가 발생할 경우 이 정책을 사용할 수 없게 되어서 문제가 될 수 있습니다.

이러한 문제가 발생 할 가능성이 있다면 도입 전 테스트 등의 확인 작업이 필요할 것으로 보입니다.

 

2008-08-08 13:53:56.240 spid1s       A significant part of sql server process memory has been paged out. This may result in a performance degradation. Duration: 337 seconds. Working set (KB): 2393904, committed (KB): 6292600, memory utilization: 38%.

2008-08-08 13:58:23.660 spid1s       A significant part of sql server process memory has been paged out. This may result in a performance degradation. Duration: 604 seconds. Working set (KB): 2844740, committed (KB): 6292344, memory utilization: 45%.


송 혁, SQL Server MVP
sqler.pe.kr // sqlleader.com
hyoksong.tistory.com // nexondbteam.tistory.com

 

신고
Posted by 송혁 - HyokSong

아래의 김정선님이 번역한 글을 참조하여, 테스트 및 고민을 하였습니다.

번역본: http://blog.naver.com/visualdb/50028175660
원문 : http://blogs.msdn.com/queryoptteam/archive/2006/04/12/575241.aspx


위에서 설명하는 비슷한 시나리오를 생각해 보면,
어떤 회사의 주문 테이블이 있고, 주문 테이블은 생성일 순으로 일련되게 데이터가 저장되고 있습니다.
생성일에 넌 클러스터 인덱스가 있으며, 데이터는 = 로 비교하며, 선택도는 0.5% 정도 입니다.

이런경우에 그냥 쿼리를 수행하여 처리하면, 각각의 환경마다 틀리겠지만 테이블 SCAN을 하여 쿼리의 결과를 던져 주게 됩니다.
하지만, 위와 같은 테이블이라면, 생성일로 걸려있는 넌클러스터 인덱스를 활용하여 처리 하면 보다 좋은 성능을 가져 올수도 있습니다.
(물론 생성일을 클러스터 인덱스로 건다면, 문제가 끝나지만 그렇지 못한 환경을 이야기 하고 있는 겁니다.)

아래 테스트는 일련되게, 일련되지 않게 데이터를 입력하여 테스트를 하였습니다.
아래 인덱스 힌트를 준 플랜을 잘 살펴보면 인덱스 SEEK한 후 BML을 하기전, RID를 가지고 정렬하는 것을 볼 수 있습니다.
보다 좋은 cachehitRatio를 가지기 위해서 SORT연산자가 추가된 것을 확인 할 수 있습니다.

일련되게 저장된 경우 FULL SCAN보다 BML에서 성능이 좋을 수 있는 이유는 물리적 디스크의 순차적 읽기를 하여, 보다 빠른 물리적 응답으로인한 것이라고 생각되지는 않습니다.
이 경우 미리읽기가 가장 큰 변수일 것 같은데, 아래와 같은 쿼리는 어쩔 수 없이 IAM기반의 미리읽기가 아닌, 인덱스 레벨의 미리읽기가 발생하여 제대로된 순차 읽기를 할 수 없기 때문입니다.

그럼 무엇 때문에 차이가?
일련되게 데이터가 저장되었기 때문에 하나의 페이지에는 같은 키값의 데이터가 밀집되었으므로, 보다 적은 페이지에, 원하는 데이터가 모두 존재하기 때문에 보다 좋은 성능을 가져온게 아닌가 생각이 듭니다.

다른 방법으로도 처리 할 수 있지만,
이러한 특이한 비지니스를 가지고 있다면 충분히 고려를 해볼 수는 있을 것 같습니다.

다른 의견 및 잘못된 부분이 있다면 알려주시길 바랍니다.

송 혁, SQL Server MVP
sqler.pe.kr
nexondbteam.tistory.com


@@버전
Microsoft SQL Server 2005 - 9.00.3175.00 (Intel X86)
    Jun 14 2007 09:20:57
    Copyright (c) 1988-2005 Microsoft Corporation
    Standard Edition on Windows NT 5.2 (Build 3790: Service Pack 2)


USE TEST

GO

DROP TABLE tbl1

DROP TABLE tbl2


--정렬된 샘플 데이터 만들기

SELECT TOP 10000000

    cast(ROW_NUMBER() over(order by A.id) / 50000 as int) col1

    ,ROW_NUMBER() over(order by A.id) col2

    ,cast('HyokSong' as char(50))col3

INTO tbl1

FROM sys.sysindexes A, sys.sysindexes B,sys.sysindexes C,sys.sysindexes D,sys.sysindexes E

ORDER BY ROW_NUMBER() over(order by A.id)


--정렬되지 않은 샘플 데이터 만들기

SELECT *

INTO tbl2

FROM tbl1 with(nolock)

ORDER BY NEWID()


--넌클 인덱스 추가

create index ix_tbl1_col1 on tbl1(col1)

create index ix_tbl1_col1 on tbl2(col1)


/*

SET STATISTICS PROFILE ON

SET STATISTICS IO ON

SET STATISTICS TIME ON

*/


/*--BP 날리기

checkpoint 1

DBCC DROPCLEANBUFFERS

*/


--=====================================[정렬된]

SELECT * FROM tbl1 where col1 = 98

|--Parallelism(Gather Streams)

|--Table Scan(OBJECT:([TEST].[dbo].[tbl1]), WHERE:([TEST].[dbo].[tbl1].[col1]=(98)))

테이블'tbl1'. 검색수5, 논리적읽기수87721, 물리적읽기수0, 미리읽기수87465

CPU 시간= 5625ms, 경과시간= 8256ms.


SELECT * FROM tbl1 WITH(INDEX(2)) where col1 = 98

|--Parallelism(Gather Streams)

|--Nested Loops(Inner Join, OUTER REFERENCES:([Bmk1000], [Expr1005]) WITH UNORDERED PREFETCH)

|--Sort(ORDER BY:([Expr1004] ASC))

| |--Compute Scalar(DEFINE:([Expr1004]=BmkToPage([Bmk1000])))

| |--Index Seek(OBJECT:([TEST].[dbo].[tbl1].[ix_tbl1_col1]), SEEK:([TEST].[dbo].[tbl1].[col1]=(98)) ORDERED FORWARD)

|--RID Lookup(OBJECT:([TEST].[dbo].[tbl1]), SEEK:([Bmk1000]=[Bmk1000]) LOOKUP ORDERED FORWARD)

테이블'tbl1'. 검색수5, 논리적읽기수50126, 물리적읽기수386, 미리읽기수169

테이블'Worktable'. 검색수0, 논리적읽기수0, 물리적읽기수0, 미리읽기수0

CPU 시간= 704ms, 경과시간= 1320ms.


--=====================================[정렬되지 않은]

SELECT * FROM tbl2 where col1 = 98

|--Parallelism(Gather Streams)

|--Table Scan(OBJECT:([TEST].[dbo].[tbl2]), WHERE:([TEST].[dbo].[tbl2].[col1]=(98)))

테이블'tbl2'. 검색수5, 논리적읽기수87721, 물리적읽기수0, 미리읽기수87657

CPU 시간= 5735ms, 경과시간= 7029ms.


SELECT * FROM tbl2 WITH(INDEX(2)) where col1 = 98

|--Parallelism(Gather Streams)

|--Nested Loops(Inner Join, OUTER REFERENCES:([Bmk1000], [Expr1005]) WITH UNORDERED PREFETCH)

|--Sort(ORDER BY:([Expr1004] ASC))

| |--Compute Scalar(DEFINE:([Expr1004]=BmkToPage([Bmk1000])))

| |--Index Seek(OBJECT:([TEST].[dbo].[tbl2].[ix_tbl1_col2]), SEEK:([TEST].[dbo].[tbl2].[col1]=(98)) ORDERED FORWARD)

|--RID Lookup(OBJECT:([TEST].[dbo].[tbl2]), SEEK:([Bmk1000]=[Bmk1000]) LOOKUP ORDERED FORWARD)

테이블'tbl2'. 검색수5, 논리적읽기수50126, 물리적읽기수4, 미리읽기수38262

테이블'Worktable'. 검색수0, 논리적읽기수0, 물리적읽기수0, 미리읽기수0

CPU 시간= 2578ms, 경과시간= 13153ms.


/*

SET STATISTICS PROFILE OFF

SET STATISTICS IO OFF

SET STATISTICS TIME OFF

*/

신고
Posted by 송혁 - HyokSong


티스토리 툴바