hugeshmget03.c revision 3ca5db1c93e102dd01c3f80ac74d95141c2ca1b5
1/* 2 * 3 * Copyright (c) International Business Machines Corp., 2004 4 * 5 * This program is free software; you can redistribute it and/or modify 6 * it under the terms of the GNU General Public License as published by 7 * the Free Software Foundation; either version 2 of the License, or 8 * (at your option) any later version. 9 * 10 * This program is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See 13 * the GNU General Public License for more details. 14 * 15 * You should have received a copy of the GNU General Public License 16 * along with this program; if not, write to the Free Software 17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 18 */ 19 20/* 21 * NAME 22 * hugeshmget03.c 23 * 24 * DESCRIPTION 25 * hugeshmget03 - test for ENOSPC error 26 * 27 * ALGORITHM 28 * create large shared memory segments in a loop until reaching 29 * the system limit 30 * loop if that option was specified 31 * attempt to create yet another shared memory segment 32 * check the errno value 33 * issue a PASS message if we get ENOSPC 34 * otherwise, the tests fails 35 * issue a FAIL message 36 * call cleanup 37 * 38 * USAGE: <for command-line> 39 * hugeshmget03 [-c n] [-e] [-i n] [-I x] [-P x] [-t] 40 * where, -c n : Run n copies concurrently. 41 * -e : Turn on errno logging. 42 * -i n : Execute test n times. 43 * -I x : Execute test for x seconds. 44 * -P x : Pause for x seconds between iterations. 45 * -t : Turn on syscall timing. 46 * 47 * HISTORY 48 * 03/2001 - Written by Wayne Boyer 49 * 04/2004 - Updated by Robbie Williamson 50 * 51 * RESTRICTIONS 52 * none 53 */ 54 55#include "hugetlb.h" 56#include "safe_macros.h" 57#include "mem.h" 58 59char *TCID = "hugeshmget03"; 60int TST_TOTAL = 1; 61 62/* 63 * The MAXIDS value is somewhat arbitrary and may need to be increased 64 * depending on the system being tested. 65 */ 66#define MAXIDS 8192 67#define PATH_SHMMNI "/proc/sys/kernel/shmmni" 68 69static size_t shm_size; 70static int shm_id_1 = -1; 71static int num_shms; 72static int shm_id_arr[MAXIDS]; 73 74static long hugepages = 128; 75static long orig_shmmni; 76static option_t options[] = { 77 {"s:", &sflag, &nr_opt}, 78 {NULL, NULL, NULL} 79}; 80 81int main(int ac, char **av) 82{ 83 int lc; 84 85 tst_parse_opts(ac, av, options, NULL); 86 87 if (sflag) 88 hugepages = SAFE_STRTOL(NULL, nr_opt, 0, LONG_MAX); 89 90 setup(); 91 92 for (lc = 0; TEST_LOOPING(lc); lc++) { 93 tst_count = 0; 94 95 TEST(shmget(IPC_PRIVATE, shm_size, 96 SHM_HUGETLB | IPC_CREAT | IPC_EXCL | SHM_RW)); 97 if (TEST_RETURN != -1) { 98 tst_resm(TFAIL, "shmget succeeded unexpectedly"); 99 continue; 100 } 101 if (TEST_ERRNO == ENOSPC) 102 tst_resm(TPASS | TTERRNO, "shmget failed as expected"); 103 else 104 tst_resm(TFAIL | TTERRNO, "shmget failed unexpectedly " 105 "- expect errno=ENOSPC, got"); 106 } 107 cleanup(); 108 tst_exit(); 109} 110 111void setup(void) 112{ 113 long hpage_size; 114 115 tst_require_root(); 116 check_hugepage(); 117 tst_sig(NOFORK, DEF_HANDLER, cleanup); 118 tst_tmpdir(); 119 120 orig_hugepages = get_sys_tune("nr_hugepages"); 121 SAFE_FILE_SCANF(NULL, PATH_SHMMNI, "%ld", &orig_shmmni); 122 123 set_sys_tune("nr_hugepages", hugepages, 1); 124 SAFE_FILE_PRINTF(NULL, PATH_SHMMNI, "%ld", hugepages / 2); 125 126 hpage_size = read_meminfo("Hugepagesize:") * 1024; 127 shm_size = hpage_size; 128 129 /* 130 * Use a while loop to create the maximum number of memory segments. 131 * If the loop exceeds MAXIDS, then break the test and cleanup. 132 */ 133 num_shms = 0; 134 shm_id_1 = shmget(IPC_PRIVATE, shm_size, 135 SHM_HUGETLB | IPC_CREAT | IPC_EXCL | SHM_RW); 136 while (shm_id_1 != -1) { 137 shm_id_arr[num_shms++] = shm_id_1; 138 if (num_shms == MAXIDS) 139 tst_brkm(TBROK, cleanup, "The maximum number of " 140 "shared memory ID's has been reached. " 141 "Please increase the MAXIDS value in " 142 "the test."); 143 shm_id_1 = shmget(IPC_PRIVATE, shm_size, 144 SHM_HUGETLB | IPC_CREAT | IPC_EXCL | SHM_RW); 145 } 146 if (errno != ENOSPC) 147 tst_brkm(TBROK | TERRNO, cleanup, "shmget #setup"); 148 149 TEST_PAUSE; 150} 151 152void cleanup(void) 153{ 154 int i; 155 156 for (i = 0; i < num_shms; i++) 157 rm_shm(shm_id_arr[i]); 158 159 FILE_PRINTF(PATH_SHMMNI, "%ld", orig_shmmni); 160 set_sys_tune("nr_hugepages", orig_hugepages, 0); 161 162 tst_rmdir(); 163} 164