ASM を味わう ~ データを壊しちゃえ リベンジ ~ その5

投稿日: 2005年9月07日

<ASM を味わう  ~ データを壊しちゃえ リベンジ ~ その5>
ペンネーム:ダーリン

今週こそ、ASM のデータを壊します。

先週は ASM を構成している DISK を ALTER 文で DROP してみました。
DROP したタイミングで自動的にデータの移動が開始され、その間でもデータ
の INSERT 処理は問題なく実行できました。

今週はどうしましょうか。 DISK を引っこ抜く。それもいいですね。
でも、DISK が本当に壊れるとちょっと困るので今回はこちらの都合でデータ
を壊すことにします。

ASM は OS から見ると RAW デバイスの上で構成されています。今回の環境で
はこんな感じです。

<>

# raw -qa
/dev/raw/raw1:  bound to major 8, minor 33
/dev/raw/raw2:  bound to major 8, minor 49
/dev/raw/raw3:  bound to major 8, minor 65
/dev/raw/raw4:  bound to major 8, minor 81
/dev/raw/raw5:  bound to major 8, minor 97

<>

# cat /etc/sysconfig/rawdevices
/dev/raw/raw1 /dev/sdc1
/dev/raw/raw2 /dev/sdd1
/dev/raw/raw3 /dev/sde1
/dev/raw/raw4 /dev/sdf1
/dev/raw/raw5 /dev/sdg1

そこで、RAW デバイスに変なデータを直接書き込んでしまいましょう。

どこに書き込みましょうか。もう一度 ASM で管理されている DISK の情報を
確認します。

SQL> select a.group_number
  2       , a.name         disk_group
  3       , a.type         redundancy
  4       , b.disk_number
  5       , b.name         disk
  6       , b.failgroup
  7       , b.path
  8    from v$asm_diskgroup a,v$asm_disk b
  9   where a.group_number = b.group_number;

GROUP_NUMBER DISK_GROUP REDUNDANCY DISK_NUMBER DISK       FAILGROUP  PATH
------------ ---------- ---------- ----------- ---------- ---------- -------------
           1 DATA       NORMAL               4 DATA_0004  DATA_0004  /dev/raw/raw5
           1 DATA       NORMAL               3 DATA_0003  DATA_0003  /dev/raw/raw4
           1 DATA       NORMAL               2 DATA_0002  DATA_0002  /dev/raw/raw3
           1 DATA       NORMAL               1 DATA_0001  DATA_0001  /dev/raw/raw2

では、DATA_0001 の DISK に書き込みましょう(壊しましょう)。

では、dd コマンドで、、

$ dd if=/dev/random of=/dev/raw/raw2 count=100
dd: writing `/dev/raw/raw2′: 無効な引数です。
読み込んだブロック数は 0+100
書き込んだブロック数は 49+0

あれ?エラーになってしまいました。
でも何ブロックかは書き込んでいるようです。

それはそれとして、ASM の DISK の情報を確認して見ましょう。
先ほどと同じ SQL を実行してみます。

SQL> /

GROUP_NUMBER DISK_GROUP REDUNDANCY DISK_NUMBER DISK       FAILGROUP  PATH
------------ ---------- ---------- ----------- ---------- ---------- -------------
           1 DATA       NORMAL               4 DATA_0004  DATA_0004  /dev/raw/raw5
           1 DATA       NORMAL               3 DATA_0003  DATA_0003  /dev/raw/raw4
           1 DATA       NORMAL               2 DATA_0002  DATA_0002  /dev/raw/raw3
           1 DATA       NORMAL               1 DATA_0001  DATA_0001  /dev/raw/raw2

ふむふむ。先週と同じです。きっと、自動的にデータを移動しているはずです。
では、DATA_0001 の DISK ( /dev/raw/raw2 )の情報を見てみましょう。

SQL> select mount_status
  2       , header_status
  3       , mode_status
  4       , state
  5       , total_mb
  6       , free_mb
  7       , path
  8    from v$asm_disk;

MOUNT_STAT HEADER_STA MODE_STATUS  STATE     TOTAL_MB    FREE_MB PATH
---------- ---------- ------------ ------- ---------- ---------- ---------------
CLOSED     FORMER     ONLINE       NORMAL       10236          0 /dev/raw/raw1
CACHED     MEMBER     ONLINE       NORMAL       10236       9702 /dev/raw/raw5
CACHED     MEMBER     ONLINE       NORMAL       10236       9708 /dev/raw/raw4
CACHED     MEMBER     ONLINE       NORMAL       10236       9714 /dev/raw/raw3
CACHED     CANDIDATE  ONLINE       NORMAL       10236          0 /dev/raw/raw2

おやぁ~? もう、FREE_MB が 0 になっています。

先週の検証でデータが他の DISK に移動している最中は、徐々に FREE_MB が
増えていくことを確認しました。しかし、すべてのデータが移動した後は上記
の “/dev/raw/raw1” のように、FREE_MB が 0 になります。
このときの HEADER_STATUS は “FORMER” です。(* STATE 列だけを見ても判
断できないことは先週お話しましたね。)ところが、今回の HEADER_STATUS
は “CANDIDATE” です。先週と様子が違うようです。
そうですね、ちょっと待ってください。 DISK に異常が発生したときにデータ
が移動するのでしょうか。 それはおかしいですね、そんなことする必要があ
りません。壊れたかもしれないデータを持っていっても意味ないですね。その
ために、多重化しているのですから、正常なDISK に存在するデータを使用する
はずです。

ということは、データがおかしくなったためデータの移動処理が省かれ、いき
なり FREE_MB が 0 になったのかも知れません。ちなみに、HEADER_STATUS が
“CANDIDATE” の状態というのは、”ALTER DISKGROUP” を使ってどこかの DISK
GROUP に追加できる DISK だということのようです。
確かに、DISK 自体には問題ないので再利用できるはずです。
ということで、データを( DISK を )1つ壊すことが出来たようです。

さて、今回検証に使用している DISK Group は REDUNDANCY = NORMAL、つまり
2 多重で作成しています。ですから、DISK がひとつ壊れても、別の DISK に
ミラーデータ、あるいは、マスタデータが存在しているのでデータベースとし
ては問題なく稼動します。

では、調子に乗って、もう一本壊してみましょう。
2 多重なので 2 本同時に壊れると、”場合によっては”いってしまいます。

では、今度は、大量に書き込んで見ましょう。別の RAW デバイスのデータを
流し込んでみます。

$ dd if=/dev/raw/raw1 of=/dev/raw/raw3

読み込んだブロック数 1576778+0
書き込んだブロック数 1576778+0

DISK のステータスは、、

SQL> select mount_status
  2       , header_status
  3       , mode_status
  4       , state
  5       , total_mb   6       , free_mb
  7       , path
  8    from v$asm_disk;

MOUNT_STAT HEADER_STA MODE_STATUS  STATE     TOTAL_MB    FREE_MB PATH
---------- ---------- ------------ ------- ---------- ---------- ---------------
CLOSED     FORMER     ONLINE       NORMAL       10236          0 /dev/raw/raw1
CACHED     MEMBER     ONLINE       NORMAL       10236       9702 /dev/raw/raw5
CACHED     MEMBER     ONLINE       NORMAL       10236       9708 /dev/raw/raw4
CACHED     FORMAR     ONLINE       NORMAL       10236          0 /dev/raw/raw3
CACHED     CANDIDATE  ONLINE       NORMAL       10236          0 /dev/raw/raw2

んん?

今度は、HEADER_STATUS が “FORMER” になり、瞬時に FREE_MB が 0 になりま
した。でも、SQL は問題なく実行できているようです。つまり、/dev/raw/raw2
と raw3 はお互いのミラー DISK ではなかったのでしょう。

SQL> select * from tbl001;
    C1 C2
 ----- ------------------------
    ...........................
    99 05-08-30 15:49:36.974664
   100 05-08-30 15:49:36.974830
 
200 rows selected.

最大何本壊してもいいのでしょうか。単純に考えると、2 重化しているので最
悪 2 本のDISKがあれば大丈夫そうです。

ではせっかくここまで壊したので、ついでにもう一本壊してみましょう。

$ dd if=/dev/random of=/dev/raw/raw4

MOUNT_STAT HEADER_STA MODE_STATUS  STATE     TOTAL_MB    FREE_MB PATH
---------- ---------- ------------ ------- ---------- ---------- ---------------
CLOSED     FORMER     ONLINE       NORMAL       10236          0 /dev/raw/raw1
CACHED     MEMBER     ONLINE       NORMAL       10236       9702 /dev/raw/raw5
CACHED     CANDIDATE  ONLINE       NORMAL       10236          0 /dev/raw/raw4
CACHED     FORMAR     ONLINE       NORMAL       10236          0 /dev/raw/raw3
CACHED     CANDIDATE  ONLINE       NORMAL       10236          0 /dev/raw/raw2

今度は、ちょっと違うことをやってみましょう。
テーブルを作成してデータを増やしてみます。

SQL> create table tbl002 tablespace test001 as select * from tbl001;

Table created.

SQL> select count(*) from tbl002;

  COUNT(*)
----------
       200

SQL> insert into tbl002 select * from tbl002;

200 rows created.

SQL> /

400 rows created.

....................

SQL>

12800 rows created.
SQL> SQL> /
insert into tbl002 select * from tbl002
*
ERROR at line 1:
ORA-03113: end-of-file on communication channel

おっとっと。 しばらく INSERT はできましたが、ついに、Oracle がとまりま
した。 2 多重の設定で 2 重化 できなくなったためでしょうか。でも、可用
性を上げるための 2 重化なのに、「 2 重化するための DISK がないのでとま
ります。」なんていうのは本末転倒のような気もしますが。

今週はこの辺で一息入れましょう。

イナゴの佃煮と蜂の子どっちがおいしい? 茅ヶ崎にて