<commit_before>#include <string.h>

#include "lily_impl.h"
#include "lily_symtab.h"

static char *classnames[] =
{
    "function",
    "str",
    "integer",
    "number",
};

struct lily_keyword {
    char *name;
    int class_id;
    int num_args;
} keywords[] =
{
    {"print", SYM_CLASS_FUNCTION, 1},
    /* All code outside of functions is stuffed here, and at the end of parsing,
       this function is called. */
    {"@main", SYM_CLASS_FUNCTION, 0}
};

static void add_symbol(lily_symtab *symtab, lily_symbol *s)
{
    s->id = symtab->next_sym_id;
    symtab->next_sym_id++;

    s->next = NULL;
    /* The symtab is the oldest, for iteration. The symtab_top is the newest,
       for adding new elements. */
    if (symtab->sym_start == NULL)
        /* If no symtab, this is both the oldest and newest. */
        symtab->sym_start = s;
    else
        symtab->sym_top->next = s;

    symtab->sym_top = s;
}

lily_class *lily_class_by_id(lily_symtab *symtab, int class_id)
{
    return symtab->classes[class_id];
}

lily_class *lily_class_by_name(lily_symtab *symtab, char *name)
{
    int i;
    lily_class **classes = symtab->classes;

    for (i = 0;i <= SYM_CLASS_NUMBER;i++) {
        if (strcmp(classes[i]->name, name) == 0)
            return classes[i];
    }

    return NULL;
}

void lily_free_symtab(lily_symtab *symtab)
{
    lily_symbol *sym = symtab->sym_start;
    lily_symbol *temp;

    while (sym != NULL) {
        temp = sym->next;

        if (isafunc(sym) && sym->code_data != NULL) {
            lily_free(((lily_code_data *)sym->code_data)->code);
            lily_free(sym->code_data);
        }

        lily_free(sym->name);
        lily_free(sym);

        sym = temp;
    }

    if (symtab->classes != NULL) {
        int i;
        for (i = 0;i <= SYM_CLASS_NUMBER;i++)
            lily_free(symtab->classes[i]);

        lily_free(symtab->classes);
    }

    lily_free(symtab);
}

static int init_classes(lily_symtab *symtab)
{
    int i, class_id, class_count, ret;

    lily_class **classes = lily_malloc(sizeof(lily_class) * 4);
    if (classes == NULL)
        return 0;

    class_id = 0;
    class_count = sizeof(classnames) / sizeof(classnames[0]);

    for (i = 0;i < class_count;i++) {
        lily_class *new_class = lily_malloc(sizeof(lily_class));

        if (new_class == NULL)
            break;

        new_class->name = classnames[i];
        new_class->id = class_id;
        class_id++;

        classes[i] = new_class;
    }

    if (i != class_count) {
        for (;i > 0;i--)
            lily_free(classes[i]);

        lily_free(classes);
        ret = 0;
    }
    else {
        symtab->classes = classes;
        ret = 1;
    }
    return ret;
}

static int init_symbols(lily_symtab *symtab)
{
    /* Turn the keywords into symbols. */
    int i, keyword_count, ret;
    lily_class *func_class = lily_class_by_id(symtab, SYM_CLASS_FUNCTION);

    if (symtab->classes == NULL)
        return 0;

    keyword_count = sizeof(keywords) / sizeof(keywords[0]);
    ret = 1;

    for (i = 0;i < keyword_count;i++) {
        lily_symbol *new_sym = lily_malloc(sizeof(lily_symbol));

        if (new_sym == NULL) {
            ret = 0;
            break;
        }

        new_sym->name = lily_malloc(strlen(keywords[i].name) + 1);
        if (new_sym->name == NULL) {
            ret = 0;
            lily_free(new_sym);
            break;
        }

        strcpy(new_sym->name, keywords[i].name);
        new_sym->code_data = NULL;
        new_sym->num_args = keywords[i].num_args;
        new_sym->object = NULL;
        new_sym->sym_class = func_class;
        new_sym->line_num = 0;
        add_symbol(symtab, new_sym);
    }
<commit_msg>Symbols made from keywords don't strcpy the name anymore.<commit_after>#include <string.h>

#include "lily_impl.h"
#include "lily_symtab.h"

static char *classnames[] =
{
    "function",
    "str",
    "integer",
    "number",
};

struct lily_keyword {
    char *name;
    int class_id;
    int num_args;
} keywords[] =
{
    {"print", SYM_CLASS_FUNCTION, 1},
    /* All code outside of functions is stuffed here, and at the end of parsing,
       this function is called. */
    {"@main", SYM_CLASS_FUNCTION, 0}
};
/* It's important to know this id, because symbols after it have their name
   malloc'd, so it'll need to be free'd. */
#define MAIN_FUNC_ID 1

static void add_symbol(lily_symtab *symtab, lily_symbol *s)
{
    s->id = symtab->next_sym_id;
    symtab->next_sym_id++;

    s->next = NULL;
    /* The symtab is the oldest, for iteration. The symtab_top is the newest,
       for adding new elements. */
    if (symtab->sym_start == NULL)
        /* If no symtab, this is both the oldest and newest. */
        symtab->sym_start = s;
    else
        symtab->sym_top->next = s;

    symtab->sym_top = s;
}

lily_class *lily_class_by_id(lily_symtab *symtab, int class_id)
{
    return symtab->classes[class_id];
}

lily_class *lily_class_by_name(lily_symtab *symtab, char *name)
{
    int i;
    lily_class **classes = symtab->classes;

    for (i = 0;i <= SYM_CLASS_NUMBER;i++) {
        if (strcmp(classes[i]->name, name) == 0)
            return classes[i];
    }

    return NULL;
}

void lily_free_symtab(lily_symtab *symtab)
{
    lily_symbol *sym = symtab->sym_start;
    lily_symbol *temp;

    while (sym != NULL) {
        temp = sym->next;

        if (isafunc(sym) && sym->code_data != NULL) {
            lily_free(((lily_code_data *)sym->code_data)->code);
            lily_free(sym->code_data);
        }
        if (sym->id > MAIN_FUNC_ID)
            lily_free(sym->name);

        lily_free(sym);

        sym = temp;
    }

    if (symtab->classes != NULL) {
        int i;
        for (i = 0;i <= SYM_CLASS_NUMBER;i++)
            lily_free(symtab->classes[i]);

        lily_free(symtab->classes);
    }

    lily_free(symtab);
}

static int init_classes(lily_symtab *symtab)
{
    int i, class_id, class_count, ret;

    lily_class **classes = lily_malloc(sizeof(lily_class) * 4);
    if (classes == NULL)
        return 0;

    class_id = 0;
    class_count = sizeof(classnames) / sizeof(classnames[0]);

    for (i = 0;i < class_count;i++) {
        lily_class *new_class = lily_malloc(sizeof(lily_class));

        if (new_class == NULL)
            break;

        new_class->name = classnames[i];
        new_class->id = class_id;
        class_id++;

        classes[i] = new_class;
    }

    if (i != class_count) {
        for (;i > 0;i--)
            lily_free(classes[i]);

        lily_free(classes);
        ret = 0;
    }
    else {
        symtab->classes = classes;
        ret = 1;
    }
    return ret;
}

static int init_symbols(lily_symtab *symtab)
{
    /* Turn the keywords into symbols. */
    int i, keyword_count, ret;
    lily_class *func_class = lily_class_by_id(symtab, SYM_CLASS_FUNCTION);

    if (symtab->classes == NULL)
        return 0;

    keyword_count = sizeof(keywords) / sizeof(keywords[0]);
    ret = 1;

    for (i = 0;i < keyword_count;i++) {
        lily_symbol *new_sym = lily_malloc(sizeof(lily_symbol));

        if (new_sym == NULL) {
            ret = 0;
            break;
        }

        new_sym->name = keywords[i].name;
        new_sym->code_data = NULL;
        new_sym->num_args = keywords[i].num_args;
        new_sym->object = NULL;
        new_sym->sym_class = func_class;
        new_sym->line_num = 0;
        add_symbol(symtab, new_sym);
    }

{'fraction_non_alphanumeric': 0.13276949926164586, 'fraction_numerical': 0.005504094509330111, 'mean_word_length': 2.321444493981275, 'pattern_counts': {'":': 0, '<': 13, '<?xml version=': 0, '>': 75, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '565017', 'n_tokens_mistral': 2732, 'n_tokens_neox': 2651, 'n_words': 584}