Ejemplo n.º 1
0
CFCParcel*
CFCParcel_new_from_file(const char *path) {
    size_t len;
    char *json = CFCUtil_slurp_text(path, &len);
    CFCParcel *self = S_new_from_json(json, path);
    FREEMEM(json);
    return self;
}
Ejemplo n.º 2
0
CFCParcel*
CFCParcel_new_from_file(CFCFileSpec *file_spec) {
    const char *path = CFCFileSpec_get_path(file_spec);
    size_t len;
    char *json = CFCUtil_slurp_text(path, &len);
    CFCParcel *self = S_new_from_json(json, file_spec);
    FREEMEM(json);
    return self;
}
Ejemplo n.º 3
0
static void
S_parse_cf_files(CFCHierarchy *self, const char *source_dir, int is_included) {
    CFCFindFilesContext context;
    context.ext       = ".cfh";
    context.paths     = (char**)CALLOCATE(1, sizeof(char*));
    context.num_paths = 0;
    CFCUtil_walk(source_dir, S_find_files, &context);

    // Process any file that has at least one class declaration.
    for (int i = 0; context.paths[i] != NULL; i++) {
        // Derive the name of the class that owns the module file.
        char *source_path = context.paths[i];
        char *path_part = S_extract_path_part(source_path, source_dir, ".cfh");

        // Ignore hidden files.
        if (path_part[0] == '.'
            || strstr(path_part, CHY_DIR_SEP ".") != NULL) {
            continue;
        }

        CFCFileSpec *file_spec = CFCFileSpec_new(source_dir, path_part, ".cfh",
                                                 is_included);

        // Slurp and parse file.
        size_t unused;
        char *content = CFCUtil_slurp_text(source_path, &unused);
        CFCFile *file = CFCParser_parse_file(self->parser, content, file_spec);
        FREEMEM(content);
        if (!file) {
            int lineno = CFCParser_get_lineno(self->parser);
            CFCUtil_die("%s:%d: parser error", source_path, lineno);
        }

        // Make sure path_part is unique because the name of the generated
        // C header is derived from it.
        CFCFile *existing = S_fetch_file(self, path_part);
        if (existing) {
            CFCUtil_die("File %s.cfh found twice in %s and %s",
                        path_part, CFCFile_get_source_dir(existing),
                        source_dir);
        }

        S_add_file(self, file);

        CFCBase_decref((CFCBase*)file);
        CFCBase_decref((CFCBase*)file_spec);
        FREEMEM(path_part);
    }

    CFCUtil_free_string_array(context.paths);
}
Ejemplo n.º 4
0
void
CFCParcel_read_host_data_json(CFCParcel *self, const char *host_lang) {
    const char *source_dir = CFCParcel_get_source_dir(self);
    char *path = CFCUtil_sprintf("%s" CHY_DIR_SEP "parcel_%s.json", source_dir,
                                 host_lang);

    size_t len;
    char *json = CFCUtil_slurp_text(path, &len);
    CFCJson *extra_data = CFCJson_parse(json);
    if (!extra_data) {
        CFCUtil_die("Invalid JSON in file '%s'", path);
    }

    CFCJson *host_module_json
        = CFCJson_find_hash_elem(extra_data, "host_module");
    if (host_module_json) {
        const char *name = CFCJson_get_string(host_module_json);
        CFCParcel_set_host_module_name(self, name);
    }

    CFCJson *class_hash = CFCJson_find_hash_elem(extra_data, "classes");
    if (class_hash) {
        CFCJson **children = CFCJson_get_children(class_hash);
        for (int i = 0; children[i]; i += 2) {
            const char *class_name = CFCJson_get_string(children[i]);
            CFCClass *klass = CFCParcel_class(self, class_name);
            if (!klass) {
                CFCUtil_die("Class '%s' in '%s' not found", class_name, path);
            }
            CFCClass_read_host_data_json(klass, children[i+1], path);
        }
    }

    CFCJson_destroy(extra_data);
    FREEMEM(json);
    FREEMEM(path);
}
Ejemplo n.º 5
0
int
main(int argc, char **argv) {
    int           i;
    size_t        file_len;
    CFCArgs       args;
    CFCHierarchy *hierarchy;
    CFCBindCore  *core_binding;
    CFCC         *c_binding;
    char         *header = NULL;
    char         *footer = NULL;
    const char   *include_env;

    S_parse_arguments(argc, argv, &args);

    hierarchy = CFCHierarchy_new(args.dest);

    for (i = 0; args.source_dirs[i]; ++i) {
        CFCHierarchy_add_source_dir(hierarchy, args.source_dirs[i]);
    }
    for (i = 0; args.include_dirs[i]; ++i) {
        CFCHierarchy_add_include_dir(hierarchy, args.include_dirs[i]);
    }

    /* Add include dirs from environment variable CLOWNFISH_INCLUDE. */
    include_env = getenv("CLOWNFISH_INCLUDE");
    if (include_env != NULL) {
        char *include_env_copy = CFCUtil_strdup(include_env);
        const char *include_dir;

        for (include_dir = strtok(include_env_copy, ":");
             include_dir != NULL;
             include_dir = strtok(NULL, ":")
        ) {
            if (include_dir[0] != '\0') {
                CFCHierarchy_add_include_dir(hierarchy, include_dir);
            }
        }

        FREEMEM(include_env_copy);
    }
    else if (UNIX_FILESYSTEM) {
        /*
         * Only add system include dirs if CLOWNFISH_INCLUDE is unset to
         * avoid errors when a parcel is found in multiple locations.
         */
        CFCHierarchy_add_include_dir(hierarchy, "/usr/local/" SYS_INCLUDE_DIR);
        CFCHierarchy_add_include_dir(hierarchy, "/usr/" SYS_INCLUDE_DIR);
    }

    for (i = 0; args.parcels[i]; ++i) {
        CFCHierarchy_add_prereq(hierarchy, args.parcels[i]);
    }

    CFCHierarchy_build(hierarchy);

    if (args.header_filename) {
        header = CFCUtil_slurp_text(args.header_filename, &file_len);
    }
    else {
        header = CFCUtil_strdup("");
    }
    if (args.footer_filename) {
        footer = CFCUtil_slurp_text(args.footer_filename, &file_len);
    }
    else {
        footer = CFCUtil_strdup("");
    }

    core_binding = CFCBindCore_new(hierarchy, header, footer);
    CFCBindCore_write_all_modified(core_binding, 0);

    c_binding = CFCC_new(hierarchy, header, footer);
    CFCC_write_hostdefs(c_binding);
    if (args.num_source_dirs != 0) {
        CFCC_write_html_docs(c_binding);
        CFCC_write_man_pages(c_binding);
    }

    CFCHierarchy_write_log(hierarchy);

    CFCBase_decref((CFCBase*)c_binding);
    CFCBase_decref((CFCBase*)core_binding);
    CFCBase_decref((CFCBase*)hierarchy);
    FREEMEM(header);
    FREEMEM(footer);

    CFCClass_clear_registry();
    CFCParcel_reap_singletons();

    S_free_arguments(&args);

    return EXIT_SUCCESS;
}
Ejemplo n.º 6
0
char*
CFCDocument_get_contents(CFCDocument *self) {
    size_t len;
    return CFCUtil_slurp_text(self->path, &len);
}