Received: from localhost (unknown [200.46.208.211]) by mail.postgresql.org (Postfix) with ESMTP id 5F746632662 for ; Thu, 12 Mar 2009 12:01:23 -0300 (ADT) Received: from mail.postgresql.org ([200.46.204.86]) by localhost (mx1.hub.org [200.46.208.211]) (amavisd-maia, port 10024) with ESMTP id 49159-04 for ; Thu, 12 Mar 2009 12:01:08 -0300 (ADT) X-Greylist: from auto-whitelisted by SQLgrey-1.7.6 Received: from brmea-mail-4.sun.com (brmea-mail-4.Sun.COM [192.18.98.36]) by mail.postgresql.org (Postfix) with ESMTP id 51A93633FB9 for ; Thu, 12 Mar 2009 12:00:58 -0300 (ADT) Received: from fe-amer-09.sun.com ([192.18.109.79]) by brmea-mail-4.sun.com (8.13.6+Sun/8.12.9) with ESMTP id n2CF0vkL001836 for ; Thu, 12 Mar 2009 15:00:57 GMT MIME-version: 1.0 Content-type: multipart/alternative; boundary="Boundary_(ID_eVXC4WqioCX0u/qhs9KihQ)" Received: from conversion-daemon.mail-amer.sun.com by mail-amer.sun.com (Sun Java(tm) System Messaging Server 7.0-5.01 64bit (built Feb 19 2009)) id <0KGE00100E2BJU00@mail-amer.sun.com> for pgsql-performance@postgresql.org; Thu, 12 Mar 2009 09:00:57 -0600 (MDT) Received: from [129.148.169.151] ([unknown] [129.148.169.151]) by mail-amer.sun.com (Sun Java(tm) System Messaging Server 7.0-5.01 64bit (built Feb 19 2009)) with ESMTPSA id <0KGE00I9RF17EW90@mail-amer.sun.com>; Thu, 12 Mar 2009 09:00:44 -0600 (MDT) Date: Thu, 12 Mar 2009 10:57:04 -0400 From: "Jignesh K. Shah" Subject: Re: Proposal of tunable fix for scalability of 8.4 In-reply-to: To: Scott Carey Cc: Kevin Grittner , "pgsql-performance@postgresql.org" Message-id: <49B922C0.6050700@sun.com> Organization: Sun Microsystems References: User-Agent: Thunderbird 2.0.0.17 (X11/20081023) X-Virus-Scanned: Maia Mailguard 1.0.1 X-Archive-Number: 200903/122 X-Sequence-Number: 33044 This is a multi-part message in MIME format. --Boundary_(ID_eVXC4WqioCX0u/qhs9KihQ) Content-type: text/plain; format=flowed; charset=ISO-8859-1 Content-transfer-encoding: 7BIT On 03/11/09 22:01, Scott Carey wrote: > On 3/11/09 3:27 PM, "Kevin Grittner" wrote: > > > I'm a lot more interested in what's happening between 60 and 180 than > over 1000, personally. If there was a RAID involved, I'd put it down > to better use of the numerous spindles, but when it's all in RAM it > makes no sense. > > If there is enough lock contention and a common lock case is a short > lived shared lock, it makes perfect sense sense. Fewer readers are > blocked waiting on writers at any given time. Readers can 'cut' in > line ahead of writers within a certain scope (only up to the number > waiting at the time a shared lock is at the head of the queue). > Essentially this clumps up shared and exclusive locks into larger > streaks, and allows for higher shared lock throughput. > Exclusive locks may be delayed, but will NOT be starved, since on the > next iteration, a streak of exclusive locks will occur first in the > list and they will all process before any more shared locks can go. > > This will even help in on a single CPU system if it is read dominated, > lowering read latency and slightly increasing write latency. > > If you want to make this more fair, instead of freeing all shared > locks, limit the count to some number, such as the number of CPU > cores. Perhaps rather than wake-up-all-waiters=true, the parameter > can be an integer representing how many shared locks can be freed at > once if an exclusive lock is encountered. > > Well I am waking up not just shared but shared and exclusives.. However i like your idea of waking up the next N waiters where N matches the number of cpus available. In my case it is 64 so yes this works well since the idea being of all the 64 waiters running right now one will be able to lock the next lock immediately and hence there are no cycles wasted where nobody gets a lock which is often the case when you say wake up only 1 waiter and hope that the process is on the CPU (which in my case it is 64 processes) and it is able to acquire the lock.. The probability of acquiring the lock within the next few cycles is much less for only 1 waiter than giving chance to 64 such processes and then let them fight based on who is already on CPU and acquire the lock. That way the period where nobody has a lock is reduced and that helps to cut out "artifact" idle time on the system. As soon as I get more "cycles" I will try variations of it but it would help if others can try it out in their own environments to see if it helps their instances. -Jignesh --Boundary_(ID_eVXC4WqioCX0u/qhs9KihQ) Content-type: text/html; charset=ISO-8859-1 Content-transfer-encoding: 7BIT

On 03/11/09 22:01, Scott Carey wrote:
Re: [PERFORM] Proposal of tunable fix for scalability of 8.4 On 3/11/09 3:27 PM, "Kevin Grittner" <Kevin.Grittner@wicourts.gov> wrote:

I'm a lot more interested in what's happening between 60 and 180 than
over 1000, personally.  If there was a RAID involved, I'd put it down
to better use of the numerous spindles, but when it's all in RAM it
makes no sense.

If there is enough lock contention and a common lock case is a short lived shared lock, it makes perfect sense sense.  Fewer readers are blocked waiting on writers at any given time.  Readers can ‘cut’ in line ahead of writers within a certain scope (only up to the number waiting at the time a shared lock is at the head of the queue).  Essentially this clumps up shared and exclusive locks into larger streaks, and allows for higher shared lock throughput.  
Exclusive locks may be delayed, but will NOT be starved, since on the next iteration, a streak of exclusive locks will occur first in the list and they will all process before any more shared locks can go.

This will even help in on a single CPU system if it is read dominated, lowering read latency and slightly increasing write latency.

If you want to make this more fair, instead of freeing all shared locks, limit the count to some number, such as the number of CPU cores.  Perhaps rather than wake-up-all-waiters=true, the parameter can be an integer representing how many shared locks can be freed at once if an exclusive lock is encountered.

Well I am waking up not just shared but shared and exclusives.. However i like your idea of waking up the next N waiters where N matches the number of cpus available.  In my case it is 64 so yes this works well since the idea being of all the 64 waiters running right now one will be able to lock the next lock  immediately and hence there are no cycles wasted where nobody gets a lock which is often the case when you say wake up only 1 waiter and hope that the process is on the CPU (which in my case it is 64 processes) and it is able to acquire the lock.. The probability of acquiring the lock within the next few cycles is much less for only 1 waiter  than giving chance to 64 such processes  and then let them fight based on who is already on CPU  and acquire the lock. That way the period where nobody has a lock is reduced and that helps to cut out "artifact"  idle time on the system.


As soon as I get more "cycles" I will try variations of it but it would help if others can try it out in their own environments to see if it helps their instances.


-Jignesh

--Boundary_(ID_eVXC4WqioCX0u/qhs9KihQ)--