ofc_parse_file_t* ofc_parse_file(ofc_sparse_t* src) { ofc_parse_debug_t* debug = ofc_parse_debug_create(); if (!debug) return NULL; ofc_parse_stmt_list_t* list = ofc_parse_stmt_list_create(); if (!list) return NULL; if (!ofc_parse_file_include( src, list, debug)) { ofc_parse_debug_print(debug); ofc_parse_debug_delete(debug); ofc_parse_stmt_list_delete(list); return NULL; } ofc_parse_debug_print(debug); ofc_parse_debug_delete(debug); if (!list) return NULL; ofc_parse_file_t* file = (ofc_parse_file_t*)malloc( sizeof(ofc_parse_file_t)); if (!file) { ofc_parse_stmt_list_delete(list); return NULL; } file->source = src; file->stmt = list; return file; }
unsigned ofc_parse_stmt_include( const ofc_sparse_t* src, const char* ptr, ofc_parse_debug_t* debug, ofc_parse_stmt_t* stmt, ofc_parse_stmt_list_t* list) { unsigned dpos = ofc_parse_debug_position(debug); unsigned i = ofc_parse_keyword( src, ptr, debug, OFC_PARSE_KEYWORD_INCLUDE); if (i == 0) return 0; unsigned l = 0; ofc_string_t* spath = ofc_parse_character( src, &ptr[i], debug, &l); if (!spath) { ofc_parse_debug_rewind(debug, dpos); return 0; } i += l; if (!ofc_is_end_statement(&ptr[i], NULL)) { ofc_parse_debug_rewind(debug, dpos); return 0; } /* Don't rewind debug after this point because we know we have a valid include statement. */ char path[spath->size + 1]; memcpy(path, spath->base, spath->size); path[spath->size] = '\0'; const char* include_path = ofc_sparse_get_include(src); char* rpath = ofc_sparse_include_path(src, path); stmt->include.file = ofc_file_create_include( rpath, ofc_sparse_lang_opts(src), include_path); if (!stmt->include.file) { ofc_sparse_error(src, ofc_str_ref(ptr, i), "Can't open include file '%s'", rpath); free(rpath); return 0; } free(rpath); stmt->include.src = ofc_prep(stmt->include.file); if (!ofc_parse_file_include( stmt->include.src, list, debug)) { ofc_sparse_delete(stmt->include.src); ofc_file_delete(stmt->include.file); return 0; } stmt->type = OFC_PARSE_STMT_INCLUDE; return i; }