当前位置:网站首页>PostgreSQL source code (57) why is the performance gap so large in hot update?
PostgreSQL source code (57) why is the performance gap so large in hot update?
2022-07-01 23:28:00 【mingjie73】
relevant
《Postgresql Source code (52)bitmapset analysis RelationGetIndexAttrBitmap》
《Postgresql Source code (57)HOT Why is the performance gap between updates so large ?》
background
PostgreSQL Multi version implementation , Heap pages are multiple versions , The index page is a single version . If you update a heap page , The new element group is actually direct append To the table , Old tuple tags are not visible .
At the same time, the index also needs to add a , But the index can be optimized , The method is to form a linked list of old and new table tuples , Use the old index to point to the old tuple , Then point from the old tuple to the new group .
This is it. PG Of HOT Renewal mechanism , stay 8.3 This optimization is introduced after version , The write amplification problem under multiple versions has been optimized to a great extent .
1 HOT And non HOT Update performance gap
result
- The test environment is kvm virtual machine 16C, Disk performance is poor .( Loose testing )
- The reason for the large difference in results is mainly due to the two test scenarios IO Is played ,IO The increase in the proportion of impacts has caused a large gap
- IO When all are full ,HOT Are updating the table page ,NOHOT Also update many index pages .
- Let's analyze later when we will leave HOT?(2.2 Step six of )
- Meet three conditions :
- BUFFER unchanged
- hot_attrs_checked:PAGE Not full
- modified_attrs: Some index columns have been modified
- Meet three conditions :
TPS | |
---|---|
HOT | 6035.041159 |
NOHOT | 2447.563057 |
IO Status interception
nohot
transaction type: ./test_nohot.sql
scaling factor: 1
query mode: prepared
number of clients: 32
number of threads: 32
duration: 120 s
number of transactions actually processed: 293701
latency average = 13.073 ms
latency stddev = 31.841 ms
initial connection time = 5.961 ms
tps = 2447.563057 (without initial connection time)
statement latencies in milliseconds:
0.001 \set id random(1,10000000)
13.064 update t0 set n1 = random()*100 where id = :id;
hot
transaction type: ./test_hot.sql
scaling factor: 1
query mode: prepared
number of clients: 32
number of threads: 32
duration: 120 s
number of transactions actually processed: 724192
latency average = 5.302 ms
latency stddev = 14.019 ms
initial connection time = 6.242 ms
tps = 6035.041159 (without initial connection time)
statement latencies in milliseconds:
0.001 \set id random(1,10000000)
5.321 update t0 set n2 = random()*100 where id = :id;
test CASE
drop table t0;
create table t0(id int primary key, n1 int, n2 int);
create index idx_t0_id_n1 on t0(id, n1);
insert into t0 select generate_series(1,10000000);
vi test_nohot.sql
\set id random(1,10000000)
update t0 set n1 = random()*100 where id = :id;
pgbench -M prepared -n -r -P 1 -f ./test_nohot.sql -c 32 -j 32 -T 120
vi test_hot.sql
\set id random(1,10000000)
update t0 set n2 = random()*100 where id = :id;
pgbench -M prepared -n -r -P 1 -f ./test_hot.sql -c 32 -j 32 -T 120
2 update technological process
from ExecUpdate Function into
- Before updating : trigger 、 Foreign key trigger 、FDW etc.
- Check the new element group constraint ExecConstraints
- Perform the update table_tuple_update
- Insert a new index tuple ExecInsertIndexTuples(HOT Update does not need to update the index )
ExecUpdate
/* Trigger before update 、 Foreign key trigger 、FDW etc. */
/* BEFORE ROW UPDATE Triggers */
/* INSTEAD OF ROW UPDATE Triggers */
/* update in foreign table: let the FDW do it */
...
ExecConstraints
table_tuple_update
/* May go HOT No new index items are required */
ExecInsertIndexTuples
/* AFTER ROW UPDATE Triggers */
/* Process RETURNING if present */
...
return
2.1 update Process details (HOT)
Then expand the above process
- Before updating : stay ExecutorState Reassemble tuples in memory ExecMaterializeSlot
- Before updating : Get all relevant indexes ExecOpenIndices
- Before updating : perform : trigger 、 Foreign key trigger 、FDW etc.
- Check : New element group constraint ExecConstraints
- Perform the update :table_tuple_update
- Returns whether the index needs to be updated , If it is HOT There is no need to update the index
- heap_update Execute specific update process ( Let's continue the analysis )
- Insert a new index tuple ExecInsertIndexTuples(HOT There is no need to update the index )
ExecUpdate
ExecMaterializeSlot
tts_buffer_heap_materialize
// Switch to ExecutorState Memory context
// Spell out tuples in the new memory pool
heap_form_tuple
/* Trigger before update 、 Foreign key trigger 、FDW etc. */
...
/* Get the relevant index oid list */
ExecOpenIndices
/* BEFORE ROW UPDATE Triggers */
/* INSTEAD OF ROW UPDATE Triggers */
/* update in foreign table: let the FDW do it */
...
ExecConstraints
table_tuple_update
heapam_tuple_update
// Perform the update
heap_update
// Whether the index needs to be updated ?HOT?
*update_indexes = result == TM_Ok && !HeapTupleIsHeapOnly(tuple)
/* May go HOT No new index items are required */
if (... && update_indexes)
ExecInsertIndexTuples
// For each relevant index, we need to construct a new index tuple
for (i = 0; i < numIndices; i++)
FormIndexDatum
index_insert
// checkUnique
/* AFTER ROW UPDATE Triggers */
/* Process RETURNING if present */
...
return
2.2 heap_update Function to perform analysis (HOT)
Expand... In the above process heap_update function :
perform :
drop table t0;
create table t0(id int primary key, n1 int, n2 int);
create index idx_t0_id_n1 on t0(id, n1);
insert into t0 select generate_series(1,2), generate_series(1,2)+100, 888;
update t0 set n2 = 0 where id = 2;
First step :bitmap To configure , Find the position of all index columns
What is the bitmap here? Refer to this article :《Postgresql Source code (52)bitmapset analysis RelationGetIndexAttrBitmap》
Generate three bitmaps to record the index position :hot_attrs、key_attrs、id_attrs
n1 id
\/
||
hot_attrs = 1100000000 : Which columns have indexes ?
key_attrs = 100000000 : Which columns have unique indexes ?
id_attrs = 100000000 : Copy identity
The second step : If PAGE Not full , May go HOT, structure bitmap interesting_attrs
To configure :hot_attrs_checked=true
n1 id
\/
||
interesting_attrs = 1100000000
The third step : Lock page
Step four : Which index columns have been modified ?
HeapDetermineColumnsInfo The function structure modified_attrs Bitmap , No index columns have been modified here
modified_attrs = 0000000000
This bitmap records which index columns have been modified , Notice the index column
Step five : Whether the old tuple is visible ?
HeapTupleSatisfiesUpdate(MVCC)
Step six : Decide whether to go HOT
Meet three conditions :
- BUFFER unchanged
- hot_attrs_checked: The second step above :PAGE Not full
- modified_attrs: Step 4 above : Some index columns have been modified
if (newbuf == buffer)
if (hot_attrs_checked && !bms_overlap(modified_attrs, hot_attrs))
use_hot_update = true;
Step seven : Start HOT to update
- One 、 Add a flag bit :
- Old tuple :HEAP_HOT_UPDATED、HEAP_ONLY_TUPLE
- Xinyuan formation :HEAP_ONLY_TUPLE
- Two 、 Configure the header of the old tuple
- 3、 ... and 、 Insert new element group
if (use_hot_update)
HeapTupleSetHotUpdated(&oldtup)
(tup)->t_infomask2 |= HEAP_HOT_UPDATED
HeapTupleSetHeapOnly(heaptup)
(tup)->t_infomask2 |= HEAP_ONLY_TUPLE
HeapTupleSetHeapOnly(newtup)
(tup)->t_infomask2 |= HEAP_ONLY_TUPLE
Step eight : Record XLOG
log_heap_update
边栏推荐
- Future trend and development of neural network Internet of things
- 2022-07-01:某公司年会上,大家要玩一食发奖金游戏,一共有n个员工, 每个员工都有建设积分和捣乱积分, 他们需要排成一队,在队伍最前面的一定是老板
- Matplotlib常用設置
- Airserver latest win64 bit personal screen projection software
- Redis 主从同步
- Know --matplotlib
- Applet form verification encapsulation
- 物联网技术应用属于什么专业分类
- 每日三题 6.30(2)
- The digital summit is popular, and city chain technology has triggered a new round of business transformation
猜你喜欢
随机推荐
Oracle中已定义者身份执行函数AUTHID DEFINER与Postgresql行为的异同
为什么PHP叫超文本预处理器
How to display real-time 2D map after rviz is opened
2021 RoboCom 世界机器人开发者大赛-本科组初赛
Openresty load balancing
[applet] realize the left and right [sliding] list through the scroll view component
De PIP. Interne. CLI. Main Import main modulenotfounderror: No module named 'PIP'
Postgresql源码(58)元组拼接heap_form_tuple剖析
Leetcode(34)——在排序数组中查找元素的第一个和最后一个位置
Redis RDB快照
mysql binlog的清理
What is the mosaic tailgate?
Jielizhi Bluetooth headset quality control and production skills [chapter]
Daily three questions 6.30 (2)
flutter Unable to load asset: assets/images/888.png
Practical application and extension of plain framework
想请教股票开户要认识谁?在线开户是安全么?
ARP报文头部格式和请求流程
【微服务|Sentinel】SentinelResourceAspect详解
[micro service sentinel] sentinelresourceaspect details