Thread: loose ends in lazy-XID-assigment patch
I've committed Florian's patch, but there remain a couple of things that need work: * Should CSV-mode logging include the virtual transaction ID (VXID) in addition to, or instead of, XID? There will be many situations where there is no XID. * As things stand, when a two-phase transaction is prepared, it drops its lock on the original VXID; this seems necessary for reasons previously discussed. I made the code put an invalid VXID into the gxact structure for the prepared xact, which means that pg_locks shows things like this: regression=# select * from pg_locks; locktype | database | relation | page | tuple | virtualxid | transactionid | classid| objid | objsubid | virtualtransaction | pid | mode | granted ---------------+----------+----------+------+-------+------------+---------------+---------+-------+----------+--------------------+-------+-----------------+---------transactionid | | | | | | 21774 | | | | -1/0 | | ExclusiveLock | trelation | 126093 | 126124 | | | | | | | | -1/0 | | AccessShareLock | trelation | 126093 | 10969 | | | | | | | | 1/260 | 20592 | AccessShareLock | tvirtualxid | | | | | 1/260 | | | | | 1/260 | 20592 | ExclusiveLock | t (4 rows) This seems fairly undesirable :-( not least because you can't tell one prepared xact from another and thus can't see which locks belong to each. But I'm unsure what to do about it. We could have the prepared xact continue to display the original VXID, but there would be no certainty about the VXID remaining unique, which seems bad. Another possibility is to put back the transaction ID column, but since that's not unique for read-only transactions, we still don't have anything usable as a join key. The best idea I can think of is to make the virtualtransaction column read out the VXID for regular transactions and the transaction ID for prepared transactions, or maybe the transaction ID for any transaction that has one and VXID just for read-only xacts. We can get away with that because the column is only text and not any better-defined datatype. It seems mighty ugly though; and changing the ID shown for a transaction mid-stream isn't very pleasant either. Anyone have a better idea? regards, tom lane
Tom Lane wrote: > * Should CSV-mode logging include the virtual transaction ID (VXID) in > addition to, or instead of, XID? There will be many situations where > there is no XID. > > > But will there be any where we care? Isn't the point of this to restrict allocation of a real XID to situations where having one might actually matter? All the rest seems to me just bookkeeping. cheers andrew
Tom Lane wrote: > I've committed Florian's patch, but there remain a couple of things > that need work: > > * Should CSV-mode logging include the virtual transaction ID (VXID) in > addition to, or instead of, XID? There will be many situations where > there is no XID. Maybe make %x show both, or only the xid if that is set, and the vxid otherwise? That would probably be what most existing users of %x want. For those who want them seperated, we'd have %v (vxid), and maybe %X (xid only). Seems a bit like overkills, though... > > * As things stand, when a two-phase transaction is prepared, it drops > its lock on the original VXID; this seems necessary for reasons > previously discussed. I made the code put an invalid VXID into the > gxact structure for the prepared xact, which means that pg_locks shows > things like this: > > regression=# select * from pg_locks; > locktype | database | relation | page | tuple | virtualxid | transactionid | classid | objid | objsubid | virtualtransaction| pid | mode | granted > ---------------+----------+----------+------+-------+------------+---------------+---------+-------+----------+--------------------+-------+-----------------+--------- > transactionid | | | | | | 21774 | | | | -1/0 | | ExclusiveLock | t > relation | 126093 | 126124 | | | | | | | | -1/0 | | AccessShareLock | t > relation | 126093 | 10969 | | | | | | | | 1/260 | 20592 | AccessShareLock | t > virtualxid | | | | | 1/260 | | | | | 1/260 | 20592 | ExclusiveLock | t > (4 rows) > > This seems fairly undesirable :-( not least because you can't tell one > prepared xact from another and thus can't see which locks belong to > each. But I'm unsure what to do about it. We could have the prepared > xact continue to display the original VXID, but there would be no > certainty about the VXID remaining unique, which seems bad. Another > possibility is to put back the transaction ID column, but since that's > not unique for read-only transactions, we still don't have anything > usable as a join key. > > The best idea I can think of is to make the virtualtransaction column > read out the VXID for regular transactions and the transaction ID for > prepared transactions, or maybe the transaction ID for any transaction > that has one and VXID just for read-only xacts. We can get away with > that because the column is only text and not any better-defined > datatype. It seems mighty ugly though; and changing the ID shown for > a transaction mid-stream isn't very pleasant either. We could make the VXID in the gxact struct be backendId=InvalidBackendId, lxid=xid. That'd be still an invalid vxid, but not the same for every prepared transaction. If we take this further, we could get rid of the lock on the xid completely, I believe. We'd define some PermanentBackendId (lets say, -2, since -1 is taken). When preparing the xact, we'd drop the lock on the old VXID, and instead acquire one on (PermanentBackendId, xid). Waiting on an xid would become a bit tricky, but doable I think. We'd have to first check the procarray - if we find the xid there, we translate it to a vxid, and wait on that. Aftwards (whether we found a vxid, or not) we wait on (PermanentBackendId, xid). That doesn't exactly make XactLockTableWait cheaper, but that might be OK, since we I haven't really thought this through, though. I think that with carefull ordering of things we can control the race conditions this might posses - but I'm not sure at this point. greetings, Florian Pflug
Andrew Dunstan <andrew@dunslane.net> writes: > Tom Lane wrote: >> * Should CSV-mode logging include the virtual transaction ID (VXID) in >> addition to, or instead of, XID? There will be many situations where >> there is no XID. > But will there be any where we care? Isn't the point of this to restrict > allocation of a real XID to situations where having one might actually > matter? All the rest seems to me just bookkeeping. Well, the point is that a transaction might well emit log messages when it hasn't changed anything and hence hasn't got an XID. If you would like to be able to match up the messages generated by a single transaction, you'd need to have VXID available to use as a join key. In any case it seems a bit odd that we have a value that's available in log_line_prefix and not available to users of CSV log output. regards, tom lane
"Florian G. Pflug" <fgp@phlo.org> writes: > Tom Lane wrote: >> This seems fairly undesirable :-( not least because you can't tell one >> prepared xact from another and thus can't see which locks belong to >> each. But I'm unsure what to do about it. > We could make the VXID in the gxact struct be > backendId=InvalidBackendId, lxid=xid. That'd be still an invalid vxid, but not > the same for every prepared transaction. Hmm, that would work. > If we take this further, we could get rid of the lock on the xid completely, Maybe, but let's not go there for now. I was already bending the rules to push this into 8.3 --- I think further improvement needs to wait for 8.4. regards, tom lane