From: | Robert Haas <robertmhaas(at)gmail(dot)com> |
---|---|
To: | Alex <zhihui(dot)fan1213(at)gmail(dot)com> |
Cc: | "pgsql-hackers(at)postgresql(dot)org" <pgsql-hackers(at)postgresql(dot)org> |
Subject: | Re: some questions about fast-path-lock |
Date: | 2019-05-29 21:29:10 |
Message-ID: | CA+TgmoYVjs9h=ZKK7bWXXt=UhXjyrNGxXoFx8X1VDhJ+JHVPOA@mail.gmail.com |
Views: | Raw Message | Whole Thread | Download mbox | Resend email |
Thread: | |
Lists: | pgsql-hackers |
On Mon, May 27, 2019 at 2:01 AM Alex <zhihui(dot)fan1213(at)gmail(dot)com> wrote:
> I got some idea from the README under storage/lmgr and read some code of LockAcquireExtended , but I still have some questions now.
>
> LWLockAcquire(&MyProc->backendLock, LW_EXCLUSIVE);
> if (FastPathStrongRelationLocks->count[fasthashcode] != 0)
> acquired = false;
> else
> acquired = FastPathGrantRelationLock(locktag->locktag_field2,
> lockmode);
>
> 1. In the README, it says: "A key point of this algorithm is that it must be possible to verify the
> absence of possibly conflicting locks without fighting over a shared LWLock or
> spinlock. Otherwise, this effort would simply move the contention bottleneck
> from one place to another."
>
> but in the code, there is LWLockAcquire in the above code. Actually I can't think out how can we proceed without a lock.
The per-backend lock is not heavily contended, because under normal
circumstances it is only accessed by a single backend. If there is a
potential lock conflict that must be analyzed then another backend may
acquire it and that might lead to a little bit of contention, but it
happens quite rarely -- so the overall contention is still much less
than if everyone is fighting over the lock manager partition locks.
> 2. Why does the MyProc->backendLock work? it is MyProc not a global lock.
It's still an LWLock. Putting it inside of MyProc doesn't make it
magically stop working. MyProc is in shared memory, not backend-local
memory, if that's what you are confused about.
> 3. for the line, acquired = FastPathGrantRelationLock(locktag->locktag_field2,
> lockmode); I think it should be able to replaced with "acquired = true" (but obviously I'm wrong) . I read "FastPathGrantRelationLock" but can't understand it.
It can't say 'acquired = true' because each backend can only acquire a
maximum of 16 relation locks via the fast-path mechanism. If a
process acquires more than 16 relation locks, at least some of them
will have to be acquired without benefit of the fast-path. This value
could be changed by changing the value of the constant
FP_LOCK_SLOTS_PER_BACKEND, but since we scan the array linearly,
making it too big will lead to other problems. I don't quite
understand what about FastPathGrantRelationLock you don't understand -
it's a pretty straightforwardly-coded search for either (a) an
existing fastpath slot for the specified relid or failing that (b) an
unused fastpath slot.
--
Robert Haas
EnterpriseDB: http://www.enterprisedb.com
The Enterprise PostgreSQL Company
From | Date | Subject | |
---|---|---|---|
Next Message | Robert Haas | 2019-05-29 21:32:45 | Re: message style |
Previous Message | Robert Haas | 2019-05-29 21:23:14 | Re: Names |