SHMCTL(2) | Руководство программиста Linux | SHMCTL(2) |
shmctl - управление общей памятью System V
#include <sys/ipc.h> #include <sys/shm.h>
int shmctl(int shmid, int cmd, struct shmid_ds *buf);
Вызов shmctl() выполняет управляющую операцию, указанную в cmd, над общим сегментом памяти System V, чей идентификатор задан в shmid.
В аргументе buf содержится указатель на структуру shmid_ds, определённую в <sys/shm.h> следующим образом:
struct shmid_ds { struct ipc_perm shm_perm; /* владелец и права */ size_t shm_segsz; /* размер сегмента (байты) */ time_t shm_atime; /* время последнего подключения */ time_t shm_dtime; /* время последнего отключения */ time_t shm_ctime; /* время последнего изменения */ pid_t shm_cpid; /* PID создателя */ pid_t shm_lpid; /* PID последнего выполнявшего shmat(2)/shmdt(2) */ shmatt_t shm_nattch; /* текущее количество подключений */ ... };
Структура ipc_perm определена следующим образом (значения полей устанавливаются с помощью IPC_SET):
struct ipc_perm { key_t __key; /* ключ, передаваемый в shmget(2) */ uid_t uid; /* эффективный UID владельца */ gid_t gid; /* эффективный GID владельца */ uid_t cuid; /* эффективный UID создателя */ gid_t cgid; /* эффективный GID создателя */ unsigned short mode; /* права + флаги SHM_DEST и SHM_LOCKED */ unsigned short __seq; /* порядковый номер */ };
Возможные значения cmd:
struct shminfo { unsigned long shmmax; /* максимальный размер сегмента */ unsigned long shmmin; /* минимальный размер сегмента; всегда 1 */ unsigned long shmmni; /* максимальное количество сегментов */ unsigned long shmseg; /* максимальное количество сегментов, к которому может подключиться; процесс не используется в ядре */ unsigned long shmall; /* макс. количество страниц общей памяти в системе */ };
struct shm_info { int used_ids; /* количество используемых в данный момент сегментов */ unsigned long shm_tot; /* общее количество общих страниц памяти */ unsigned long shm_rss; /* количество общих страниц, находящихся в памяти */ unsigned long shm_swp; /* количество страниц памяти в пространстве подкачки */ unsigned long swap_attempts; /* не используется, начиная с Linux 2.4 */ unsigned long swap_successes; /* не используется, начиная с Linux 2.4 */ };
Вызывающий может запретить или разрешить размещение общего сегмента памяти в пространство подкачки с помощью следующих значений cmd:
В ядрах до версии 2.6.10 только привилегированный процесс мог использовать SHM_LOCK и SHM_UNLOCK. Начиная с ядра версии 2.6.10 непривилегированный процесс может использовать эти операции, если его эффективный UID совпадает с UID владельца или создателя сегмента и (для SHM_LOCK) количество блокируемой памяти находится в пределах ресурса RLIMIT_MEMLOCK (см. setrlimit(2)).
При успешном выполнении операции IPC_INFO или SHM_INFO возвращается индекс самого последнего использованного элемента внутреннего массива ядра, в котором записывается информация о всех общих сегментах памяти (эта информация может быть использована в повторяющихся операциях SHM_STAT или SHM_STAT_ANY для получения информации о всех общих сегментах памяти системы). При успешном выполнении операции SHM_STAT возвращается идентификатор общего сегмента памяти, чей индекс был указан в shmid. При успешном выполнении других операций возвращается 0.
В случае ошибки возвращается -1 и значение errno устанавливается соответствующим образом.
POSIX.1-2001, POSIX.1-2008, SVr4.
Включение файлов <sys/types.h> и <sys/ipc.h> не требуется в Linux или любых версий POSIX. Однако, некоторые старые реализации требуют включения данных заголовочных файлов, и это также требуется по SVID. В приложениях, которые нужно перенести на такие старые системы, может потребоваться включить данных заголовочные файлы.
Операции IPC_INFO, SHM_STAT и SHM_INFO используются программой ipcs(1) для получения информации о выделенных ресурсах. В будущем для этого может быть задействован интерфейс файловой системы /proc.
Linux разрешает процессу подключаться (shmat(2)) к общему сегменту память, который уже помечен как удалённый с помощью shmctl(IPC_RMID). Это свойство недоступно в других реализациях UNIX; в переносимых приложениях лучше не использовать это свойство.
В Linux 2.2 различные поля struct shmid_ds имели тип short. В Linux 2.4 тип был изменён на long. Для задействования преимуществ этого изменения необходима перекомпиляция программы с glibc-2.1.91 или более поздней версией (ядро различает старые и новые вызовы по флагу IPC_64 в аргументе cmd).
mlock(2), setrlimit(2), shmget(2), shmop(2), capabilities(7), svipc(7)
2019-03-06 | Linux |