여러 가지 방법이 존재하겠지만,
db2diag.log에서 Backup Complete 메시지와 함께 정확한 사이즈가 찍혀있다.

2009-05-15-22.46.53.108696+540 I790856A473        LEVEL: Warning
PID     : 1991526              TID  : 1           PROC : db2agent (SAMPLE) 0
INSTANCE: instance             NODE : 000         DB   : SAMPLE
APPHDL  : 0-1823               APPID: *LOCAL.dbpainst.090515090122
FUNCTION: DB2 UDB, database utilities, sqlubcka, probe:128
MESSAGE : Estimated size of backup in bytes:
DATA #1 : Hexdump, 8 bytes
0x0FFFFFFFFFFEDB78 : 0000 09DD 446C 9000                        ....Dl..

2009-05-15-22.46.53.110938+540 I791330A470        LEVEL: Warning
PID     : 1991526              TID  : 1           PROC : db2agent (SAMPLE) 0
INSTANCE: instance             NODE : 000         DB   : SAMPLE
APPHDL  : 0-1823               APPID: *LOCAL.dbpainst.090515090122
FUNCTION: DB2 UDB, database utilities, sqlubcka, probe:128
MESSAGE : Actual size of backup in bytes:
DATA #1 : Hexdump, 8 bytes
0x0FFFFFFFFFFEDB80 : 0000 09DD D4D4 7000                        ......p.

2009-05-15-22.46.53.111391+540 I791801A355        LEVEL: Warning
PID     : 1991526              TID  : 1           PROC : db2agent (SAMPLE) 0
INSTANCE: instance             NODE : 000         DB   : SAMPLE
APPHDL  : 0-1823               APPID: *LOCAL.dbpainst.090515090122
FUNCTION: DB2 UDB, database utilities, sqlubcka, probe:130
MESSAGE : Backup Complete.

위의 예시에서 16진수 0000 09DD D4D4 7000 를 10진수로 변환하면
Backup image의 byte는 10,848,363,114,496 임을 알 수 있다.
Posted by in0de
,

sqllib/tmp

DB2 LUW 2009. 4. 16. 16:38

${instance home}/sqllib/tmp는 다음의 유틸리티/어플리케이션/툴 들에 의해 I/O가 발생한다.

DB2 Engine
db2 Utilities(Backup, load, import 등)
DB2 Governor
DB2 Snapshot functions
DB2 GUI tools / DB2 Wizards
  (ie. Server profile generated from the Control Center, Redistribution Data wizard) 
DB2 Extenders (ie. Text Information Extender)
any application (ie. WebSphere)


Linux의 경우, sqllib/tmp 에 named pipe를 생성하여
frontend(db2), backend(db2bp) 프로세스 간의 통신을 하기도 한다.

DB2 Engine에서의 temporary processing의 세부내용은 알 수 없겠지만
대부분의 경우는 index key sorting 이라던가
여러 utility나 application들에 의해 I/O가 발생된다고 보면 되겠다.

엔터프라이즈 시스템에서의 sqllib/tmp의 위치는 신경써서 정해야할 듯 한데
실제로 이 디렉토리를 모니터링해보면 상당히 자주, 많이 access하고있고

파일시스템에 문제가 있거나
(ie. 시만텍의 매우 오래된 VxFS 4.0.3.2 (4.0 MP3RP2)의
비효율적인 dirty page scan 알고리즘으로 인해 disk I/O의 30%를 일으켰던 경우)

좋지 못한 성능의 Internal disk에 instance home을 둔다거나 한다면
전체적으로 DB의 성능을 떨어뜨릴 수 있기 때문이다.

instance home 디렉토리는 디스크 장애에 의해서 inaccessible할 경우
DB에 대해서 어떠한 제어도 할 수 없게 되므로, 안정적인 디스크에 두어야 하며

안정적인 디스크에 instance home을 두었으나 속도가 좋지 못해,
sqllib/tmp로 인한 성능 저하가 우려되는 경우
DB 자체적으로 sqllib/tmp의 위치를 hidden parameter등으로 변경할 방법은 존재하지 않으며
다음과 같은 방법으로 성능 좋은 디스크 쪽의 디렉토리를 링크하여
안정성과 성능을 둘 다 만족시킬 수 있다.

mkdir ${better perf disk path}/newTmpPath
rm -rf ${instance home}/sqllib/tmp
ln -s ${better perf disk path}/newTmpPath ${instance home}/sqllib/tmp
Posted by in0de
,

db2diag.log 분할하기

DB2 LUW 2009. 4. 16. 14:50
db2diag.log는 db에 문제가 생겼을 때 참조할 수 있는
가장 확실하고 가장 먼저 살펴볼 제 1의 레퍼런스이다.

db2diag.log는
active log, archive log, loadcopy, dump, tablespaces 와 함께
용량관리를 해주어야 하는 대상이 되는데

db2diag 커맨드는 db2diag.log를 분석하는 포매팅 툴로서,
제공하는 기능들 중에서 -A 옵션으로, db2diag.log를 분할하여 archive 할 수 있다.

in root's crontab
59 23 * * * su - ${instance user} -c "db2diag -A ${diagpath}/db2diag.log" > /dev/null 2>&1

매일 오후 23시 59분에 db2diag.log를 db2diag.log_YYYY-MM-DD-HH.MM.SS 형태로
하루에 하나씩 db2diag.log를 새로 생성하도록 해두면
로그를 검색하기도 쉽고 오래된 로그를 백업해두거나 삭제하는 정책을 만들기도 좋다.
Posted by in0de
,
DB backup copy를 사용하여 restore를 수행할 경우,
해당 backup copy의 timestamp를 알아내야 한다.

db2 DB의 backup copy가 생성된 timestamp를 확인하는 command는 다음과 같다.

db2 list history backup since YYYYMMDD for ${dbname}

정상적인 경우에는 다음과 같이 timestamp를 확인할 수 있다.

$ db2 list history backup since 20090316 for sample |more
                    List History File for sample
Number of matching file entries = 12
 Op Obj Timestamp+Sequence Type Dev Earliest Log Current Log  Backup ID
 -- --- ------------------ ---- --- ------------ ------------ --------------
  B  D  20090316183010001   N    O  S0422805.LOG S0422879.LOG 
 ----------------------------------------------------------------------------
  Contains 276 tablespace(s):
  00001 SYSCATSPACE
  00002 USERSPACE1
              ...

그러나, 간혹 다음과 같이 조회 시 오류가 발생하는 경우가 있다.

$ db2 list history backup since YYYYMMDD for ${dbname}
                    List History File for sample
Number of matching file entries = 12
SQL2155W  Changes have been made to the recovery history file since the open
scan was issued.

이는 내부적으로 history file에 대해 open scan이 발행된 후
이를 종료하기 위한 db2HistoryCloseScan API의 호출이
비정상적이었을 경우 발생하는 오류이다.

이런 경우는
다음 SQL로 timestamp를 조회할 수도 있고,

select  timestamp(start_time) as "Start Time (min)",
          case(operationType)         when 'F'  then 'Offline Full'
                                                 when 'N' then 'Online Full'
                                                 when 'I' then 'Offline Incremental'
                                                 when 'O' then 'Online Incremental'
                                                 when 'D' then 'Offline Delta' 
                                                 when 'E' then 'Online Delta'        
          else '?'       end as Type, 
          SQLCODE
 from TABLE(ADMIN_LIST_HIST()) AS LIST_HISTORY
where  operation = 'B' ;

위의 TABLE(ADMIN_LIST_HIST()) snapshot function을 수행하는 과정에서
history file scan이 초기화 되므로
간단히 ADMIN_LIST_HIST() function을 호출한 후에
본디의 list history backup 명령을 사용해서 조회가 가능해진다.
Posted by in0de
,
Tablespace의 File System Caching 기능을 해제하여 DB2 응답 성능을 향상시킬 수 있다.

모든 I/O를 할 때, OS 레벨의 File system caching 기능을 사용하지 않고
DB2의 bufferpool만을 사용하는 개념인데,
모든 상황, 모든 버전에서 효과가 있는 지는 테스트를 해봐야 알 것 같다.

Filesystem caching On 상태

이 상태로 속도는 최초 수행 시 0.83초, 반복 수행 시 0.45초로 나타났다.
정확한 측정을 위해서는 db2batch command를 사용해야하나, 측정 결과는 크게 다르지 않다.

Alter tablespace문의 NO FILE SYSTEM CACHING command option으로 OS level의 cache를 사용하지 않도록 지정한다.
online으로 바로 적용 가능하며, Connection terminate 이후부터 반영된다.

FSC 컬럼을 보면 Filesystem caching이 해제된 것을 확인할 수 있다.

적용 후의 동일 쿼리 수행 결과

OS Caching을 bypass함으로써, 상당한 성능 향상을 볼 수 있다.

단, 다음 환경에서의 테스트에 따르면
OS : AIX 5.3, CPU : 2, Memory : 2GB, DB size : 8GB, Partition : Single, db2_parallelism_io = null
FSC OFF 할 경우 백업 속도가
36MB/sec에서 30MB/sec 정도로 느려질 수 있다는 결과가 있다.
Posted by in0de
,
SQL0101N The statement is too long or too complex.

복잡한 쿼리가 수행되는 경우이거나,
32bit 환경에서 잘 수행되던 쿼리가 64bit 환경으로 바뀌면서 발생하거나
클라이언트의 버전에 따라서 Statement heap이 모자라다는 오류가 발생할 수 있다.

Statement heap은
동적 SQL의 경우 Precompile시,
정적 Package의 경우 bind시 사용하는 공간인데
32bit 의 경우 2048, 64bit의 경우 4096이 default이며
필요 시 다음과 같이 확장할 수 있다.

db2 update db cfg for ${db} using STMTHEAP NNNN
Posted by in0de
,

db2 instance bit 변경

DB2 LUW 2008. 10. 15. 03:38
처음 db2를 배우면 db2icrt, db2idrop과 함께 기본적으로 나오는 명령어이기는 하지만,
대체 언제 이것을 써먹을 수 있을까 대충 지나쳤던 부분인데, 실제로 적용할 일이 발생했다.

32bit WAS와 bit를 맞춰야 하는데 db2를 64bit로 설치했던 것.
그래서 -w 32 옵션으로 db2iupdt로 해결 가능했다.

db2iupdt -w 32 ${instanceName}
Posted by in0de
,
참 단순한데 가끔 이런 것으로도 곤란한 경우가 있다.

원인은 double 값이 scientific notation으로 출력되는 점이다.

예를 들어
0.0001 = 1.0E-4
314.15 = 3.14E+2

이를 substr(char(${column}),1,3) 한 경우
1.0
3.1
처럼 정수 한 자리의 값들로 나오게 된다.
이런 경우 원하는 결과를 얻으려면 decimal()로 캐스팅해주어야 한다.
Posted by in0de
,

UTIL_IMPACT_PRIORITY

DB2 LUW 2008. 4. 17. 11:20
UTIL_IMPACT_PRIORITY는 DB2의 Utility의 실행 우선 순위를 지정하는 옵션이다.
그러나 DB2 UDB v8.2 현재 Runstats와 Backup에만 적용할 수 있다.

Throttle mode를 사용하려면
DBM CFG의 UTIL_IMPACT_LIM 변수를 100이 아닌 숫자값으로 설정해주어야 한다.
이 환경 변수의 권장치는 10 이하이며, 아마 default로 10이 설정되어 있을 것이다.

UTIL_IMPACT_PRIORITY를 달리 지정하지 않을 경우는 throttle을 조절하지 않고 수행된다.
사실 보통은 이 옵션을 지정하지 않기 때문에, 최대한 빨리 실행중이었다고 보면 되는데,
Online peak time이나, scheduled batch time에 runstats를 실행할 경우에 유용할 수 있다.
또한, HADR 구성에 따라 Online Reorg를 수행하지 못하는 경우에 적용할 수 있을 듯 하다.
$ db2 get dbm cfg | grep UTIL_IMPACT
   Workload impact by throttled utilities(UTIL_IMPACT_LIM) = 10
UTIL_IMPACT_PRIORITY 옵션은 숫자값 1~100을 step 1 단위로 지정해줄 수 있으며
숫자를 쓰지 않고 UTIL_IMPACT_PRIORITY 만 써준 경우는 기본적으로 50 으로 실행된다.
db2 backup db ${dbname} online UTIL_IMPACT_PRIORITY include logs
db2 runstats on table ${schema}.${table} and indexes all UTIL_IMPACT_PRIORITY 20
이미 실행중인 utility의 UTIL_IMPACT_PRIORITY를 변경하기 위해서는
db2 set UTIL_IMPACT_PRIORITY for ${utility_id} TO ${priority}

로 변경할 수 있다.
Posted by in0de
,

문자열 길이 구하기

DB2 LUW 2008. 4. 14. 08:15
db2에서 문자열의 길이를 구하려면 다음과 같이 한다.
VALUES(LENGTH(CHAR(${colname})))
위와 같이 길이를 구하면, 한글 1글자를 2byte로 count하기 때문에
유니코드 string 1글자를 1로 count하기 위해서는 다음과 같이 구한다.
VALUES(LENGTH(VARGRAPHIC(${colname})))
Posted by in0de
,