/** * @brief Create and initilize AVL tree for environment variables * in global variable called "env_avltree" * * @return void * * @retval None */ void create_env_avltree() { int i = 0; char varname_tmp[_MAX_ENV] = {'\0'}; char *name = NULL; char *value = NULL; AVL_IX_REC *pe = NULL; extern char **environ; if (env_avltree == NULL) { if ((env_avltree = malloc(sizeof(AVL_IX_DESC))) != NULL) { avl_create_index(env_avltree, AVL_NO_DUP_KEYS, 0); } } if (env_avltree != NULL) { for (i=0; environ[i] != NULL; i++) { (void)strncpy_s(varname_tmp, sizeof(varname_tmp), environ[i], _TRUNCATE); if ((name = strtok_s(varname_tmp, "=", &value)) != NULL) { if ((pe = malloc(sizeof(AVL_IX_REC) + WINLOG_BUF_SIZE + 1)) != NULL) { strncpy(pe->key, name, WINLOG_BUF_SIZE); if ((pe->recptr = (void *)strdup(value)) != NULL) avl_add_key(pe, env_avltree); free(pe); pe = NULL; } } } } }
/** * @brief * entlim_replace - replace a record with a key based on the key-string * if the record already exists, if not then this becomes equivalent * to entlim_add(). * * @param[in] keystr - key string whose key is to be built * @param[in] recptr - pointer to record * @param[in] ctx - pointer to avl descending order tree info * @param[in] free_leaf() - function called to delete data record when removing * exiting record. * * @return int * @retval 0 success, record replace/added * @retval -1 change failed */ int entlim_replace(const char *keystr, void *recptr, void *ctx, void fr_leaf(void *)) { pbs_entlim_key_t *pkey; int rc; pkey = entlim_create_key(keystr); if (pkey == NULL) return -1; pkey->recptr = recptr; if (avl_add_key((AVL_IX_REC *)pkey, (AVL_IX_DESC *)ctx) == AVL_IX_OK) { free(pkey); return 0; } else { /* record with key may already exist, try deleting it */ rc = avl_find_key((AVL_IX_REC *)pkey, (AVL_IX_DESC *)ctx); if (rc == AVL_IX_OK) { void *olddata = pkey->recptr; rc = avl_delete_key((AVL_IX_REC *)pkey, (AVL_IX_DESC *)ctx); if (rc == AVL_IX_OK) { fr_leaf(olddata); free(pkey); pkey = entlim_create_key(keystr); if (pkey == NULL) return -1; pkey->recptr = recptr; rc = avl_add_key((AVL_IX_REC *)pkey, (AVL_IX_DESC *)ctx); } } free(pkey); if (rc == AVL_IX_OK) return 0; else return -1; } }
/** * @brief Update the AVL tree in global variable * called "env_avltree" for environment variables * * @return void * * @retval None */ void update_env_avltree() { int i = 0; int found = 0; int ret = 0; char varname_tmp[_MAX_ENV] = {'\0'}; char *name = NULL; char *value = NULL; AVL_IX_REC *pe = NULL; extern char **environ; if (env_avltree != NULL) { avl_first_key(env_avltree); if ((pe = malloc(sizeof(AVL_IX_REC) + WINLOG_BUF_SIZE + 1)) != NULL) { while ((ret = avl_next_key(pe, env_avltree)) == AVL_IX_OK) { found = 0; for (i=0; environ[i] != NULL; i++) { if (!strncmp(environ[i], pe->key, strlen(pe->key))) { found = 1; break; } } if (!found) { free(pe->recptr); pe->recptr = NULL; avl_delete_key(pe, env_avltree); } } free(pe); pe = NULL; } for (i=0; environ[i] != NULL; i++) { (void)strncpy_s(varname_tmp, sizeof(varname_tmp), environ[i], _TRUNCATE); if ((name = strtok_s(varname_tmp, "=", &value)) != NULL) { if ((pe = malloc(sizeof(AVL_IX_REC) + WINLOG_BUF_SIZE + 1)) != NULL) { strncpy(pe->key, name, WINLOG_BUF_SIZE); if (avl_find_key(pe, env_avltree) != AVL_IX_OK) { if ((pe->recptr = (void *)strdup(value)) != NULL) avl_add_key(pe, env_avltree); } free(pe); pe = NULL; } } } } }
/** * @brief * entlim_add - add a record with a key based on the key-string * * @param[in] keystr - key string whose key is to be built * @param[in] recptr - pointer to record * @param[in] ctx - pointer to avl descending order tree info * * @return int * @retval 0 success, record added * @retval -1 add failed */ int entlim_add(const char *keystr, const void *recptr, void *ctx) { pbs_entlim_key_t *pkey; pkey = entlim_create_key(keystr); if (pkey == NULL) return -1; pkey->recptr = (AVL_RECPOS)recptr; if (avl_add_key((AVL_IX_REC *)pkey, (AVL_IX_DESC *)ctx) == AVL_IX_OK) { free(pkey); return 0; } else { return -1; } }