heterodb/pg-strom

[VTJ-JP]Crash in partitioning table

Closed this issue · 3 comments

概要

パーティショニングテーブルに対するクエリを実施したところ、PG-Stromがクラッシュしました。具体的には Star schema benchmark(ssb)実施中で、特定のクエリで落ちるわけではなく、毎度異なるクエリにてクラッシュします(13個すべてのクエリを無事に終えることもあります)。

エラー内容例

$ ./run-ssbm_partitions_gpuonly.sh "-Upostgres ssb" "shachi_s400_partitionGPUonly_04"
vm.drop_caches = 1
psql:sqls/ssbm-all-strom_partitions.sql:129: WARNING:  terminating connection because of crash of another server process
DETAIL:  The postmaster has commanded this server process to roll back the current transaction and exit, because another server process exited abnormally and possibly corrupted shared memory.
HINT:  In a moment you should be able to reconnect to the database and repeat your command.
psql:sqls/ssbm-all-strom_partitions.sql:129: server closed the connection unexpectedly
        This probably means the server terminated abnormally
        before or while processing the request.
psql:sqls/ssbm-all-strom_partitions.sql:129: error: connection to server was lost
vm.drop_caches = 1
psql: error: connection to server on socket "/var/run/postgresql/.s.PGSQL.5432" failed: FATAL:  the database system is in recovery mode
vm.drop_caches = 1
psql: error: connection to server on socket "/var/run/postgresql/.s.PGSQL.5432" failed: FATAL:  the database system is in recovery mode

Crash dump

(gdb) bt
#0  GpuJoinInnerPreload (pts=pts@entry=0x1928440) at gpu_join.c:2254
#1  0x00007f5d06f68f68 in __pgstromExecTaskOpenConnection (pts=0x1928440) at executor.c:1811
#2  pgstromExecTaskState (node=0x1928440) at executor.c:1858
#3  0x00000000006bd5d7 in ExecAppend ()
#4  0x00000000006c174a in ExecGather ()
#5  0x00000000006b7a31 in fetch_input_tuple ()
#6  0x00000000006bae9f in ExecAgg ()
#7  0x00000000006d7f3e in ExecSort ()
#8  0x00000000006a79d3 in standard_ExecutorRun ()
#9  0x000000000084469e in PortalRunSelect ()
#10 0x00000000008459d0 in PortalRun ()
#11 0x0000000000841d9b in exec_simple_query ()
#12 0x000000000084352f in PostgresMain ()
#13 0x00000000007bde63 in ServerLoop ()
#14 0x00000000007bee2d in PostmasterMain ()
#15 0x0000000000506ddf in main ()

再現方法

PG-Strom付属のスクリプトで作成した ssb実施環境が既にあるものとします(今回は s=400でデータを作成した環境)。

パーティションテーブルとデータの作成

-- パーティションテーブルの作成
CREATE TABLE lineorder_pn (
    LIKE lineorder
)
PARTITION BY RANGE(lo_orderdate);

CREATE TABLE lineorder_pn_1992 PARTITION OF lineorder_pn FOR VALUES FROM (19000101) TO (19930101);
CREATE TABLE lineorder_pn_1993 PARTITION OF lineorder_pn FOR VALUES FROM (19930101) TO (19940101);
CREATE TABLE lineorder_pn_1994 PARTITION OF lineorder_pn FOR VALUES FROM (19940101) TO (19950101);
CREATE TABLE lineorder_pn_1995 PARTITION OF lineorder_pn FOR VALUES FROM (19950101) TO (19960101);
CREATE TABLE lineorder_pn_1996 PARTITION OF lineorder_pn FOR VALUES FROM (19960101) TO (19970101);
CREATE TABLE lineorder_pn_1997 PARTITION OF lineorder_pn FOR VALUES FROM (19970101) TO (19980101);
CREATE TABLE lineorder_pn_1998 PARTITION OF lineorder_pn FOR VALUES FROM (19980101) TO (19990101);
CREATE TABLE lineorder_pn_1999 PARTITION OF lineorder_pn FOR VALUES FROM (19990101) TO (20000101);

-- データの投入
INSERT INTO lineorder_pn SELECT * FROM lineorder;

スクリプトの書き換え

ssb実施SQLの、lineorder テーブルを参照していたところを、lineorder_pnテーブルを参照するように書き換える。

$ cat ssbm-all-pgsql.sql | sed 's/lineorder/lineorder_pn/g' > ssbm-all-pgsql_partitions.sql 
$ cat ssbm-all-strom.sql | sed 's/lineorder/lineorder_pn/g' > ssbm-all-strom_partitions.sql 

--スクリプトの書き換え
$ cat run-ssbm.sh | sed -e 's/ssbm-all-pgsql.sql/ssbm-all-pgsql_partitions.sql/g' -e 's/ssbm-all-strom.sql/ssbm-all-strom_partitions.sql/g' > run-ssbm_partitions.sh

kaigaiさんより、max_parallel_workers_per_gather をゼロにした場合の挙動についてお尋ねがあったので、動作を確認しました。

ssb実施スクリプトの冒頭にある
SET max_parallel_workers_per_gather = 2;SET max_parallel_workers_per_gather = 0; に書き換えて、GPUのベンチマーク実施。 エラーが発生することなく処理が完了しました。

c449cbf7d0a0779c0e4fc3b4ba87e12c477d8f40 で直しました。

あるプロセスが GpuJoinInnerPreload() に突入した時に、既にINNER_PHASE__SCAN_RELATIONS状態が終わってたが、
まだINNER_PHASE__SETUP_BUFFERS状態であった場合、ローカルで Inner 側から読み込んだタプルを保持してある
preload_bufferをノーチェックで触っていた。⇒ ぬるぽ ⇒ ガッ!

何も読み込んでいないプロセスはバッファのセットアップに寄与しないので、そのままスキップする処理を付加。

同じベンチマークスクリプトを流したところ、エラーなく完了するようになりました。

c449cbf7d0a0779c0e4fc3b4ba87e12c477d8f40 の2つあとのコミット 863ac4832c692d28d6421aa75376ca6f7a003d22 で確認