12

I've used the documentation from PostgreSQL to set it for example this config:

>>> cat /proc/meminfo 
MemTotal:       16345480 kB
MemFree:         1770128 kB
Buffers:          382184 kB
Cached:         10432632 kB
SwapCached:            0 kB
Active:          9228324 kB
Inactive:        4621264 kB
Active(anon):    7019996 kB
Inactive(anon):   548528 kB
Active(file):    2208328 kB
Inactive(file):  4072736 kB
Unevictable:           0 kB
Mlocked:               0 kB
SwapTotal:             0 kB
SwapFree:              0 kB
Dirty:              3432 kB
Writeback:             0 kB
AnonPages:       3034588 kB
Mapped:          4243720 kB
Shmem:           4533752 kB
Slab:             481728 kB
SReclaimable:     440712 kB
SUnreclaim:        41016 kB
KernelStack:        1776 kB
PageTables:        39208 kB
NFS_Unstable:          0 kB
Bounce:                0 kB
WritebackTmp:          0 kB
CommitLimit:     8172740 kB
Committed_AS:   14935216 kB
VmallocTotal:   34359738367 kB
VmallocUsed:      399340 kB
VmallocChunk:   34359334908 kB
HardwareCorrupted:     0 kB
AnonHugePages:    456704 kB
HugePages_Total:       0
HugePages_Free:        0
HugePages_Rsvd:        0
HugePages_Surp:        0
Hugepagesize:       2048 kB
DirectMap4k:       12288 kB
DirectMap2M:    16680960 kB

>>> ipcs -l          

------ Shared Memory Limits --------
max number of segments = 4096
max seg size (kbytes) = 4316816
max total shared memory (kbytes) = 4316816
min seg size (bytes) = 1

------ Semaphore Limits --------
max number of arrays = 128
max semaphores per array = 250
max semaphores system wide = 32000
max ops per semop call = 32
semaphore max value = 32767

------ Messages Limits --------
max queues system wide = 31918
max size of message (bytes) = 8192
default max size of queue (bytes) = 16384

sysctl.conf extract, calculated by me:

kernel.shmall = 1079204
kernel.shmmax = 4420419584

postgresql.conf non defaults, calculated by me:

max_connections = 60            # (change requires restart)
shared_buffers = 4GB            # min 128kB
work_mem = 4MB              # min 64kB
wal_sync_method = open_sync     # the default is the first option
checkpoint_segments = 16        # in logfile segments, min 1, 16MB each
checkpoint_completion_target = 0.9  # checkpoint target duration, 0.0 - 1.0
effective_cache_size = 6GB

Is this appropriate ? If not (or not necessarily), in which case would it be appropriate ?

We did note nice performance improvements with this config, how would you improve it ?

How to calculate kernel memory management parameters ?

Can anybody explain how to really set them from the ground up ?

jpic
  • 232
  • 1
  • 3
  • 14
  • That's a lot of questions, and you haven't told us what your current problem is (if any), or what your usage pattern is. It might be worth getting a book on PostgreSQL performance. – hmallett Mar 26 '12 at 13:59
  • My problem is that I am not convinced that I made the right settings. I think kernel memory management options are not PostgreSQL specific also I'm not sure that PostgreSQL is the best placed to talk about these options. Sure, they are heavily mentioned in any article about PostgreSQL performance, but that's Linux options and I'm looking forward to really understand how to tune them in general. – jpic Mar 26 '12 at 14:06

4 Answers4

12

I answered this for another question here:

Git fails to push with error 'out of memory'

I'm not answering all your questions here, but the question in your title:

How to set shmall, shmmax, shmmni, etc … in general and for postgresql

With some kernel distributions, there are settings which prevent the kernel from allocation max memory to a single process:

Set Kernel Parameters

Modify the /etc/sysctl.conf file to include the lines appropriate to your operating system:

# Red Hat Enterprise Linux 3.0 and CentOS 3.x 
kernel.shmmax = 2147483648
kernel.shmmni = 4096
kernel.shmall = 2097152
kernel.shmmin = 1
kernel.shmseg = 10

# semaphores: 
semmsl, semmns, semopm, semmni kernel.sem = 250 32000 100 128
fs.file-max = 65536

# Red Hat Enterprise Linux 4.0 and CentOS 4.x 
kernel.shmmax = 536870912
kernel.shmmni = 4096
kernel.shmall = 2097152

If your process exceeds the limits, the kernel will kill the process despite the max memory reported being available on your system.

Note: be careful with these settings. You probably don't want to use the settings in that example as i pulled them from a server in our environment.

A few extra notes to mention:

To update and test kernel settings with sysctl, use following commands:

List current settings:

sysctl -A | grep shm
sysctl -w kernel.shmmax=<value> to write in sysctl.conf
sysctl -p /etc/sysctl.conf to read/reload the values from sysctl.conf

Disable secure linux by editing the /etc/selinux/config file, making sure the SELINUX flag is set as follows.

SELINUX=disabled

Is this appropriate ? If not (or not necessarily), in which case would it be appropriate ?

The kernel settings are usually more strictly defined in datacenter environments when ISP providers don't want a single customer process hogging all the resources on a shared server.

You don't usually have to set the kernel memory parameters unless you have a process that is getting killed by the kernel due to resource starvation.

In some cases, postgres can also allocate more mem to specific page sizes than what's available in shared mememory:

* The PostgreSQL server failed to start. Please check the log output:
2011-11-04 05:06:26 UTC FATAL: could not create shared memory segment: Invalid
argument
2011-11-04 05:06:26 UTC DETAIL: Failed system call was shmget(key=5432001, size
=161849344, 03600).
2011-11-04 05:06:26 UTC HINT: This error usually means that PostgreSQL’s reques
t for a shared memory segment exceeded your kernel’s SHMMAX parameter. You can
either reduce the request size or reconfigure the kernel with larger SHMMAX. To
reduce the request size (currently 161849344 bytes), reduce PostgreSQL’s shared
_buffers parameter (currently 19200) and/or its max_connections parameter (curre
ntly 53).
If the request size is already small, it’s possible that it is less than
your kernel’s SHMMIN parameter, in which case raising the request size or recon
figuring SHMMIN is called for.
The PostgreSQL documentation contains more information about shared memo
ry configuration.
…fail!

Errors such as the example above, can be resolved by tweaking your kernel resource settings. The recommended settings and methods, for determining resource settings, are described in detail here:

http://www.postgresql.org/docs/9.1/static/kernel-resources.html

However, you really don't have to touch these settings unless you're encountering resource starvation situations related to the postgres process. These situations occur, most often, in shared environments or servers with little resources allocated to them.

Can anybody explain how to really set them from the ground up ?

As for Postgres tuning, you should read this:

http://wiki.postgresql.org/wiki/Tuning_Your_PostgreSQL_Server

pevik
  • 286
  • 1
  • 12
Jason Huntley
  • 1,253
  • 3
  • 10
  • 22
  • 1
    "Note: be careful with these settings. You probably don't want to use the settings in that example as i pulled them from a server in our environment." How should I calculate them for my environments ? – jpic Apr 03 '12 at 20:00
  • 1
    Hey jpic, I updated to provide more detail regarding kernel settings. – Jason Huntley Apr 03 '12 at 20:34
2

Oh!! I find a wonderful tool that gives you a starting point to tune up your postgresql server here.

http://pgtune.leopard.in.ua/

Pablo Luna
  • 21
  • 3
  • This tool is not about to calculate the optimus configuration, it gives you a starting point to tune up your server, as it gives you an answer based mainly on your hardware settings. Database size, number of queries and sizes are also important to tune config parameters. – EAmez Oct 30 '19 at 09:03
1

Those kernel configurations are global, not process specific, so it is appropriate to set them in sysctl.conf.

mgorven
  • 30,036
  • 7
  • 76
  • 121
  • The question is about determining values for kernel shared memory management parameters, the "how", not the "where" ... Thanks for the effort put into your answer. – jpic Mar 27 '12 at 08:38
  • yep. there where is trivial. the how is the meat of it. – Henley Feb 01 '14 at 19:13
0

Well it depends what else is running on the server, if this is a pure PostgreSQL server then PostgreSQL is the right place to look for these settings.
If you are running other applications/services that have specific memory needs then you will need to find an optimal setting between these different applications.

If you are seeing an increased performance on the database, and no loss of performance on other applications then i would not worry about this.

Generally databases are the most sensitive to memory settings, since they are also most likely the bottleneck on application performance it makes sense to optimize you system for the DB.

Sibster
  • 397
  • 1
  • 3
  • How "to find an optimal setting between these different applications" ? I don't have a performance problem, I'm looking for the canonical way to configure shared memory kernel settings, how would a real pro do it ? Say someone handles you a running server with a handful of services and pays you to set just memory management settings, what would you do ? – jpic Apr 02 '12 at 09:24
  • There is no golden rule, you just look what the vendor says, and test it. If you have multiple applications running on the same machine try to optimize for the most memory intensive application, in most cases the DB. But besides looking at vendor suggestions en testing them there is no single right solution – Sibster Apr 02 '12 at 09:51
  • I know there is no golden rule. I hoped maybe the bounty would motivate someone who actually fully understands this to write some directions. But I think nobody really fully understands this after all - since nobody is able to give a simple explanation. – jpic Apr 02 '12 at 09:52