메모리 관리 방식: 수동, ASMM, AMM
수동 공유 메모리 관리, ASMM, AMM의 차이와 현재 데이터베이스가 어느 방식인지 판별하는 순서, AMM과 ASMM의 비교
#핵심 요약
메모리 관리 방식은 세 가지임
수동 공유 메모리 관리, 자동 공유 메모리 관리(ASMM), 자동 메모리 관리(AMM)
ASMM은 SGA_TARGET으로 SGA 구성 요소 사이를 자동 조정하고, AMM은 MEMORY_TARGET으로 SGA와 PGA 사이까지 자동 조정함
판별 순서는 MEMORY_TARGET이 0보다 큰가, 아니면 SGA_TARGET이 0보다 큰가, 둘 다 0이면 수동임
실습의 설명은 AMM이 설정이 간단해 개발과 소규모 DB에 쓰이고, 대형 운영 DB에는 ASMM에 PGA_AGGREGATE_TARGET과 HugePages를 쓴다는 것임
#개념과 동작 원리
| 방식 | 핵심 매개변수 | 자동으로 조정하는 범위 |
|---|---|---|
| 수동 공유 메모리 관리 | SHARED_POOL_SIZE, DB_CACHE_SIZE 등 개별 지정 |
없음 |
| 자동 공유 메모리 관리(ASMM) | SGA_TARGET |
SGA 구성 요소 사이 |
| 자동 메모리 관리(AMM) | MEMORY_TARGET |
SGA와 PGA 사이까지 |
#AMM과 ASMM의 비교
AMM은 MEMORY_TARGET 하나로 SGA와 PGA 크기를 자동 조절하는 방식임
| 구분 | AMM | ASMM |
|---|---|---|
| 메모리 관리 | SGA + PGA 자동 조절 | SGA 자동 조절, PGA 별도 설정 |
| SGA 크기 | 가변 | 비교적 안정적 |
| HugePages | 사용 어려움 | 사용 가능 |
| 주 사용 환경 | 개발, 테스트, 소규모 DB | 운영, 대용량 DB |
| 장점 | 설정 간단, 관리 편의성 | 성능, 안정성, HugePages 활용 |
AMM은 편의성 중심이고 ASMM은 운영 성능과 안정성 중심이라는 것이 실습의 요약임
#AMM의 제약
LOCK_SGA=TRUE와 함께 사용할 수 없음
공식 문서도 LOCK_SGA가 TRUE이면 AMM을 켤 수 없다고 적음(Oracle Database 19c Administrator's Guide E96348-21, 6장 Managing Memory)
Linux HugePages와 함께 사용하기 어려움
HugePages는 SGA 같은 큰 메모리 영역을 큰 페이지 단위로 관리하는 Linux 기능임
공식 문서는 Linux에서 기동 시점에 MEMORY_TARGET, MEMORY_MAX_TARGET을 명시하지 말 것을 권하며, SGA가 작은 페이지로 할당될 수 있다고 설명함USE_LARGE_PAGES=ONLY인 상태에서 이 두 값을 설정하면 인스턴스가 기동되지 않음(Oracle Database 19c Reference E96196-45, MEMORY_TARGET)
공식 문서는 인스턴스 메모리가 4GB보다 크면 설치와 DB 생성 단계에서 AMM을 고를 수 없고 ASMM을 권장한다고 적음(Administrator's Guide E96348-21, 6장)
SGA가 큰 서버에서는 4KB 페이지를 쓰면 페이지 테이블과 TLB 오버헤드가 커질 수 있음
4KB Page
-> 페이지 수 많음
-> 페이지 테이블/TLB 부담 증가
2MB HugePages
-> 페이지 수 감소
-> 메모리 관리 오버헤드 감소
-> 대용량 SGA에 유리#메모리 관리 구성 예시
개발/테스트, 소규모 DB
-> AMM
대형 운영 DB
-> ASMM + PGA_AGGREGATE_TARGET + HugePages#주요 용어와 구성 요소
| 용어 | 설명 |
|---|---|
MEMORY_TARGET |
AMM의 핵심 매개변수 SGA와 PGA 합계를 자동 조정함 |
SGA_TARGET |
ASMM의 핵심 매개변수 SGA 구성 요소 사이를 자동 조정함 |
PGA_AGGREGATE_TARGET |
PGA 별도 설정(ASMM 환경) |
SGA_MAX_SIZE |
SGA 최대 크기 파라미터 실습에서는 파라미터 조회 목록에 포함했음 |
| HugePages | 큰 메모리 영역을 큰 페이지 단위로 관리하는 Linux 기능 |
#필수 명령어 또는 SQL
#1. AMM 여부: 0이면 AMM이 아님
SHOW PARAMETER memory_target결과 해석: 개별 실행 출력은 기재 없음
#2. ASMM 여부: 0보다 크면 ASMM
SHOW PARAMETER sga_target결과 해석: 개별 실행 출력은 기재 없음
#3. 개별 구성 요소 파라미터: 수동 관리라면 값이 확인됨
SELECT name, display_value, isdefault
FROM v$parameter
WHERE name IN ('shared_pool_size', 'db_cache_size', 'large_pool_size',
'java_pool_size', 'streams_pool_size');결과 해석: 개별 실행 출력은 기재 없음
#4. 오라클이 실제로 관리하는 구성 요소 목록
SELECT component,
current_size/1024/1024 MB,
min_size/1024/1024 min_mb,
user_specified_size/1024/1024 user_mb
FROM v$memory_dynamic_components
WHERE current_size > 0;결과 해석: 개별 실행 출력은 기재 없음
#5. 판단 기준을 쿼리 하나로 확인
SELECT CASE
WHEN (SELECT TO_NUMBER(value) FROM v$parameter WHERE name='memory_target') > 0
THEN 'AMM'
WHEN (SELECT TO_NUMBER(value) FROM v$parameter WHERE name='sga_target') > 0
THEN 'ASMM'
ELSE 'MANUAL'
END AS memory_mgmt
FROM dual;결과 해석: 개별 실행 출력은 기재 없음
#6. 자동 조정이 실제로 있었는가
SELECT component, ROUND(current_size/1024/1024) cur_mb,
oper_count, last_oper_type
FROM v$memory_dynamic_components
WHERE current_size > 0;결과 해석:
OPER_COUNT가 0보다 크면 그 구성 요소가 실제로 크기를 주고받은 것이라는 것이 실습의 해석임
V$MEMORY_DYNAMIC_COMPONENTS의 실습 출력 예시
실습 기록의 출력이며 환경은 확인 불가
COMPONENT CUR_MB OPER_COUNT LAST_OPER_TYP
----------------------- ---------- ---------- -------------
shared pool 800 2 GROW
large pool 144 0 STATIC
java pool 16 0 STATIC
DEFAULT buffer cache 2128 2 SHRINK#SGA와 PGA 관련 파라미터 조회
SHOW PARAMETER SGA_TARGET
show parameter sga_max_size
show parameter pga_aggregate_target결과 해석: 개별 실행 출력은 기재 없음
#PDB별 SGA_TARGET과 SGA_MIN_SIZE
ALTER SESSION SET CONTAINER=CDB$ROOT;
COL pdb_name FOR A15
COL sga_target FOR A12
COL sga_min_size FOR A12
SELECT p.name AS pdb_name,
MAX(CASE WHEN s.name='sga_target'
THEN CASE WHEN REGEXP_LIKE(s.value$,'^\d+$')
THEN TO_CHAR(TO_NUMBER(s.value$)/1024/1024)||'M'
ELSE s.value$ END END) AS sga_target,
MAX(CASE WHEN s.name='sga_min_size'
THEN CASE WHEN REGEXP_LIKE(s.value$,'^\d+$')
THEN TO_CHAR(TO_NUMBER(s.value$)/1024/1024)||'M'
ELSE s.value$ END END) AS sga_min_size
FROM pdb_spfile$ s
JOIN v$pdbs p ON p.con_uid = s.pdb_uid
WHERE s.name IN ('sga_target','sga_min_size')
GROUP BY p.name
ORDER BY p.name;결과 해석: 개별 실행 출력은 기재 없음
#메모리 어드바이저로 크기 판단하기
Oracle은 구성 요소 크기를 바꿨을 때의 효과를 추정해 어드바이저 뷰에 보여 줌
근거가 되는 부하 기간은 AWR 스냅샷으로 확인함
SELECT sga_size, sga_size_factor, estd_db_time, estd_physical_reads
FROM v$sga_target_advice ORDER BY sga_size;
SELECT pga_target_for_estimate/1024/1024 pga_mb, pga_target_factor,
estd_pga_cache_hit_percentage, estd_overalloc_count
FROM v$pga_target_advice ORDER BY pga_target_for_estimate;
SELECT size_for_estimate mb, size_factor, estd_physical_read_factor, estd_physical_reads
FROM v$db_cache_advice
WHERE name = 'DEFAULT' AND advice_status = 'ON';
SELECT shared_pool_size_for_estimate mb, shared_pool_size_factor, estd_lc_time_saved
FROM v$shared_pool_advice;
SELECT snap_id, begin_interval_time, end_interval_time
FROM dba_hist_snapshot ORDER BY snap_id DESC FETCH FIRST 5 ROWS ONLY;EXEC DBMS_WORKLOAD_REPOSITORY.CREATE_SNAPSHOT;
@?/rdbms/admin/awrrpt.sql결과 해석:
실습 서버는 부하가 없어 어드바이저 값이 평평하게 나옴
수업 자료는 PGA가 실제로 모자란 서버(PGA_AGGREGATE_TARGET 2048M)를 가정한 아래 예로 읽는 법을 설명함(실측값이 아니라 설명용 예시)
| PGA_MB | 배수 | 추정 캐시 적중률(%) | ESTD_OVERALLOC_COUNT |
|---|---|---|---|
| 1024 | 0.5 | 58 | 615 |
| 2048 | 1 | 71 | 12 |
| 2458 | 1.2 | 78 | 0 |
| 3277 | 1.6 | 91 | 0 |
| 4096 | 2 | 99 | 0 |
| 6144 | 3 | 100 | 0 |
ESTD_OVERALLOC_COUNT가 0이 되는 첫 지점이 하한선임
0이 아니면 그 크기로는 부족하다는 뜻이라, 현재값 2048M은 이미 부족함- 적중률 증가폭이 꺾이는 지점(무릎)이 권장 지점임
4096M에서 6144M으로 2GB를 더 늘려도 1%만 오르므로 4096M이 권장이고 그 이상은 낭비임 - 어드바이저 숫자만으로는 근거가 얇으므로 작업 영역 처리 실적을 함께 봄
SELECT low_optimal_size/1024 low_kb,
optimal_executions, onepass_executions, multipasses_executions
FROM v$sql_workarea_histogram
WHERE total_executions > 0;결과 해석: MULTIPASSES_EXECUTIONS가 0이 아니면 정렬과 해시가 메모리에 다 들어가지 못해 임시 테이블스페이스를 여러 번 오갔다는 뜻이고, 그 자체가 PGA 증설 근거가 됨
#구문과 옵션 설명
| 구문 | 의미 | 바꿀 입력값 | 결과 해석 |
|---|---|---|---|
SHOW PARAMETER memory_target |
AMM 사용 여부 확인 | 파라미터 이름 | 값이 0이면 AMM이 아님 |
SHOW PARAMETER sga_target |
ASMM 사용 여부 확인 | 파라미터 이름 | MEMORY_TARGET이 0일 때 0보다 크면 ASMMAMM에서는 SGA 최솟값 |
v$parameter의 isdefault |
기본값 여부 | 조회할 파라미터 이름 목록 | TRUE는 DBA가 지정한 값이 아님 |
v$memory_dynamic_components의 current_size > 0 |
실제로 관리 중인 구성 요소만 표시 | 없음 | min_size, user_specified_size를 MB로 함께 봄 |
OPER_COUNT, LAST_OPER_TYPE |
크기 조정 횟수와 마지막 조정 종류 | 없음 | 0보다 크면 크기를 주고받은 것 예시에서는 GROW, SHRINK, STATIC |
ALTER SESSION SET CONTAINER=CDB$ROOT |
현재 세션의 컨테이너를 CDB$ROOT로 변경 | 이동할 컨테이너 이름 | 세션 설정만 바뀌고 객체나 데이터는 바뀌지 않음 이후 SQL은 CDB$ROOT에서 실행됨 |
pdb_spfile$ + v$pdbs |
PDB별로 저장된 sga_target, sga_min_size 값 |
조회할 파라미터 이름 | 숫자면 MB로 환산해 M을 붙이고 아니면 저장된 값을 그대로 표시 |
#사용 조건과 주의사항
실습의 비교표에서 "주 사용 환경"은 일반적 경향을 적은 것이며 모든 환경에 적용되는 규칙으로 읽으면 안 됨