1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2010-2014 Intel Corporation 3 */ 4 5 #include <stdio.h> 6 7 #include "test.h" 8 9 #include <stdint.h> 10 #include <stdlib.h> 11 #include <stdarg.h> 12 #include <inttypes.h> 13 #include <sys/queue.h> 14 #include <errno.h> 15 #include <string.h> 16 #include <unistd.h> 17 #include <sys/wait.h> 18 #include <libgen.h> 19 #include <dirent.h> 20 #include <limits.h> 21 22 #include <rte_common.h> 23 #include <rte_memory.h> 24 #include <rte_memzone.h> 25 #include <rte_eal.h> 26 #include <rte_launch.h> 27 #include <rte_per_lcore.h> 28 #include <rte_lcore.h> 29 #include <rte_errno.h> 30 #include <rte_branch_prediction.h> 31 #include <rte_atomic.h> 32 #include <rte_ring.h> 33 #include <rte_debug.h> 34 #include <rte_log.h> 35 #include <rte_mempool.h> 36 37 #ifdef RTE_LIBRTE_HASH 38 #include <rte_hash.h> 39 #include <rte_fbk_hash.h> 40 #endif /* RTE_LIBRTE_HASH */ 41 42 #ifdef RTE_LIBRTE_LPM 43 #include <rte_lpm.h> 44 #endif /* RTE_LIBRTE_LPM */ 45 46 #include <rte_string_fns.h> 47 48 #include "process.h" 49 50 #define launch_proc(ARGV) process_dup(ARGV, RTE_DIM(ARGV), __func__) 51 52 /* 53 * This function is called in the primary i.e. main test, to spawn off secondary 54 * processes to run actual mp tests. Uses fork() and exec pair 55 */ 56 static int 57 run_secondary_instances(void) 58 { 59 int ret = 0; 60 char coremask[10]; 61 62 #ifdef RTE_EXEC_ENV_LINUX 63 char tmp[PATH_MAX] = {0}; 64 char prefix[PATH_MAX] = {0}; 65 66 get_current_prefix(tmp, sizeof(tmp)); 67 68 snprintf(prefix, sizeof(prefix), "--file-prefix=%s", tmp); 69 #else 70 const char *prefix = ""; 71 #endif 72 73 /* good case, using secondary */ 74 const char *argv1[] = { 75 prgname, "-c", coremask, "--proc-type=secondary", 76 prefix 77 }; 78 /* good case, using auto */ 79 const char *argv2[] = { 80 prgname, "-c", coremask, "--proc-type=auto", 81 prefix 82 }; 83 /* bad case, using invalid type */ 84 const char *argv3[] = { 85 prgname, "-c", coremask, "--proc-type=ERROR", 86 prefix 87 }; 88 #ifdef RTE_EXEC_ENV_LINUX 89 /* bad case, using invalid file prefix */ 90 const char *argv4[] = { 91 prgname, "-c", coremask, "--proc-type=secondary", 92 "--file-prefix=ERROR" 93 }; 94 #endif 95 96 snprintf(coremask, sizeof(coremask), "%x", \ 97 (1 << rte_get_master_lcore())); 98 99 ret |= launch_proc(argv1); 100 ret |= launch_proc(argv2); 101 102 ret |= !(launch_proc(argv3)); 103 #ifdef RTE_EXEC_ENV_LINUX 104 ret |= !(launch_proc(argv4)); 105 #endif 106 107 return ret; 108 } 109 110 /* 111 * This function is run in the secondary instance to test that creation of 112 * objects fails in a secondary 113 */ 114 static int 115 run_object_creation_tests(void) 116 { 117 const unsigned flags = 0; 118 const unsigned size = 1024; 119 const unsigned elt_size = 64; 120 const unsigned cache_size = 64; 121 const unsigned priv_data_size = 32; 122 123 printf("### Testing object creation - expect lots of mz reserve errors!\n"); 124 125 rte_errno = 0; 126 if ((rte_memzone_reserve("test_mz", size, rte_socket_id(), 127 flags) == NULL) && 128 (rte_memzone_lookup("test_mz") == NULL)) { 129 printf("Error: unexpected return value from rte_memzone_reserve\n"); 130 return -1; 131 } 132 printf("# Checked rte_memzone_reserve() OK\n"); 133 134 rte_errno = 0; 135 if ((rte_ring_create( 136 "test_ring", size, rte_socket_id(), flags) == NULL) && 137 (rte_ring_lookup("test_ring") == NULL)){ 138 printf("Error: unexpected return value from rte_ring_create()\n"); 139 return -1; 140 } 141 printf("# Checked rte_ring_create() OK\n"); 142 143 rte_errno = 0; 144 if ((rte_mempool_create("test_mp", size, elt_size, cache_size, 145 priv_data_size, NULL, NULL, NULL, NULL, 146 rte_socket_id(), flags) == NULL) && 147 (rte_mempool_lookup("test_mp") == NULL)){ 148 printf("Error: unexpected return value from rte_mempool_create()\n"); 149 return -1; 150 } 151 printf("# Checked rte_mempool_create() OK\n"); 152 153 #ifdef RTE_LIBRTE_HASH 154 const struct rte_hash_parameters hash_params = { .name = "test_mp_hash" }; 155 rte_errno=0; 156 if ((rte_hash_create(&hash_params) != NULL) && 157 (rte_hash_find_existing(hash_params.name) == NULL)){ 158 printf("Error: unexpected return value from rte_hash_create()\n"); 159 return -1; 160 } 161 printf("# Checked rte_hash_create() OK\n"); 162 163 const struct rte_fbk_hash_params fbk_params = { .name = "test_fbk_mp_hash" }; 164 rte_errno=0; 165 if ((rte_fbk_hash_create(&fbk_params) != NULL) && 166 (rte_fbk_hash_find_existing(fbk_params.name) == NULL)){ 167 printf("Error: unexpected return value from rte_fbk_hash_create()\n"); 168 return -1; 169 } 170 printf("# Checked rte_fbk_hash_create() OK\n"); 171 #endif 172 173 #ifdef RTE_LIBRTE_LPM 174 rte_errno=0; 175 struct rte_lpm_config config; 176 177 config.max_rules = rte_socket_id(); 178 config.number_tbl8s = 256; 179 config.flags = 0; 180 if ((rte_lpm_create("test_lpm", size, &config) != NULL) && 181 (rte_lpm_find_existing("test_lpm") == NULL)){ 182 printf("Error: unexpected return value from rte_lpm_create()\n"); 183 return -1; 184 } 185 printf("# Checked rte_lpm_create() OK\n"); 186 #endif 187 188 return 0; 189 } 190 191 /* if called in a primary process, just spawns off a secondary process to 192 * run validation tests - which brings us right back here again... 193 * if called in a secondary process, this runs a series of API tests to check 194 * how things run in a secondary instance. 195 */ 196 int 197 test_mp_secondary(void) 198 { 199 if (rte_eal_process_type() == RTE_PROC_PRIMARY) { 200 return run_secondary_instances(); 201 } 202 203 printf("IN SECONDARY PROCESS\n"); 204 205 return run_object_creation_tests(); 206 } 207 208 REGISTER_TEST_COMMAND(multiprocess_autotest, test_mp_secondary); 209