Re: [HACKERS] Concurrency control questions 6.3.2 vs. 6.4 - Mailing list pgsql-hackers
From | Bruce Momjian |
---|---|
Subject | Re: [HACKERS] Concurrency control questions 6.3.2 vs. 6.4 |
Date | |
Msg-id | 199812130230.VAA08615@candle.pha.pa.us Whole thread Raw |
In response to | Re: [HACKERS] Concurrency control questions 6.3.2 vs. 6.4 (Steve Frampton <frampton@mail.flarc.edu.on.ca>) |
List | pgsql-hackers |
> Hi everyone: > > Thanks for the helpful responses. Are you folks getting sick of me yet? > I'm hoping somebody could help me understand a bit better the way locking > protocols are used in PostGreSQL 6.4, including how a query is parsed, > executed, etc. > > I understand that there are two locks available: one for reads and one for > writes. They are called by RelationSetLockForRead() and > RelationSetLockForWrite(), respectively, which are both implemented in > backend/storage/lmgr.c. > > These functions are called by the query parser, trigger handler, and > indexing subsystem. The query parser is responsible for parsing a given > expression in backend/parser/parse_expr.c and actually grabbing tuples in > backend/parser/parse_func.c which are passed as a heap array to the > backend which in turn passes the information to the client. Am I still > okay? > > I'm interested in the locking protocols as used for query processing > so I guess I can ignore the trigger and indexing for now. > > Locking is not accomplished with calls to the operating system but instead > is managed by the locking manager through a lock hash table which lives in > shared memory. The table contains information on locks such as the type of > lock (read/write), number of locks currently held, an array of bitmasks > showing lock conflicts, and lock priority level (used to prevent > starvation). In addition, each relation has its own data structure which > includes some locking information. > > Here's where things get fuzzy -- there's a lot of code here so please be > patient with me if I really screwed up in my interpretation. :-) > > When the RelationSetLockFor...() function is called, it ensures that the > relation and lock information for the relation are both valid. It then > calls MultiLockReln() with a pointer to the relation's lock information > and the appropriate lock type. MultiLockReln() initializes a lock tag > which is passed to MultiAcquire(). > > I'm a little vague on MultiAcquire(). It seems to search through the > lock hash table to see if a lock should be allowed? And if so it calls > LockAcquire(). But LockAcquire() itself checks for conflicts, sleeps if > one exists, or sets the appropriate lock, adding it to the lock table. So > I'm a bit confused here... > > Unlocks are accomplished in much the same fashion. > RelationUnsetLockFor...() is called which in turn calls MultiRelease() > which searches the lock table using the same algorithm as in > MultiAcquire(). MultiRelease() calls LockRelease() which performs two > functions. First, it removes the lock information from the lock table. > Second, this function will awaken any transaction which had blocked > waiting for the same lock. This is done here because if it was not, a new > process could come along and request the lock causing a race condition. Sounds pretty close. I assume you have studied the backend flowcart on the web support page and in src/tools/backend? -- Bruce Momjian | http://www.op.net/~candle maillist@candle.pha.pa.us | (610) 853-3000+ If your life is a hard drive, | 830 Blythe Avenue + Christ can be your backup. | Drexel Hill, Pennsylvania19026
pgsql-hackers by date: