views:

246

answers:

5

I'm taking an intro class on database management systems, and had a question that wasn't answered by my book. This question is not from my homework, I was just curious.

The textbook continually stresses that a transaction is one logical unit of work. However, when coming across the shared/exclusive locking modes, I got a little confused.

There was a diagram in the book that looked like this:

Time | Transaction Status

1         Request Lock

2         Receive Lock

3         Process transaction

4         Release Lock

5         Lock is released

Does the transaction get processed all at the same time, or does it get processed as individual locks are obtained?

If there are commands in two transactions that result in a shared lock as well as an exclusive lock, do those transactions run concurrently, or are they scheduled one after the other?

A: 

If it needs an exclusive lock, it will either block the other transaction or it will wait for the other transaction to finish before obtaining the lock.

Things that need exclusive locks (UPDATE/DELETE/etc) can't happen while anything else is accessing the data.

Satanicpuppy
So, nothing in a transaction will happen unless it has all relevant locks in place?
Jeremy White
+1  A: 

In practice each operation aquires the needed lock before it proceeds. A SELECT will first aquire a shared lock on a row, then read the row. An UPDATE will first acquire an exclusive lock on that row, then update the row. In theory you can say that 'locks are aquired, then the transaction processes', but in real life is it each individual operation in the transaction that knows what locks are required.

Remus Rusanu
That's not quite true, as just acquiring locks in order of operations can lead to deadlocks. Consider {update A; update B;} and {update B; update A;} -- they will wait on each other forever, or both time out.
SquareCog
@Square: Are you suggesting that in practice, in real life, DBMSs are deadlock free?
Remus Rusanu
I am suggesting that an algorithm that leads to a deadlock and requires deadlock detection to bounce both transactions should be considered a bug with a hack to cover for it. It might be an expedient hack (ease of implementation vs correcting the true issue, etc), but it's a bug. I guess MS doesn't see it this way.
SquareCog
@Square: Right. Is the agreement lazy sloppy programmers at MS signed with other lazy bunch at Sybase, DB2, Tandem, PostgreSQL, InnoDB etc that keeps the world deadlocking ad nauseam...
Remus Rusanu
you are just jealous my answer got accepted ;). Just kidding. Thanks for educating me on what the accepted industry practice is. It seems counterintuitive that the preference is to deal with deadlocks rather than avoid them, but I guess there must be reasons.
SquareCog
http://www.amazon.com/Transaction-Processing-Concepts-Techniques-Management/dp/1558601902
Remus Rusanu
+1  A: 

The answer is, as usual, "it depends" :-)

Generally speaking, you don't need to take out all your locks before you begin; however, you need to take out all your locks before you release any locks. So you can do the following:

lock resource A
update A
lock resource B
update B
unlock A
unlock B

This allows you to be a bit friendlier to other transactions that may want to read B, and don't care about A, for example. It does introduce more risk -- you may be unable to acquire a lock on B, and decide to roll back your transaction. Them's the breaks.

You also want to always acquire all locks in the same order, so that you don't wind up in a deadlock (transaction 1 has A and wants B; trans 2 has B and wants A; standoff at high noon, no one wins. If you enforce consistent order, trans 2 will try to get A before B and either wait, letting trans 2 proceed, or fail, if trans 1 already started -- either way, no deadlock).

Things get more interesting when you have intent-to-exclude locks -- locks that are taken as shared with an "option" to make them exclusive. This might be covered somewhere in the back of your book :-)

SquareCog
A: 

in general locks are determined at run time. When the BEGIN TRANSACTION command is processed, nothing has run in the transaction yet, so there are no locks. As commands execute in the transaction locks are acquired.

KM
A: 

"If there are commands in two transactions that result in a shared lock as well as an exclusive lock, do those transactions run concurrently, or are they scheduled one after the other?"

A lock does not consist solely of the notion "shared/exclusive". The most important thing about a lock is the resource that it applies to.

Two transactions that each hold an exclusive lock on distinct resources (say, two separate tables, or two separate partitions, or two separate pages, or two separate rows, or two separate printers, or two separate IP ports, ...) can continue to run concurrently without any problem.

Transaction serialization only becomes necessary when a transaction requests a lock on some resource, where the sharing mode of that lock is incompatible with a lock held on the same resource by some other transaction.

If your textbook really gives the sequence of events as you state, then throw it away. Lock requests emerge as the transaction is being processed, and there is no definitive and final way for the transaction processor to know at the start of the transaction which locks it will be needing (otherwise deadlocking would be a nonexistant problem).

Erwin Smout