Fix error when changing force write mode
When we try to change force write mode on database that has connections, we can get various types of errors or asserts from PIO_ functions (Super Server mode only). These errors can be reproduced using TPCC load and changing force write mode.
This patch fixes cases where someone tries to change force write mode when database has connections. This is done via RWLock for file descriptor, so we can be sure that some other thread won't close this descriptor while we're using it.
For Classic Server we can change force write mode only with no connections.
For Classic Server we can change force write mode only with no connections.
Why ?
For Classic Server we can change force write mode only with no connections.
Why ?
I tried to implement this via AST, looking at LCK_monitor as an example, but I couldn't figure it out where and when I should relock my lock after LCK_downgrade in AST. So I stop on restriction for classic server. Maybe you can give me some advice on this issue?
For Classic Server we can change force write mode only with no connections.
Why ?
I tried to implement this via AST, looking at LCK_monitor as an example, but I couldn't figure it out where and when I should relock my lock after LCK_downgrade in AST. So I stop on restriction for classic server. Maybe you can give me some advice on this issue?
My question was - why different CS processes must run with the same FW mode ? I.e. why force same mode here ? I highly doubt it can produce
various types of errors or asserts from PIO_ functions
why different CS processes must run with the same FW mode ?
I think because it's more expected, if someone changes FW mode, they will expect all connections to change FW mode too. This works with Super, but not with Classic.
But this is how I see it, currently if we change FW mode on Classic, it will not change for already connected users, maybe I should keep this behavior.
I.e. why force same mode here ? I highly doubt it can produce
various types of errors or asserts from PIO_ functions
Yes, these errors can only be reproduced on Super, I should have mentioned that in the PR description, added it now.
The more I think about it the more I consider that solution is not fully correct and excessive, sorry.
There is no (direct) harm when different CS processes use different FW mode. It is not perfect, I agree, but we lived with it many years with no complains.
As for SS, where the real problem happens, I think it is not good to re-open database file with a (lot of) user connections - it could lead to a significant performance loss for a visible time, as OS flushes the file buffers when file is closing and it could take a time. Note, all user connections the require disk IO will wait for this process to finish.
So, instead, I offer to save new FW flag value to the header page (all architectures) and re-open file only if there is no other connections (required for SS only, but could be discussed). This is similar to how change of page buffers number works, btw.
So, instead, I offer to save new FW flag value to the header page (all architectures) and re-open file only if there is no other connections (required for SS only, but could be discussed).
I would expect that while file open mode changes are delayed in this case for SS, changes in page cache flush strategy would be immediate. Perhaps file re-opening also may be immediate if the change is done in sole connection.
So, instead, I offer to save new FW flag value to the header page (all architectures) and re-open file only if there is no other connections (required for SS only, but could be discussed).
I would expect that while file open mode changes are delayed in this case for SS, changes in page cache flush strategy would be immediate.
Could you show what you means by 'flush strategy', how it works now and how you would expect it to work ?
Perhaps file re-opening also may be immediate if the change is done in sole connection.
This is what I said above.
Could you show what you means by 'flush strategy', how it works now and how you would expect it to work ?
I expect that when I set FW OFF, dirty pages won't be flushed immediately on commit for all connections. Because that's why I do it.
My last comment is for SS. CS can do whatever it wants.
Could you show what you means by 'flush strategy', how it works now and how you would expect it to work ?
I expect that when I set FW OFF, dirty pages won't be flushed immediately on commit for all connections. Because that's why I do it.
When engine works with FW=ON (FIL_force_write flag is set) is doesn't call PIO_flush(), because it makes no sence - OS does it for us on every write().
When engine works with FW=OFF (FIL_force_write flag is not set) is does call PIO_flush() (as often as it allowed by MaxUnflushedWrites and MaxUnflushedWriteTime settings) - this is necessary, as OS doesn't do it.
Now, imagine database with FW=ON and admin changed FW to OFF. File mode is not changed and OS still writes every page to disk immediately. You offer to clear FIL_force_write flag and make engine to call PIO_flush() in addition to the OS immediate writes. In best case it will change nothing, in worst case - adds performance penalty. In any case your expectation about perf boost is wrong.
In opposite case, when FW is changed from OFF to ON, engine will never call PIO_flush() and OS also will not write data to disk immediately. This is very bad for on-disk consistency, obviously.
as often as it allowed by
MaxUnflushedWritesandMaxUnflushedWriteTimesettings
Which by default are -1, i.e. "never".
as often as it allowed by
MaxUnflushedWritesandMaxUnflushedWriteTimesettingsWhich by default are -1, i.e. "never".
Not on Windows. Either way, that doesn't make your expectation/proposal correct.
As for SS, where the real problem happens, I think it is not good to re-open database file with a (lot of) user connections - it could lead to a significant performance loss for a visible time, as OS flushes the file buffers when file is closing and it could take a time. Note, all user connections the require disk IO will wait for this process to finish.
I guess the main point was when someone changes the FW mode, he usually wants to get the effect immediately. And there are 2 ways to do this: either force all user connections to close or reopen the file with relatively less time and performance penalty. The second one looks better from this point. Also, if we allow the actual FW mode change to be delayed then we cannot trust its status showed by gstat.
This is similar to how change of page buffers number works, btw.
Similarity is good but changing the FW mode is more critical, I believe.
What I don't like in the "delayed option" is it being unpredictable. DBA turns FW on and expects that crashes will not lead to corruptions after that. The same for CS - if some connections will still be using FW=OFF after that and crash and corrupt the database this is not what DBA expects after changing FW to ON. But they have no idea when the change will be actually applied. So to ensure that they need also to shutdown the database to force everybody to reconnect. This is hardly pleasant under user load. This is the difference between BUFFERS and FW -- one is just about performance but the other is about reliability which is more important, IMO.
What I don't like in the "delayed option" is it being unpredictable. DBA turns FW on and expects that crashes will not lead to corruptions after that. The same for CS - if some connections will still be using FW=OFF after that and crash and corrupt the database this is not what DBA expects after changing FW to ON.
Same for SC.
But they have no idea when the change will be actually applied.
Document it. Issue warning.
So to ensure that they need also to shutdown the database to force everybody to reconnect. This is hardly pleasant under user load.
Explain, please - why reasonable DBA could think about changing FW under real load ever ? What is real necessity for this and how often it happens ?
PS this is again flame about nothing. The original intent was to fix errors on SS when FW is changing under load. But it was not about making any uneducated "want-to-be-dba" happy.
So, we stop at the realization proposed by @hvlad?
So to ensure that they need also to shutdown the database to force everybody to reconnect. This is hardly pleasant under user load.
Explain, please - why reasonable DBA could think about changing FW under real load ever ? What is real necessity for this and how often it happens ?
Why to change FW at all? Loading, indexing, or even just because someone wants. At least untill we don't require EX lock on DB for this. So it should either predictbaly work or not. Moreover, an ability to change FW on the fly looks not so bad option for me, and might be useful for some heavy regilar operations, in combination with nbackup as "global transaction".