Bug #105978 Dynamically updating low_priority_updates not affect the session property
Submitted: 26 Dec 2021 6:09 Modified: 27 Dec 2021 10:14
Reporter: teng wang (OCA) Email Updates:
Status: Verified Impact on me:
None 
Category:MySQL Server: Options Severity:S4 (Feature request)
Version:5.7.35 OS:Linux
Assigned to: CPU Architecture:Any

[26 Dec 2021 6:09] teng wang
Description:
The option low_priority_updates means, if set to ON, all INSERT, UPDATE, DELETE, and LOCK TABLE WRITE statements wait until there is no pending SELECT or LOCK TABLE READ on the affected table. I start MySQL with low_priority_updates as ON and add a lock to table t1 with "LOCK TABLE t1 READ LOCAL;". When I update global low_priority_updates to OFF in another session, it still hang when inserting at table t1. Then I check the global and session property of low_priority_updates, and find the session value of low_priority_updates is still ON. 

When people dynamically set a global option, usually they also want to update the option in the current session. So I suggest that setting global low_priority_updates also makes sense to the current session.

How to repeat:
connect (root,localhost,root,,test,$MASTER_MYPORT,$MASTER_MYSOCK);
connection root;
CREATE TABLE t1 ( a INT NOT NULL PRIMARY KEY AUTO_INCREMENT ) ENGINE=MyISAM;
LOCK TABLE t1 READ LOCAL;

connect (root2,localhost,root,,test,$MASTER_MYPORT,$MASTER_MYSOCK);
connection root2;
show global variables where variable_name like 'low_priority_updates';
show session variables where variable_name like 'low_priority_updates';

set global low_priority_updates = OFF;
show global variables where variable_name like 'low_priority_updates';
show session variables where variable_name like 'low_priority_updates';
# hang when inserting to t1
INSERT INTO t1 VALUES (1), (2), (3);

connection root;
SELECT * FROM t1;
UNLOCK TABLES;
drop table t1;

disconnect root;
disconnect root2;

Suggested fix:
Potential fixing is that when updating global low_priority_updates, also update the session value of low_priority_updates

sql/sys_vars.cc
static bool fix_low_prio_updates(sys_var *self, THD *thd, enum_var_type type)
{
  if (type == OPT_SESSION)
  {
    thd->update_lock_default= (thd->variables.low_priority_updates ?
                               TL_WRITE_LOW_PRIORITY : TL_WRITE);
    thd->insert_lock_default= (thd->variables.low_priority_updates ?
                               TL_WRITE_LOW_PRIORITY : TL_WRITE_CONCURRENT_INSERT);
  }
  else
    thr_upgraded_concurrent_insert_lock=
      (global_system_variables.low_priority_updates ?
       TL_WRITE_LOW_PRIORITY : TL_WRITE);
+   //when updating global low_priority_updates, also updating the session value
+   thd->variables.low_priority_updates = global_system_variables.low_priority_updates;
+   thd->update_lock_default= (thd->variables.low_priority_updates ?
                               TL_WRITE_LOW_PRIORITY : TL_WRITE);
+   thd->insert_lock_default= (thd->variables.low_priority_updates ?
                               TL_WRITE_LOW_PRIORITY : TL_WRITE_CONCURRENT_INSERT);
  return false;
}
[27 Dec 2021 10:14] MySQL Verification Team
Hello teng wang,

Thank you for the feature request and supplying patch along with it, we appreciate it!

In order for us to continue the process of reviewing your contribution to MySQL, please send us a signed copy of the Oracle Contributor Agreement (OCA) as outlined in https://oca.opensource.oracle.com

Signing an OCA needs to be done only once and it's valid for all other Oracle governed Open Source projects as well.

Getting a signed/approved OCA on file will help us facilitate your contribution - this one, and others in the future.  

Please let me know, if you have any questions.

Thank you for your interest in MySQL.

regards,
Umesh