#include "libublsettings.h"

int yon_char_find_last(char *source, char find){
    int size = strlen(source);
    int i=size;
    for (;source[i]!=find&&i>0;i--);
    if (source[i]!=find)i=-1;
    return i;
}

char *yon_char_append(const char *source, const char *append)
{
    if (source && append)
    {
        int size = strlen(source) + strlen(append) + 1;
        char *final = malloc(size);
        memset(final, 0, size);
        sprintf(final, "%s%s", source, append);
        return final;
    }
        return NULL;
}

char *yon_char_append_c(const char *source, char append)
{
    if (source)
    {
        size_t size = strlen(source) + 2;
        char *final = malloc(size);
        memset(final, 0, size);
        memcpy(final,source,size-2);
        final[size-2]=append;
        return final;
    }
        return NULL;
}

char *yon_char_append_element(char *source,char *target, char *divider){
    if (!yon_char_is_empty(target)&&!yon_char_is_empty(divider)){
        if (yon_char_is_empty(source)) return yon_char_new(target);
        int size;
        config_str parsed = yon_char_parse(source,&size,divider);
        if (yon_char_parsed_check_exist(parsed,size,target)==-1){
            yon_char_parsed_add_or_create_if_exists(parsed,&size,target);
            return yon_char_parsed_to_string(parsed,size,divider);
        }
    }
    return yon_char_new(source);
}

char *yon_char_append_elements(char *source,char *target, char *divider){
    if (!yon_char_is_empty(target)&&!yon_char_is_empty(divider)){
        if (yon_char_is_empty(source)) return yon_char_new(target);
        int size=0;
        int target_size=0;
        config_str parsed = yon_char_parse(source,&size,divider);
        config_str target_parsed = yon_char_parse(target,&target_size,divider);
        for (int i=0;i<target_size;i++){
            if (yon_char_parsed_check_exist(parsed,size,target_parsed[i])==-1){
                yon_char_parsed_add_or_create_if_exists(parsed,&size,target_parsed[i]);
            }
        }
        yon_char_parsed_free(target_parsed,target_size);
        return yon_char_parsed_to_string(parsed,size,divider);
    }
    return yon_char_new(source);
}

char *yon_char_force_append_element(char *source,char *target, char *divider){
    if (yon_char_is_empty(target)){
        target = "";
    }
    if (!yon_char_is_empty(divider)){
        if (!source) return yon_char_new(target);
        int size;
        config_str parsed = yon_char_parse(source,&size,divider);
        yon_char_parsed_add_or_create_if_exists(parsed,&size,target);
        return yon_char_parsed_to_string_full(parsed,size,divider);
    }
    return yon_char_new(source);
}

char *yon_char_remove_element(char *source,char *target, char *divider){
    if (!yon_char_is_empty(source)&&!yon_char_is_empty(target)&&!yon_char_is_empty(divider)){
        if (yon_char_is_empty(source)) return NULL;
        int size;
        config_str parsed = yon_char_parse(source,&size,divider);
        int pos = yon_char_parsed_check_exist(parsed,size,target);
        if (pos!=-1){
            parsed = yon_char_parsed_rip(parsed,&size,pos);
            return yon_char_parsed_to_string(parsed,size,divider);
        }
    }
    return yon_char_new(source);
}

char *yon_char_remove_elements(char *source,char *target, char *divider){
    if (!yon_char_is_empty(source)&&!yon_char_is_empty(target)&&!yon_char_is_empty(divider)){
        int size;
        int element_size;
        config_str parsed = yon_char_parse(source,&size,divider);
        config_str parsed_element = yon_char_parse(target,&element_size,divider);
        for (int i=0;i<element_size;i++){
            if (yon_char_is_empty(source)) return NULL;
            int pos = yon_char_parsed_check_exist(parsed,size,parsed_element[i]);
            if (pos!=-1){
                parsed = yon_char_parsed_rip(parsed,&size,pos);
            }
        }
        char *final = yon_char_parsed_to_string(parsed,size,divider);

        yon_char_parsed_free(parsed,size);
        yon_char_parsed_free(parsed_element,element_size);
        return final;
    }
    return yon_char_new(source);
}

char *yon_char_new(const char *chr)
{
    if (chr){
        char *newchar = malloc(strlen(chr) + 1);
        if (newchar){
            memset(newchar, 0, strlen(chr) + 1);
            memcpy(newchar, chr, strlen(chr));
        }
        return newchar;
    } else
        return NULL;
}

char *yon_char_unite(const char *source, ...){
    if (source){
        va_list arglist;
        char *new_char=NULL;
        char *unite_char=NULL;
        new_char=yon_char_new(source);
        va_start(arglist,source);
        unite_char = va_arg(arglist,char*);
        while(unite_char){
            if (unite_char[0]!='\0'){
                char *temp = yon_char_append(new_char,unite_char);
                free(new_char);
                new_char=temp;
            }
            unite_char = va_arg(arglist,char*);
        }
        va_end(arglist);
        return new_char;
    }
    return NULL;
}

char *yon_cut(char *source, int size, int startpos)
{
    if (source){
        if (strlen(source+startpos)>=size){
            char *cut = NULL;
            cut = malloc(size + 1);
            memset(cut, 0, size + 1);
            memcpy(cut, source + startpos, size);
            return cut;
        }
    }
    return NULL;
}

int yon_char_check_element(char *target, char *element, char *divider){
    if (yon_char_is_empty(target)||yon_char_is_empty(element)||yon_char_is_empty(divider)) return 0;
    int size;
    config_str parsed = yon_char_parse(target,&size,divider);
    int found = yon_char_parsed_check_exist(parsed,size,element);
    yon_char_parsed_free(parsed,size);
    return found>-1;
}

int yon_char_check_elements(char *target, char *element, char *divider){
    if (yon_char_is_empty(target)||yon_char_is_empty(element)||yon_char_is_empty(divider)) return 0;
    int size;
    int element_size;
    config_str parsed = yon_char_parse(target,&size,divider);
    config_str parsed_element = yon_char_parse(element,&element_size,divider);
    for (int i=0;i<element_size;i++){
        int found = yon_char_parsed_check_exist(parsed,size,parsed_element[i]);
        if (found<0){
            yon_char_parsed_free(parsed,size);
            yon_char_parsed_free(parsed_element,element_size);
            return 0;
        }

    }
    yon_char_parsed_free(parsed,size);
    yon_char_parsed_free(parsed_element,element_size);
    return 1;
}

char *yon_char_swap_element(const char *source, const char *a, const char *b, const char *divider){
    if (yon_char_is_empty(source)||yon_char_is_empty(a)||yon_char_is_empty(b)) return 0;
    int size;
    config_str parsed = yon_char_parse(source,&size,(char*)divider);
    int found_a = yon_char_parsed_check_exist(parsed,size,(char*)a);
    int found_b = yon_char_parsed_check_exist(parsed,size,(char*)b);
    if (found_a>-1&&found_b>-1){
        char *temp = parsed[found_a];
        parsed[found_a] = parsed[found_b];
        parsed[found_b] = temp;
        char *full = yon_char_parsed_to_string(parsed,size,(char*)divider);
        yon_char_parsed_free(parsed,size);
        return full;
    }
        yon_char_parsed_free(parsed,size);
    return NULL;
}

// char *yon_char_remove_element(char *target, char *element, char *divider){
//     if (!yon_char_check_element(target,element,divider)) return NULL;
//     int size;
//     config_str parsed = yon_char_parse(target,&size,divider);
//     int found = yon_char_parsed_check_exist(parsed,size,element);
//     yon_char_parsed_rip(parsed,&size,found);
//     char *final = yon_char_parsed_to_string(parsed,size,divider);
//     yon_char_parsed_free(parsed,size);

//     return final;
// }

int yon_char_add_element(char *target, char *element, int position, char *divider){
    if (!yon_char_check_element(target,element,divider)) return 0;
    int size;
    config_str parsed = yon_char_parse(target,&size,divider);
    if (position>size) position = size;
    yon_char_parsed_add_or_create_if_exists(parsed,&size,element);
    memcpy(parsed+position+1,parsed+position,sizeof(parsed)-sizeof(char*)*(size-position-1));
    return 1;
}

int yon_char_check_begins_with(char *haystack, char *needle){
    if (!yon_char_is_empty(haystack)&&!yon_char_is_empty(needle)&&strlen(haystack)>=strlen(needle)){
        int size = strlen(needle);
        for (int i=0;i<size;i++){
            if (haystack[i]!=needle[i])
                return 0;
        }
        return 1;
    }
    return 0;
}

char *yon_char_parsed_check_exist_begins_with(char **target, int size, char *compare){
    for (int i=0;i<size;i++){
        if (yon_char_check_begins_with(target[i],compare)){
            return yon_char_new(target[i]);
        }
    }
    return NULL;
}

config_str yon_char_wrap_to_lines(char *target, unsigned int line_count, unsigned int *final_size){
    (*final_size)=0;
    if (!yon_char_is_empty(target)&&line_count){
        unsigned int size = strlen(target);
        unsigned int line_size = ((unsigned int)size/line_count)+1;

        char *final = yon_char_wrap_to_length_str(target,line_size);
        return yon_char_parse(final,final_size,"\n");

    }
    return NULL;
}

char *yon_char_divide(char *source, int dividepos)
{
    if (source&&strlen(source)>=dividepos){
        char *cut = malloc(dividepos + 1);
        memset(cut, 0, dividepos + 1);
        memcpy(cut, source, dividepos);
        char *left = malloc(strlen(source) - strlen(cut));
        memset(left, 0, strlen(source) - strlen(cut));
        memcpy(left, source + dividepos + 1, (strlen(source) - dividepos));
        memset(source, 0, strlen(source));
        memcpy(source, left, strlen(left));
        free(left);
        return cut;
    }
    return NULL;
}

// int yon_char_find_count(char *source, char *find){
//     char *working_string=yon_char_new(source);
//     int i=0;
//     int size=0;
//     int pos=0;
//     config_str rtn = yon_char_parse(working_string,&size,find);
//     free(working_string);
//     yon_char_parsed_free(rtn,size);
//     return size-1;
// }

int yon_char_count(char *source, char *find){
    char *working_string=yon_char_new(source);
    int i=0;
    int size=0;
    char *cur=strstr(source,find);
    for (i=0;cur;cur = strstr(cur,find)){
        cur++;
        i++;
    }
    return i;
}

char *yon_char_divide_search(char *source, char *dividepos, int delete_divider)
{
    if (source&&dividepos){
        char *cut = strstr(source, dividepos);
        if (cut){
            int leng = strlen(source) - strlen(cut);
            cut = yon_char_divide(source, leng);
            return cut;
            
        }
    }
    return source;
}

char *yon_char_from_int(int int_to_convert)
{
    int i = snprintf( NULL, 0, "%d", int_to_convert)+1;
    
    char *ch = malloc(i * sizeof(char));
    memset(ch,0,i * sizeof(char));
    sprintf(ch, "%d", int_to_convert);
    return ch;
}

char *yon_char_from_float(float int_to_convert)
{
    int i = snprintf( NULL, 0, "%f", int_to_convert)+1;
    
    char *ch = malloc(i * sizeof(char));
    memset(ch,0,i * sizeof(char));
    sprintf(ch, "%.2f", int_to_convert);
    return ch;
}

char *yon_char_from_double(double int_to_convert)
{
    int i = snprintf( NULL, 0, "%f", int_to_convert)+1;
    
    char *ch = malloc(i * sizeof(char));
    memset(ch,0,i * sizeof(char));
    sprintf(ch, "%.2f", int_to_convert);
    return ch;
}

char *yon_char_from_long(long int_to_convert)
{
    int i = snprintf( NULL, 0, "%ld", int_to_convert)+1;
    
    char *ch = malloc(i * sizeof(char));
    memset(ch,0,i * sizeof(char));
    sprintf(ch, "%ld", int_to_convert);
    return ch;
}

char* yon_char_replace(char *source, char *find, char *replace){
    int size;
    config_str parsed = yon_char_parse(source,&size,find);
    char *final = yon_char_parsed_to_string_full(parsed,size,replace);
    return final;
}

char* yon_char_replace_valist(const char *source, ...){
    if (yon_char_is_empty(source)) return NULL;
    va_list arglist;
    va_start(arglist,source);
    char *cur_find = NULL;
    char *final_string = yon_char_new(source);
    while ((cur_find = va_arg(arglist,char*))){
        char *cur_replace = va_arg(arglist,char*);
        int size;
        config_str parsed = yon_char_parse(final_string,&size,cur_find);
        char *temp = yon_char_parsed_to_string_full(parsed,size,cur_replace);
        free(final_string);
        final_string = temp;
    }
    return final_string;
}

char *yon_char_replace_single(char *source, char *find, char *replace){
    int size;
    char *source_copy = yon_char_new(source);
    char *divided = strstr(source_copy,find);
    if (!yon_char_is_empty(divided)){
        int pos_start = strlen(source_copy)-strlen(divided);
        int pos_end = pos_start + strlen(find);
        int size_left = pos_start;
        int size_right = strlen(source_copy)-size_left;
        char *left = malloc(sizeof(char)*size_left+1);
        memset(left,0,sizeof(char)*size_left+1);
        memcpy(left,source_copy,size_left);

        char *right = yon_char_new(source_copy+pos_start+strlen(find));

        char *final = yon_char_unite(left,replace,right,NULL);
        free(left);
        free(right);
        free(source_copy);

        return final;
    }
    return NULL;
}

char **yon_char_parse(const char * parameters, int *size, char * divider){
    *size=0; 
    if (parameters&&!yon_char_is_empty(divider)){
        if (!strstr(parameters,divider)) return yon_char_parsed_new(size,parameters,NULL);
        char **string=NULL;
        char *paramline=yon_char_new(parameters);
        char *param = strstr(paramline,divider);
        for (;param;param=strstr(paramline,divider)){
            string = yon_remalloc(string,sizeof(char*)*((*size)+1));
            int cur_size = strlen(paramline)-strlen(param);
            string[(*size)] = malloc(cur_size+1);
            memset(string[(*size)],0,cur_size+1);
            memcpy(string[(*size)],paramline,cur_size);
            memmove(paramline,paramline+strlen(string[(*size)])+strlen(divider),strlen(param) - strlen(divider) + 1);
            // string[(*size)]=yon_char_divide(paramline,strlen(paramline)-strlen(param));
            *size=(*size)+1;
        }
            string = yon_remalloc(string,sizeof(char*)*((*size)+1));
            string[(*size)]=paramline;
            (*size)+=1;
        if(!string){
            string = yon_char_parsed_new(size,parameters,NULL);
        }
        return string;
    }
    return NULL;
}

char **yon_char_parsed_rip(char **char_string, int *size, int item_to_delete) {
    if (char_string && size && (*size) > 0 && (*size) > item_to_delete && item_to_delete >= 0) {
        if ((*size)==1){
            yon_char_parsed_free(char_string,*size);
            return NULL;
        }

        char **new_char_parsed = malloc(sizeof(char*) * ((*size) - 1));
        if (!new_char_parsed) {
            return NULL;
        }
        
        int new_index = 0;
        for (int i = 0; i < (*size); i++) {
            if (i != item_to_delete) {
                new_char_parsed[new_index] = yon_char_new(char_string[i]);
                new_index++;
            } else {
                free(char_string[i]);
            }
        }

        free(char_string);
        (*size) = (*size) - 1;
        return new_char_parsed;
    } else {
        return NULL;
    }
}


int yon_char_parsed_check_exist(char **parameters, int size, char *param){
    if (parameters&&size&&!yon_char_is_empty(param)){
        for (int i=0;i<size;i++){
            if (parameters[i]){
                if (!strcmp(parameters[i],param))
                    return i;
            } else return -1;
        }
    }

    return -1;
}

int yon_char_parsed_strstr(char **parameters, int size, char *param){
    if (parameters){
        for (int i=0;i<size;i++){
            if (parameters[i]){
                if (strstr(parameters[i],param))
                    return i;
            } else return -1;
        }
    }

    return -1;
}

int yon_char_parsed_check_repeats(char **parameters, int size, int *first_overlap, int *second_overlap){
    if (parameters){
        *first_overlap=0;
        *second_overlap=0;
        for ((*first_overlap)=0;(*first_overlap)<size;(*first_overlap)++){
            for ((*second_overlap)=0;(*second_overlap)<size;(*second_overlap)++){
                if (parameters[(*first_overlap)]&&parameters[(*second_overlap)]){
                    if (!strcmp(parameters[(*first_overlap)],parameters[(*second_overlap)])&&(*first_overlap)!=(*second_overlap))
                        return 1;
                }
            }
        }
    }
    return 0;
}

int yon_char_parsed_includes_char_parsed (config_str source, config_str to_check, int source_size, int check_size){
    int overall_found=0;
    for (int i=0;i<source_size;i++){
        int found=0;
        for (int j=0;j<check_size;j++){
            if (strcmp(source[i],to_check[j])==0&&found==0) { found=1; overall_found++; }
        }
    }
    if (overall_found==check_size)
        return 1;
    else return 0;
}

config_str yon_char_parsed_new (int *size, ...){
    va_list arglist;
    config_str new_parsed=NULL;
        new_parsed=new(char*);
    int new_size=0;
    va_start(arglist,size);
    char *newparse = va_arg(arglist,char*);
    while (newparse){
        new_size++;
        new_parsed=realloc(new_parsed,new_size*sizeof(char*));
        new_parsed[new_size-1]=yon_char_new(newparse);
        newparse=va_arg(arglist,char*);
    }
    va_end(arglist);
    *size=new_size;
    return new_parsed;
}

void yon_char_parsed_free(config_str source, int size){
    if (source&&size>0){
        for (int i=0;i<size;i++){
            if (!yon_char_is_empty(source[i])){
                free(source[i]);
            }
        }
        free(source);
    }
}

config_str yon_char_parsed_copy(config_str to_copy, int size){
    if (to_copy&&(*to_copy)&&size>0){
        int final_size=0;
        config_str final = yon_char_parsed_new(&final_size,to_copy[0],NULL);
        for (int i=1;i<size;i++){
            final = yon_char_parsed_append(final,&final_size,to_copy[i]);
        }
        return final;
    }
}

config_str yon_char_parsed_append(config_str parsed, int *size, char *string){
    config_str new_parsed=realloc(parsed,(*size+1)*sizeof(char*));
    if (new_parsed){
        new_parsed[(*size)]=yon_char_new(string);
        (*size)++;
    }
    return new_parsed;
}

config_str yon_char_parsed_prepend(config_str parsed, int *size, char *string){
    config_str new_parsed=realloc(parsed,(*size+1)*sizeof(char*));
    memcpy(&new_parsed[1],new_parsed,(*size)*sizeof(char*));
    new_parsed[0]=yon_char_new(string);
    (*size)++;
    return new_parsed;
}

void yon_char_parsed_append_strings (config_str array, int size, char *prepend){
    if (array && size>0 && !yon_char_is_empty(prepend)){
        for (int i=0;i<size;i++){
            char *newstr = yon_char_append(array[i],prepend);
            free(array[i]);
            array[i]=newstr;
        }
    }
}

void yon_char_parsed_prepend_strings (config_str array, int size, char *prepend){
    if (array && size>0 && !yon_char_is_empty(prepend)){
        for (int i=0;i<size;i++){
            char *newstr = yon_char_append(prepend,array[i]);
            free(array[i]);
            array[i]=newstr;
        }
    }
}

config_str yon_char_parsed_merge_stack(int *final_size, ...){
    (*final_size)=0;
    config_str final_array = NULL;
    va_list list;
    va_start(list,final_size);
    config_str cur_array = NULL;

    int cur_size = -1;
    while ((cur_size = va_arg(list,int))!=-1){
        cur_array = va_arg(list,config_str);
        if (!cur_array||!cur_size) continue;
        if (!final_array){
            final_array=cur_array;
            (*final_size)=cur_size;
        } else {
            int temp_size = (*final_size);
            final_array = yon_char_parsed_merge(final_array,temp_size,cur_array,cur_size,final_size);
        }
    }
    return final_array;
}

config_str yon_char_parsed_merge(config_str array1, int size1, config_str array2, int size2, int *final_size){
    if (array1&&array2&&size1>0&&size2>0){
        *final_size=0;
        config_str parsed_final = yon_char_parsed_new(final_size,array1[0],NULL);
        for (int i=1;i<size1;i++){
            parsed_final = yon_char_parsed_append(parsed_final,final_size,array1[i]);
        }
        for (int i=0;i<size2;i++){
            parsed_final = yon_char_parsed_append(parsed_final,final_size,array2[i]);
        }
        return parsed_final;
    } else {
        if (array1){
            *final_size=size1;
            return array1;
        }
        if (array2)
            *final_size=size2;
            return array2;
    }
}

int yon_char_parsed_compare(const config_str a, const config_str b){
    const config_str str_a = (const config_str)a;
    const config_str str_b = (const config_str)b;

    return strcmp(*str_a,*str_b);
}

config_str yon_char_parsed_merge_no_repeats(config_str array1, int size1, config_str array2, int size2, int *final_size){
    if (array1&&array2&&size1>0&&size2>0){
        *final_size=0;
        int new_size=0;
        config_str parsed_final = yon_char_parsed_new(final_size,array1[0],NULL);
        for (int i=1;i<size1;i++){
            parsed_final = yon_char_parsed_append(parsed_final,final_size,array1[i]);
        }
        for (int i=0;i<size2;i++){
            int found=0;
            for (int j=0;j<size1;j++){
                if (!strcmp(array1[j],array2[i])){
                    found=1;
                    break;
                }
            }
            if (!found)
                parsed_final= yon_char_parsed_append(parsed_final,final_size,array2[i]);
        }
        return parsed_final;
    }
}

int yon_char_parsed_divide_full(config_str parsed,int size,int divide_pos){
    if(parsed&&size>0){
        for (int i=0;i<size;i++){
            char *parsed_temp = yon_char_divide(parsed[i],divide_pos);
            free(parsed[i]);
            parsed[i]=parsed_temp;
        }
        return 1;
    } return 0;
}

int yon_char_parsed_divide_search_full(config_str parsed,int size,char *divide_pos, int delete_divider){
    if(parsed&&size>0){
        for (int i=0;i<size;i++){
            char *parsed_temp = yon_char_divide_search(parsed[i],divide_pos,delete_divider);
            free(parsed[i]);
            parsed[i]=parsed_temp;
        }
        return 1;
    } return 0;
}

dictionary *yon_char_parsed_convert_to_dictionary(config_str parsed, int size){
    if (parsed&&size>0){
        dictionary *dict = NULL;
        for (int i=0;i<size;i++){
            yon_dictionary_add_or_create_if_exists_with_data(dict,NULL,parsed[i]);
        }
        return dict;
    }
    return NULL;
}

dictionary *yon_char_parsed_convert_copy_to_dictionary(config_str parsed, int size){
    if (parsed&&size>0){
        dictionary *dict = NULL;
        for (int i=0;i<size;i++){
            yon_dictionary_add_or_create_if_exists_with_data(dict,NULL,yon_char_new(parsed[i]));
        }
        return dict;
    }
    return NULL;
}

char *yon_char_parsed_to_string(config_str parsed, int size, char *divider_replace){
    if (parsed && size>0){
        char *final_string = "";
        char *temp;
        for (int i=0;i<size;i++){
            if (!yon_char_is_empty(parsed[i])){
                temp = yon_char_unite(final_string,yon_char_is_empty(final_string)?"":divider_replace,parsed[i],NULL);
                if (!yon_char_is_empty(final_string)) free(final_string);
                final_string=temp;
            }
        }
        if (!yon_char_is_empty(final_string)){
            return final_string;
        } else return NULL;
    }
    return "";
}

char *yon_char_parsed_to_string_full(config_str parsed, int size, char *divider_replace){
    if (parsed && size>0){
        char *final_string = "";
        char *temp;
        temp = yon_char_unite(final_string,parsed[0],NULL);
        final_string=temp;
        for (int i=1;i<size;i++){
                temp = yon_char_unite(final_string,divider_replace,parsed[i],NULL);
                if (!yon_char_is_empty(final_string)) free(final_string);
                final_string=temp;
        }
        if (!yon_char_is_empty(final_string)){
            return final_string;
        } else return NULL;
    }
    return "";
}

char *yon_char_parsed_to_string_for_iters(config_str parsed, int size, char *divider_replace,int iterations){
    if (parsed && size>0&& iterations>0){
        char *final_string = "";
        char *temp;
        for (int i=0;i<iterations;i++){
            if (!yon_char_is_empty(parsed[i])){
                temp = yon_char_unite(final_string,yon_char_is_empty(final_string)?"":divider_replace,parsed[i],NULL);
                if (!yon_char_is_empty(final_string)) free(final_string);
                final_string=temp;
            }
        }
        if (!yon_char_is_empty(final_string)){
            return final_string;
        } else return NULL;
    } else if (size==0&&!parsed) return "";
}

config_str yon_char_parsed_cut(config_str parsed, int size, int pos){
    if (size&&pos&&parsed&&size>pos){
        config_str new_parsed = malloc(sizeof(char*)*pos);
        for (int i=0;i<size;i++){
            if (i<pos){
                new_parsed[i]=parsed[i];
            }

        }
        return new_parsed;
    }
    return NULL;
}

int yon_char_parsed_find_element(config_str parsed, int size, char *target){
    if (parsed&&size){
        for (int i=0;i<size;i++){
            if (strstr(parsed[i],target)){
                return i;
            }
        }
        return -1;
    }
    return -1;
}

int yon_char_find_last_symbol_before_length(char *string, char target, int length){
    if (yon_char_is_empty(string)||strlen(string)<length||length<1) return -1;
    int last = -1;
    for (int i=0;i<length;i++){
        if (string[i]==target){
            last = i;
        }
    }
    return last;
}

config_str yon_char_wrap_to_length(char *target, unsigned int length, int *size){
    (*size)=0;
    if (!yon_char_is_empty(target)&&strlen(target)>length&&strstr(target," ")){
        config_str final = NULL;
        char *current = yon_char_new(target);
        for (;strlen(current)>length;){
            int last = yon_char_find_last_symbol_before_length(target,' ',length);
            if (last>-1){
                char *parsed = yon_char_divide(current,last);
                yon_char_parsed_add_or_create_if_exists(final,size,parsed);
                free(parsed);
            }

        }
        return final;
    }
    config_str ret_target = yon_char_parsed_new(size,target,NULL);
    return ret_target;
}

char *yon_char_get_element(char *target, unsigned int position, char *divider){
    if (!yon_char_is_empty(target)&&strstr(target,divider)){
        int size;
        char *final = NULL;
        config_str parsed = yon_char_parse(target,&size,divider);
        if (size>=position){
            final = yon_char_new(parsed[position]);
        }
        yon_char_parsed_free(parsed,size);
        return final;
    }
    return NULL;
}

char *yon_char_wrap_to_length_str(char *target, unsigned int length){
    int size=0;
    if (!yon_char_is_empty(target)&&strlen(target)>length&&strstr(target," ")){
        config_str final = NULL;
        char *current = yon_char_new(target);
        for (;strlen(current)>length;){
            int last = yon_char_find_last_symbol_before_length(current,' ',length);
            if (last>-1){
                char *parsed = yon_char_divide(current,last);
                yon_char_parsed_add_or_create_if_exists(final,&size,parsed);
                free(parsed);
            }else {
                char *next_space = strstr(current," ");
                if (next_space) {
                    last = strlen(current)-strlen(next_space);
                    char *parsed = yon_char_divide(current,last);
                    yon_char_parsed_add_or_create_if_exists(final,&size,parsed);
                    free(parsed);
                } else {
                    break;
                }
            }

        }
                yon_char_parsed_add_or_create_if_exists(final,&size,current);
        char *final_string = yon_char_parsed_to_string(final,size,"\n");
        yon_char_parsed_free(final,size);
        return final_string;
    }
    return yon_char_new(target);
}

int yon_ubl_check_root(){
    if (getuid()==0) return 1;
    else return 0;
}

char *yon_ubl_root_user_get(){
    char *user=NULL;
    if (yon_ubl_check_root()){
        user=getenv("SUDO_USER");
        if (user&&strcmp(user,"")!=0){
            return user;
        }else {
            FILE *file = popen("getent passwd $PKEXEC_UID | cut -d: -f1","r");
            user=malloc(4096);
            memset(user,0,4096);
            if (fgets(user,4096,file)){};
            user=yon_char_divide_search(user,"\n",-1);
            fclose(file);
            if (user) return user;
        }
    }
    return getlogin();
}

char *yon_ubl_user_get_home_directory(){
    FILE *path = popen(get_home_dir_command,"r");
    char *ret = malloc(4096);
    memset(ret,0,4096);
    if (fgets(ret,4096,path)){};
    ret=yon_char_divide_search(ret,"\n",-1);
    fclose(path);
    return ret;
}

config_str yon_ubl_get_all_users(int *user_size){
    struct passwd *user = NULL;
    config_str user_list = NULL;
    while ((user = getpwent())) {
        if (!user_list)
            user_list = yon_char_parsed_new(user_size,user->pw_name,NULL);
        else {
            user_list = yon_char_parsed_append(user_list,user_size,user->pw_name);
        }
    }
    endpwent();
    return user_list;
}