eolian: preliminary doc dependency detection for external files

This doesn't quite work yet as path sanitization needs to be done for it to
work correctly. For now this code path is disabled and will be enabled once
all paths are correctly sanitized.
This commit is contained in:
Daniel Kolesa 2015-09-23 17:17:50 +01:00
parent 411089d5e3
commit c0d82ba900
4 changed files with 91 additions and 0 deletions

View File

@ -217,6 +217,7 @@ eo_parser_database_fill(const char *filename, Eina_Bool eot)
Eina_Iterator *itr;
Eolian_Class *cl;
Eo_Lexer *ls;
const char *dep;
if (eina_hash_find(_parsedeos, filename))
return EINA_TRUE;
@ -257,6 +258,7 @@ eo_parser_database_fill(const char *filename, Eina_Bool eot)
{
fprintf(stderr, "eolian: unable to find function '%s'\n",
eolian_implement_full_name_get(impl));
eina_iterator_free(itr);
goto error;
}
else if (eolian_function_is_constructor(impl->foo_id, impl->klass))
@ -271,6 +273,7 @@ eo_parser_database_fill(const char *filename, Eina_Bool eot)
{
fprintf(stderr, "eolian: unable to find function '%s'\n",
eolian_constructor_full_name_get(ctor));
eina_iterator_free(itr);
goto error;
}
else
@ -278,6 +281,20 @@ eo_parser_database_fill(const char *filename, Eina_Bool eot)
}
eina_iterator_free(itr);
/* parse deferred eos (doc dependencies) */
itr = eina_hash_iterator_data_new(_defereos);
EINA_ITERATOR_FOREACH(itr, dep)
{
if (!eina_hash_find(_parsingeos, dep) && !eolian_file_parse(dep))
{
eina_iterator_free(itr);
eina_hash_free_buckets(_defereos);
goto error;
}
}
eina_iterator_free(itr);
eina_hash_free_buckets(_defereos);
done:
eina_hash_set(_parsedeos, filename, (void *)EINA_TRUE);
eina_hash_set(_parsingeos, filename, (void *)EINA_FALSE);

View File

@ -253,6 +253,72 @@ enum Doc_Tokens {
DOC_MANGLED = -2, DOC_UNFINISHED = -1, DOC_TEXT = 0, DOC_SINCE = 1
};
static void
doc_ref_class(const char *cname)
{
size_t clen = strlen(cname);
char *buf = alloca(clen + 4);
memcpy(buf, cname, clen);
buf[clen] = '\0';
for (char *p = buf; *p; ++p)
{
if (*p == '.')
*p = '_';
else
*p = tolower(*p);
}
memcpy(buf + clen, ".eo", sizeof(".eo"));
const char *eop = eina_hash_find(_filenames, buf);
if (!eop)
return;
eina_hash_set(_defereos, buf, eop);
}
static void
doc_ref(Eo_Lexer *ls)
{
#if 0
const char *st = ls->stream, *ste = ls->stream_end;
size_t rlen = 0;
while ((st != ste) && ((*st == '.') || isalnum(*st)))
{
++st;
++rlen;
}
if ((rlen > 1) && (*(st - 1) == '.'))
--rlen;
if (!rlen)
return;
if (*ls->stream == '.')
return;
char *buf = alloca(rlen + 1);
memcpy(buf, ls->stream, rlen);
buf[rlen] = '\0';
/* actual full class name */
doc_ref_class(buf);
/* method name at the end */
char *end = strrchr(buf, '.');
if (!end)
return;
*end = '\0';
doc_ref_class(buf);
/* .get or .set at the end, handle possible property */
if (strcmp(end + 1, "get") && strcmp(end + 1, "set"))
return;
end = strrchr(buf, '.');
if (!end)
return;
*end = '\0';
doc_ref_class(buf);
#else
(void)ls;
#endif
}
static int
doc_lex(Eo_Lexer *ls, Eina_Bool *term, Eina_Bool *since)
{
@ -324,6 +390,7 @@ doc_lex(Eo_Lexer *ls, Eina_Bool *term, Eina_Bool *since)
tokret = DOC_TEXT;
goto exit_with_token;
}
doc_ref(ls);
eina_strbuf_append_char(ls->buff, '@');
next_char(ls);
/* in-class references */

View File

@ -27,6 +27,8 @@ Eina_Hash *_declsf = NULL;
Eina_Hash *_parsedeos = NULL;
Eina_Hash *_parsingeos = NULL;
Eina_Hash *_defereos = NULL;
static int _database_init_count = 0;
static void
@ -58,6 +60,7 @@ database_init()
_declsf = eina_hash_stringshared_new(_hashlist_free);
_parsedeos = eina_hash_string_small_new(NULL);
_parsingeos = eina_hash_string_small_new(NULL);
_defereos = eina_hash_string_small_new(NULL);
return ++_database_init_count;
}
@ -91,6 +94,7 @@ database_shutdown()
eina_hash_free(_declsf ); _declsf = NULL;
eina_hash_free(_parsedeos ); _parsedeos = NULL;
eina_hash_free(_parsingeos); _parsingeos = NULL;
eina_hash_free(_defereos ); _defereos = NULL;
eina_shutdown();
}
return _database_init_count;

View File

@ -53,6 +53,9 @@ extern Eina_Hash *_decls;
extern Eina_Hash *_parsedeos;
extern Eina_Hash *_parsingeos;
/* for deferred dependency parsing */
extern Eina_Hash *_defereos;
typedef struct _Eolian_Object
{
const char *file;