switch_core.c 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574
  1. /*
  2. * FreeSWITCH Modular Media Switching Software Library / Soft-Switch Application
  3. * Copyright (C) 2005-2018, Anthony Minessale II <anthm@freeswitch.org>
  4. *
  5. * Version: MPL 1.1
  6. *
  7. * The contents of this file are subject to the Mozilla Public License Version
  8. * 1.1 (the "License"); you may not use this file except in compliance with
  9. * the License. You may obtain a copy of the License at
  10. * http://www.mozilla.org/MPL/
  11. *
  12. * Software distributed under the License is distributed on an "AS IS" basis,
  13. * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
  14. * for the specific language governing rights and limitations under the
  15. * License.
  16. *
  17. * The Original Code is FreeSWITCH Modular Media Switching Software Library / Soft-Switch Application
  18. *
  19. * The Initial Developer of the Original Code is
  20. * Anthony Minessale II <anthm@freeswitch.org>
  21. * Portions created by the Initial Developer are Copyright (C)
  22. * the Initial Developer. All Rights Reserved.
  23. *
  24. * Contributor(s):
  25. * Chris Rienzo <chris@signalwire.com>
  26. * Seven Du <dujinfang@gmail.com>
  27. *
  28. *
  29. * switch_core.c -- tests core functions
  30. *
  31. */
  32. #include <switch.h>
  33. #include <test/switch_test.h>
  34. #if defined(HAVE_OPENSSL)
  35. #include <openssl/ssl.h>
  36. #endif
  37. #define ENABLE_SNPRINTFV_TESTS 0 /* Do not turn on for CI as this requires a lot of RAM */
  38. FST_CORE_BEGIN("./conf")
  39. {
  40. FST_SUITE_BEGIN(switch_core)
  41. {
  42. FST_SETUP_BEGIN()
  43. {
  44. switch_core_set_variable("spawn_instead_of_system", "false");
  45. }
  46. FST_SETUP_END()
  47. FST_TEARDOWN_BEGIN()
  48. {
  49. }
  50. FST_TEARDOWN_END()
  51. FST_TEST_BEGIN(test_switch_rand)
  52. {
  53. int i, c = 0;
  54. switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "\nLet's generate a few random numbers.\n");
  55. for (i = 0; i < 10; i++) {
  56. uint32_t rnd = switch_rand();
  57. switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "Random number %d\n", rnd);
  58. if (rnd == 1) {
  59. c++;
  60. }
  61. }
  62. /* We do not expect all random numbers to be 1 all 10 times. That would mean we have an error OR we are lucky to have 10 random ones! */
  63. fst_check(c < 10);
  64. }
  65. FST_TEST_END()
  66. FST_TEST_BEGIN(test_switch_uint31_t_overflow)
  67. {
  68. switch_uint31_t x;
  69. uint32_t overflow;
  70. x.value = 0x7fffffff;
  71. x.value++;
  72. fst_check_int_equals(x.value, 0);
  73. x.value++;
  74. fst_check_int_equals(x.value, 1);
  75. x.value -= 2;
  76. fst_check_int_equals(x.value, 0x7fffffff);
  77. overflow = (uint32_t)0x7fffffff + 1;
  78. x.value = overflow;
  79. fst_check_int_equals(x.value, 0);
  80. }
  81. FST_TEST_END()
  82. FST_TEST_BEGIN(test_switch_parse_cidr_v6)
  83. {
  84. ip_t ip, mask;
  85. uint32_t bits;
  86. fst_check(!switch_parse_cidr("fe80::/10", &ip, &mask, &bits));
  87. fst_check_int_equals(bits, 10);
  88. fst_check_int_equals(ip.v6.s6_addr[0], 0xfe);
  89. fst_check_int_equals(ip.v6.s6_addr[1], 0x80);
  90. fst_check_int_equals(ip.v6.s6_addr[2], 0);
  91. fst_check_int_equals(mask.v6.s6_addr[0], 0xff);
  92. fst_check_int_equals(mask.v6.s6_addr[1], 0xc0);
  93. fst_check_int_equals(mask.v6.s6_addr[2], 0);
  94. fst_check(!switch_parse_cidr("::/0", &ip, &mask, &bits));
  95. fst_check_int_equals(bits, 0);
  96. fst_check_int_equals(ip.v6.s6_addr[0], 0);
  97. fst_check_int_equals(ip.v6.s6_addr[1], 0);
  98. fst_check_int_equals(ip.v6.s6_addr[2], 0);
  99. fst_check_int_equals(mask.v6.s6_addr[0], 0);
  100. fst_check_int_equals(mask.v6.s6_addr[1], 0);
  101. fst_check_int_equals(mask.v6.s6_addr[2], 0);
  102. fst_check(!switch_parse_cidr("::1/128", &ip, &mask, &bits));
  103. fst_check_int_equals(bits, 128);
  104. fst_check_int_equals(ip.v6.s6_addr[0], 0);
  105. fst_check_int_equals(ip.v6.s6_addr[1], 0);
  106. fst_check_int_equals(ip.v6.s6_addr[2], 0);
  107. fst_check_int_equals(ip.v6.s6_addr[3], 0);
  108. fst_check_int_equals(ip.v6.s6_addr[4], 0);
  109. fst_check_int_equals(ip.v6.s6_addr[5], 0);
  110. fst_check_int_equals(ip.v6.s6_addr[6], 0);
  111. fst_check_int_equals(ip.v6.s6_addr[7], 0);
  112. fst_check_int_equals(ip.v6.s6_addr[8], 0);
  113. fst_check_int_equals(ip.v6.s6_addr[9], 0);
  114. fst_check_int_equals(ip.v6.s6_addr[10], 0);
  115. fst_check_int_equals(ip.v6.s6_addr[11], 0);
  116. fst_check_int_equals(ip.v6.s6_addr[12], 0);
  117. fst_check_int_equals(ip.v6.s6_addr[13], 0);
  118. fst_check_int_equals(ip.v6.s6_addr[14], 0);
  119. fst_check_int_equals(ip.v6.s6_addr[15], 1);
  120. fst_check_int_equals(mask.v6.s6_addr[0], 0xff);
  121. fst_check_int_equals(mask.v6.s6_addr[1], 0xff);
  122. fst_check_int_equals(mask.v6.s6_addr[2], 0xff);
  123. fst_check_int_equals(mask.v6.s6_addr[3], 0xff);
  124. fst_check_int_equals(mask.v6.s6_addr[4], 0xff);
  125. fst_check_int_equals(mask.v6.s6_addr[5], 0xff);
  126. fst_check_int_equals(mask.v6.s6_addr[6], 0xff);
  127. fst_check_int_equals(mask.v6.s6_addr[7], 0xff);
  128. fst_check_int_equals(mask.v6.s6_addr[8], 0xff);
  129. fst_check_int_equals(mask.v6.s6_addr[9], 0xff);
  130. fst_check_int_equals(mask.v6.s6_addr[10], 0xff);
  131. fst_check_int_equals(mask.v6.s6_addr[11], 0xff);
  132. fst_check_int_equals(mask.v6.s6_addr[12], 0xff);
  133. fst_check_int_equals(mask.v6.s6_addr[13], 0xff);
  134. fst_check_int_equals(mask.v6.s6_addr[14], 0xff);
  135. fst_check_int_equals(mask.v6.s6_addr[15], 0xff);
  136. }
  137. FST_TEST_END()
  138. #if ENABLE_SNPRINTFV_TESTS
  139. FST_TEST_BEGIN(test_snprintfv_1)
  140. {
  141. size_t src_buf_size = 0x100000001;
  142. char* src = calloc(1, src_buf_size);
  143. if (!src) {
  144. printf("bad allocation\n");
  145. return -1;
  146. }
  147. src[0] = '\xc0';
  148. memset(src + 1, '\x80', 0xffffffff);
  149. char dst[256];
  150. switch_snprintfv(dst, 256, "'%!q'", src);
  151. free(src);
  152. }
  153. FST_TEST_END()
  154. FST_TEST_BEGIN(test_snprintfv_2)
  155. {
  156. #define STR_LEN ((0x100000001 - 3) / 2)
  157. char* src = calloc(1, STR_LEN + 1); /* Account for NULL byte. */
  158. if (!src) { return -1; }
  159. memset(src, 'a', STR_LEN);
  160. char* dst = calloc(1, STR_LEN + 3); /* Account for extra quotes and NULL byte */
  161. if (!dst) { return -1; }
  162. switch_snprintfv(dst, 2 * STR_LEN + 3, "'%q'", src);
  163. free(src);
  164. free(dst);
  165. }
  166. FST_TEST_END()
  167. #endif
  168. FST_TEST_BEGIN(test_switch_is_number_in_range)
  169. {
  170. fst_check_int_equals(switch_is_uint_in_range("x5", 0, 10), SWITCH_FALSE);
  171. fst_check_int_equals(switch_is_uint_in_range("0", 1, 10), SWITCH_FALSE);
  172. fst_check_int_equals(switch_is_uint_in_range("-11", -10, 10), SWITCH_FALSE);
  173. fst_check_int_equals(switch_is_uint_in_range("-10", -10, 10), SWITCH_FALSE);
  174. fst_check_int_equals(switch_is_uint_in_range("-5", -10, 10), SWITCH_FALSE);
  175. fst_check_int_equals(switch_is_uint_in_range("-5", -10, 10), SWITCH_FALSE);
  176. fst_check_int_equals(switch_is_uint_in_range("5", -10, 10), SWITCH_FALSE);
  177. fst_check_int_equals(switch_is_uint_in_range("0", 0, 10), SWITCH_TRUE);
  178. fst_check_int_equals(switch_is_uint_in_range("10", 0, 10), SWITCH_TRUE);
  179. fst_check_int_equals(switch_is_uint_in_range("11", 0, 10), SWITCH_FALSE);
  180. }
  181. FST_TEST_END()
  182. FST_TEST_BEGIN(test_md5)
  183. {
  184. char digest[SWITCH_MD5_DIGEST_STRING_SIZE] = { 0 };
  185. char test_string[] = "test";
  186. switch_status_t status;
  187. status = switch_md5_string(digest, (void *)test_string, strlen(test_string));
  188. fst_check_int_equals(status, SWITCH_STATUS_SUCCESS);
  189. fst_check_string_equals(digest, "098f6bcd4621d373cade4e832627b4f6");
  190. }
  191. FST_TEST_END()
  192. FST_TEST_BEGIN(test_switch_event_add_header_leak)
  193. {
  194. switch_event_t* event;
  195. if (switch_event_create(&event, SWITCH_EVENT_CHANNEL_CALLSTATE) == SWITCH_STATUS_SUCCESS) {
  196. switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "Channel-Call-State-Number[0]", "1");
  197. switch_event_fire(&event);
  198. }
  199. if (switch_event_create(&event, SWITCH_EVENT_CHANNEL_CALLSTATE) == SWITCH_STATUS_SUCCESS) {
  200. switch_event_add_header_string(event, SWITCH_STACK_BOTTOM, "Channel-Call-State-Number[5000]", "12");
  201. switch_event_fire(&event);
  202. }
  203. }
  204. FST_TEST_END()
  205. FST_TEST_BEGIN(test_xml_free_attr)
  206. {
  207. switch_xml_t parent_xml = switch_xml_new("xml");
  208. switch_xml_t xml = switch_xml_add_child_d(parent_xml, "test", 1);
  209. switch_xml_set_attr(xml, "a1", "v1");
  210. switch_xml_set_attr_d(xml, "a2", "v2");
  211. switch_xml_free(parent_xml);
  212. }
  213. FST_TEST_END()
  214. FST_TEST_BEGIN(test_xml_set_attr)
  215. {
  216. switch_xml_t parent_xml = switch_xml_new("xml");
  217. switch_xml_t xml = switch_xml_add_child_d(parent_xml, "test", 1);
  218. switch_xml_set_attr_d(xml, "test1", "1");
  219. switch_xml_set_attr(xml, "a1", "v1");
  220. switch_xml_set_attr_d(xml, "a2", "v2");
  221. switch_xml_set_attr(xml, "test1", NULL);
  222. switch_xml_set_attr_d(xml, "test2", "2");
  223. switch_xml_set_attr_d(xml, "a3", "v3");
  224. switch_xml_set_attr(xml, "test2", NULL);
  225. switch_xml_set_attr(xml, "a1", NULL);
  226. switch_xml_set_attr(xml, "a2", NULL);
  227. switch_xml_set_attr(xml, "a3", NULL);
  228. switch_xml_free(parent_xml);
  229. }
  230. FST_TEST_END()
  231. #ifdef HAVE_OPENSSL
  232. FST_TEST_BEGIN(test_md5)
  233. {
  234. char *digest_name = "md5";
  235. char *digest_str = NULL;
  236. const char *str = "test data";
  237. unsigned int outputlen;
  238. switch_status_t status = switch_digest_string(digest_name, &digest_str, str, strlen(str), &outputlen);
  239. fst_check_int_equals(status, SWITCH_STATUS_SUCCESS);
  240. fst_check_string_equals(digest_str, "eb733a00c0c9d336e65691a37ab54293");
  241. switch_safe_free(digest_str);
  242. }
  243. FST_TEST_END()
  244. FST_TEST_BEGIN(test_sha256)
  245. {
  246. char *digest_name = "sha256";
  247. char *digest_str = NULL;
  248. const char *str = "test data";
  249. unsigned int outputlen;
  250. switch_status_t status = switch_digest_string(digest_name, &digest_str, str, strlen(str), &outputlen);
  251. fst_check_int_equals(status, SWITCH_STATUS_SUCCESS);
  252. fst_check_string_equals(digest_str, "916f0027a575074ce72a331777c3478d6513f786a591bd892da1a577bf2335f9");
  253. switch_safe_free(digest_str);
  254. }
  255. FST_TEST_END()
  256. #endif
  257. #if OPENSSL_VERSION_NUMBER >= 0x10101000L
  258. FST_TEST_BEGIN(test_sha512_256)
  259. {
  260. char *digest_name = "sha512-256";
  261. char *digest_str = NULL;
  262. const char *str = "test data";
  263. unsigned int outputlen;
  264. switch_status_t status = switch_digest_string(digest_name, &digest_str, str, strlen(str), &outputlen);
  265. fst_check_int_equals(status, SWITCH_STATUS_SUCCESS);
  266. fst_check_string_equals(digest_str, "9fe875600168548c1954aed4f03974ce06b3e17f03a70980190da2d7ef937a43");
  267. switch_safe_free(digest_str);
  268. }
  269. FST_TEST_END()
  270. #endif
  271. #ifndef WIN32
  272. FST_TEST_BEGIN(test_fork)
  273. {
  274. switch_stream_handle_t exec_result = { 0 };
  275. SWITCH_STANDARD_STREAM(exec_result);
  276. fst_requires(switch_stream_system_fork("ip ad sh", &exec_result) == 0);
  277. fst_requires(!zstr(exec_result.data));
  278. switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "%s\n", (char *)exec_result.data);
  279. fst_requires(switch_stream_system_fork("ip ad sh | grep link", &exec_result) == 0);
  280. fst_requires(!zstr(exec_result.data));
  281. switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "%s\n", (char *)exec_result.data);
  282. switch_safe_free(exec_result.data);
  283. }
  284. FST_TEST_END()
  285. #endif
  286. FST_TEST_BEGIN(test_non_fork_exec_set)
  287. {
  288. char *var_test = switch_core_get_variable_dup("test");
  289. char *var_default_password = switch_core_get_variable_dup("default_password");
  290. switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "global_getvar test: %s\n", switch_str_nil(var_test));
  291. switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "global_getvar default_password: %s\n", switch_str_nil(var_default_password));
  292. fst_check_string_not_equals(var_test, "");
  293. fst_check_string_not_equals(var_default_password, "");
  294. fst_check_string_equals(var_test, var_default_password);
  295. switch_safe_free(var_test);
  296. switch_safe_free(var_default_password);
  297. }
  298. FST_TEST_END()
  299. FST_TEST_BEGIN(test_switch_sockaddr_new)
  300. {
  301. int type = SOCK_DGRAM;
  302. switch_port_t port = 12044;
  303. const char *ip = "127.0.0.1";
  304. switch_memory_pool_t *pool = NULL;
  305. switch_sockaddr_t *local_addr = NULL;
  306. switch_socket_t *sock = NULL;
  307. switch_bool_t r = SWITCH_FALSE;
  308. if (switch_core_new_memory_pool(&pool) == SWITCH_STATUS_SUCCESS) {
  309. if (switch_sockaddr_new(&local_addr, ip, port, pool) == SWITCH_STATUS_SUCCESS) {
  310. if (switch_socket_create(&sock, switch_sockaddr_get_family(local_addr), type, 0, pool) == SWITCH_STATUS_SUCCESS) {
  311. if (switch_socket_bind(sock, local_addr) == SWITCH_STATUS_SUCCESS) {
  312. r = SWITCH_TRUE;
  313. }
  314. switch_socket_close(sock);
  315. }
  316. }
  317. switch_core_destroy_memory_pool(&pool);
  318. }
  319. fst_check_int_equals(r, SWITCH_TRUE);
  320. }
  321. FST_TEST_END()
  322. FST_TEST_BEGIN(test_switch_spawn)
  323. {
  324. #ifdef __linux__
  325. int status;
  326. switch_stream_handle_t stream = { 0 };
  327. status = switch_spawn("echo CHECKING_BAD_FILE_DESCRIPTOR", SWITCH_TRUE);
  328. fst_check_int_equals(status, 0);
  329. SWITCH_STANDARD_STREAM(stream);
  330. status = switch_stream_spawn("echo DEADBEEF", SWITCH_FALSE, SWITCH_TRUE, &stream);
  331. fst_check_int_equals(status, 0);
  332. fst_check_string_equals(stream.data, "DEADBEEF\n");
  333. switch_safe_free(stream.data);
  334. SWITCH_STANDARD_STREAM(stream);
  335. status = switch_stream_spawn("echo DEADBEEF", SWITCH_FALSE, SWITCH_FALSE, &stream);
  336. fst_check_int_equals(status, 0);
  337. fst_check_string_equals(stream.data, "DEADBEEF\n");
  338. switch_safe_free(stream.data);
  339. printf("\nExpected warning check ... ");
  340. status = switch_spawn("false", SWITCH_TRUE);
  341. fct_chk_neq_int(status, 0);
  342. status = switch_spawn("false", SWITCH_FALSE);
  343. fct_chk_eq_int(status, 0);
  344. status = switch_spawn("true", SWITCH_TRUE);
  345. fct_chk_eq_int(status, 0);
  346. #endif
  347. }
  348. FST_TEST_END()
  349. FST_TEST_BEGIN(test_switch_spawn_instead_of_system)
  350. {
  351. #ifdef __linux__
  352. int status;
  353. char file_uuid[SWITCH_UUID_FORMATTED_LENGTH + 1] = { 0 };
  354. const char *filename = NULL;
  355. const char *cmd = NULL;
  356. // tell FS core to use posix_spawn() instead of popen() and friends
  357. switch_core_set_variable("spawn_instead_of_system", "true");
  358. // echo text to a file using shell redirection- this will ensure the command was executed in a shell, as expected
  359. switch_uuid_str(file_uuid, sizeof(file_uuid));
  360. filename = switch_core_sprintf(fst_pool, "%s" SWITCH_PATH_SEPARATOR "%s", SWITCH_GLOBAL_dirs.temp_dir, file_uuid);
  361. cmd = switch_core_sprintf(fst_pool, "echo test_switch_spawn_instead_of_system with spaces > %s", filename);
  362. status = switch_system(cmd, SWITCH_TRUE);
  363. fst_check_int_equals(status, 0);
  364. fst_xcheck(status == 0, "Expect switch_system() command to return 0");
  365. fst_xcheck(switch_file_exists(filename, fst_pool) == SWITCH_STATUS_SUCCESS, "Expect switch_system() to use shell to create file via > redirection");
  366. unlink(filename);
  367. // verify exec-set works- see conf/freeswitch.xml for test setup of shell_exec_set_test global variable
  368. fst_check_string_equals(switch_core_get_variable("shell_exec_set_test"), "usr");
  369. #endif
  370. }
  371. FST_TEST_END()
  372. FST_TEST_BEGIN(test_switch_safe_atoXX)
  373. {
  374. fst_check_int_equals(switch_safe_atoi("1", 0), 1);
  375. fst_check_int_equals(switch_safe_atoi("", 2), 0);
  376. fst_check_int_equals(switch_safe_atoi(0, 3), 3);
  377. fst_check_int_equals(switch_safe_atol("9275806", 0), 9275806);
  378. fst_check_int_equals(switch_safe_atol("", 2), 0);
  379. fst_check_int_equals(switch_safe_atol(0, 3), 3);
  380. fst_check_int_equals(switch_safe_atoll("9275806", 0), 9275806);
  381. fst_check_int_equals(switch_safe_atoll("", 2), 0);
  382. fst_check_int_equals(switch_safe_atoll(0, 3), 3);
  383. }
  384. FST_TEST_END()
  385. FST_TEST_BEGIN(test_switch_core_hash_insert_dup)
  386. {
  387. char *magicnumber = malloc(9);
  388. switch_hash_index_t *hi;
  389. switch_hash_t *hash = NULL;
  390. void *hash_val;
  391. switch_core_hash_init(&hash);
  392. fst_requires(hash);
  393. snprintf(magicnumber, 9, "%s", "DEADBEEF");
  394. switch_core_hash_insert_dup(hash, "test", (const char *)magicnumber);
  395. snprintf(magicnumber, 9, "%s", "BAADF00D");
  396. hi = switch_core_hash_first(hash);
  397. switch_core_hash_this(hi, NULL, NULL, &hash_val);
  398. fst_check_string_equals(hash_val, "DEADBEEF");
  399. switch_safe_free(hash_val);
  400. free(magicnumber);
  401. free(hi);
  402. switch_core_hash_destroy(&hash);
  403. fst_requires(hash == NULL);
  404. }
  405. FST_TEST_END()
  406. FST_TEST_BEGIN(test_switch_core_hash_insert_alloc)
  407. {
  408. char *item;
  409. switch_hash_index_t *hi;
  410. switch_hash_t *hash = NULL;
  411. void *hash_val;
  412. switch_core_hash_init(&hash);
  413. fst_requires(hash);
  414. item = switch_core_hash_insert_alloc(hash, "test", 10);
  415. fst_requires(item);
  416. snprintf(item, 9, "%s", "DEADBEEF");
  417. hi = switch_core_hash_first(hash);
  418. switch_core_hash_this(hi, NULL, NULL, &hash_val);
  419. fst_check_string_equals(hash_val, "DEADBEEF");
  420. free(hi);
  421. switch_core_hash_destroy(&hash);
  422. fst_requires(hash == NULL);
  423. free(item);
  424. }
  425. FST_TEST_END()
  426. FST_TEST_BEGIN(test_switch_core_hash_insert_pointer)
  427. {
  428. int i, sum = 0;
  429. switch_hash_index_t *hi;
  430. switch_hash_t *hash = NULL;
  431. switch_core_hash_init(&hash);
  432. fst_requires(hash);
  433. for (i = 0; i < 10; i++) {
  434. int *num = malloc(sizeof(int));
  435. *num = i;
  436. fst_check_int_equals(switch_core_hash_insert_pointer(hash, (void*)num), SWITCH_STATUS_SUCCESS);
  437. }
  438. i = 0;
  439. for (hi = switch_core_hash_first(hash); hi; hi = switch_core_hash_next(&hi)) {
  440. void *hash_val;
  441. switch_core_hash_this(hi, NULL, NULL, &hash_val);
  442. sum += *(int*)hash_val;
  443. free(hash_val);
  444. i++;
  445. }
  446. fst_check_int_equals(i, 10);
  447. fst_check_int_equals(sum, 45);
  448. switch_core_hash_destroy(&hash);
  449. fst_requires(hash == NULL);
  450. }
  451. FST_TEST_END()
  452. FST_SESSION_BEGIN(test_switch_channel_get_variable_strdup)
  453. {
  454. const char *val;
  455. switch_channel_t *channel = switch_core_session_get_channel(fst_session);
  456. fst_check(channel);
  457. switch_channel_set_variable(channel, "test_var", "test_value");
  458. fst_check(!switch_channel_get_variable_strdup(channel, "test_var_does_not_exist"));
  459. val = switch_channel_get_variable_strdup(channel, "test_var");
  460. fst_check(val);
  461. fst_check_string_equals(val, "test_value");
  462. free((char *)val);
  463. }
  464. FST_SESSION_END()
  465. FST_SESSION_BEGIN(test_switch_channel_get_variable_buf)
  466. {
  467. char buf[16] = { 0 };
  468. switch_channel_t *channel = switch_core_session_get_channel(fst_session);
  469. fst_check(channel);
  470. switch_channel_set_variable(channel, "test_var", "test_value");
  471. fst_check(switch_channel_get_variable_buf(channel, "test_var", buf, sizeof(buf)) == SWITCH_STATUS_SUCCESS);
  472. fst_check_string_equals(buf, "test_value");
  473. fst_check(switch_channel_get_variable_buf(channel, "test_var_does_not_exist", buf, sizeof(buf)) == SWITCH_STATUS_FALSE);
  474. }
  475. FST_SESSION_END()
  476. }
  477. FST_SUITE_END()
  478. }
  479. FST_CORE_END()