Ejemplo n.º 1
0
static void
_generate_ref(const char *refn, Eina_Strbuf *wbuf, Eina_Bool use_legacy)
{
   const Eolian_Declaration *decl = eolian_declaration_get_by_name(refn);
   if (decl)
     {
        char *n = strdup(eolian_declaration_name_get(decl));
        char *p = n;
        while ((p = strchr(p, '.'))) *p = '_';
        eina_strbuf_append(wbuf, n);
        free(n);
        return;
     }

   /* not a plain declaration, so it must be struct/enum field or func */
   const char *sfx = strrchr(refn, '.');
   if (!sfx) goto noref;

   Eina_Stringshare *bname = eina_stringshare_add_length(refn, sfx - refn);

   const Eolian_Type *tp = eolian_type_struct_get_by_name(bname);
   if (tp)
     {
        if (!eolian_type_struct_field_get(tp, sfx + 1))
          {
             eina_stringshare_del(bname);
             goto noref;
          }
        _generate_ref(bname, wbuf, use_legacy);
        eina_strbuf_append(wbuf, sfx);
        eina_stringshare_del(bname);
        return;
     }

   tp = eolian_type_enum_get_by_name(bname);
   if (tp)
     {
        const Eolian_Enum_Type_Field *efl = eolian_type_enum_field_get(tp, sfx + 1);
        if (!efl)
          {
             eina_stringshare_del(bname);
             goto noref;
          }
        _generate_ref(bname, wbuf, use_legacy);
        Eina_Stringshare *str = eolian_type_enum_field_c_name_get(efl);
        eina_strbuf_append_char(wbuf, '.');
        eina_strbuf_append(wbuf, str);
        eina_stringshare_del(str);
        eina_stringshare_del(bname);
        return;
     }

   const Eolian_Class *cl = eolian_class_get_by_name(bname);
   const Eolian_Function *fn = NULL;
   Eolian_Function_Type ftype = EOLIAN_UNRESOLVED;
   if (!cl)
     {
        const char *mname;
        if (!strcmp(sfx, ".get")) ftype = EOLIAN_PROP_GET;
        else if (!strcmp(sfx, ".set")) ftype = EOLIAN_PROP_SET;
        if (ftype != EOLIAN_UNRESOLVED)
          {
             eina_stringshare_del(bname);
             mname = sfx - 1;
             while ((mname != refn) && (*mname != '.')) --mname;
             if (mname == refn) goto noref;
             bname = eina_stringshare_add_length(refn, mname - refn);
             cl = eolian_class_get_by_name(bname);
             eina_stringshare_del(bname);
          }
        if (cl)
          {
             char *meth = strndup(mname + 1, sfx - mname - 1);
             fn = eolian_class_function_get_by_name(cl, meth, ftype);
             if (ftype == EOLIAN_UNRESOLVED)
               ftype = eolian_function_type_get(fn);
             free(meth);
          }
     }
   else
     {
        fn = eolian_class_function_get_by_name(cl, sfx + 1, ftype);
        ftype = eolian_function_type_get(fn);
     }

   if (!fn) goto noref;

   Eina_Stringshare *fcn = eolian_function_full_c_name_get(fn, ftype, use_legacy);
   if (!fcn) goto noref;
   eina_strbuf_append(wbuf, fcn);
   eina_stringshare_del(fcn);
   return;
noref:
   eina_strbuf_append(wbuf, refn);
}
Ejemplo n.º 2
0
static void
_gen_func(const Eolian_Unit *src, const Eolian_Class *cl,
          const Eolian_Function *fid, Eolian_Function_Type ftype,
          Eina_Strbuf *buf, const Eolian_Implement *impl, Eina_Strbuf *lbuf)
{
   Eina_Bool is_empty = eolian_implement_is_empty(impl, ftype);
   Eina_Bool is_auto = eolian_implement_is_auto(impl, ftype);

   if ((ftype != EOLIAN_PROP_GET) && (ftype != EOLIAN_PROP_SET))
     ftype = eolian_function_type_get(fid);

   Eina_Bool is_prop = (ftype == EOLIAN_PROP_GET || ftype == EOLIAN_PROP_SET);
   Eina_Bool var_as_ret = EINA_FALSE;

   const Eolian_Expression *def_ret = NULL;
   const Eolian_Type *rtp = eolian_function_return_type_get(fid, ftype);
   if (rtp)
     {
        is_auto = EINA_FALSE; /* can't do auto if func returns */
        def_ret = eolian_function_return_default_value_get(fid, ftype);
     }

   const char *func_suffix = "";
   if (ftype == EOLIAN_PROP_GET)
     {
        func_suffix = "_get";
        if (!rtp)
          {
             void *d1, *d2;
             Eina_Iterator *itr = eolian_property_values_get(fid, ftype);
             if (eina_iterator_next(itr, &d1) && !eina_iterator_next(itr, &d2))
               {
                  Eolian_Function_Parameter *pr = d1;
                  rtp = eolian_parameter_type_get(pr);
                  var_as_ret = EINA_TRUE;
                  def_ret = eolian_parameter_default_value_get(pr);
               }
             eina_iterator_free(itr);
          }
     }
   else if (ftype == EOLIAN_PROP_SET)
     func_suffix = "_set";

   Eina_Strbuf *params = eina_strbuf_new(); /* par1, par2, par3, ... */
   Eina_Strbuf *params_full = eina_strbuf_new(); /* T par1, U par2, ... for decl */
   Eina_Strbuf *params_full_imp = eina_strbuf_new(); /* as above, for impl */
   Eina_Strbuf *params_init = eina_strbuf_new(); /* default value inits */

   Eina_Stringshare *promise_param_name = NULL;
   Eina_Stringshare *promise_param_type = NULL;

   /* property keys */
   {
      Eina_Iterator *itr = eolian_property_keys_get(fid, ftype);
      Eolian_Function_Parameter *pr;
      EINA_ITERATOR_FOREACH(itr, pr)
        {
           const char *prn = eolian_parameter_name_get(pr);
           const Eolian_Type *pt = eolian_parameter_type_get(pr);
           Eina_Stringshare *ptn = eolian_type_c_type_get(pt);

           if (eina_strbuf_length_get(params))
             eina_strbuf_append(params, ", ");
           eina_strbuf_append(params, prn);

           eina_strbuf_append_printf(params_full, ", %s", ptn);
           eina_strbuf_append_printf(params_full_imp, ", %s", ptn);
           if (ptn[strlen(ptn) - 1] != '*')
             {
                eina_strbuf_append_char(params_full, ' ');
                eina_strbuf_append_char(params_full_imp, ' ');
             }
           eina_strbuf_append(params_full, prn);
           eina_strbuf_append(params_full_imp, prn);
           if (is_empty || is_auto)
             eina_strbuf_append(params_full_imp, " EINA_UNUSED");

           eina_stringshare_del(ptn);
        }
      eina_iterator_free(itr);
   }

   /* property values or method params if applicable */
   if (!var_as_ret)
     {
        Eina_Iterator *itr;
        if (is_prop)
          itr = eolian_property_values_get(fid, ftype);
        else
          itr = eolian_function_parameters_get(fid);
        Eolian_Function_Parameter *pr;
        EINA_ITERATOR_FOREACH(itr, pr)
          {
             Eolian_Parameter_Dir pd = eolian_parameter_direction_get(pr);
             const Eolian_Expression *dfv = eolian_parameter_default_value_get(pr);
             const char *prn = eolian_parameter_name_get(pr);
             const Eolian_Type *pt = eolian_parameter_type_get(pr);
             Eina_Stringshare *ptn = eolian_type_c_type_get(pt);

             Eina_Bool had_star = ptn[strlen(ptn) - 1] == '*';
             const char *add_star = _get_add_star(ftype, pd);

             if (eina_strbuf_length_get(params))
               eina_strbuf_append(params, ", ");

             eina_strbuf_append(params_full_imp, ", ");
             eina_strbuf_append(params_full_imp, ptn);
             if (!had_star)
               eina_strbuf_append_char(params_full_imp, ' ');
             eina_strbuf_append(params_full_imp, add_star);
             eina_strbuf_append(params_full_imp, prn);
             if (!dfv && is_empty)
               eina_strbuf_append(params_full_imp, " EINA_UNUSED");
             eina_strbuf_append(params, prn);

             eina_strbuf_append(params_full, ", ");
             eina_strbuf_append(params_full, ptn);
             if (!had_star)
               eina_strbuf_append_char(params_full, ' ');
             eina_strbuf_append(params_full, add_star);
             eina_strbuf_append(params_full, prn);

             if (is_auto)
               {
                  if (ftype == EOLIAN_PROP_SET)
                    eina_strbuf_append_printf(params_init, "   %s = pd->%s;\n", prn, prn);
                  else
                    {
                       eina_strbuf_append_printf(params_init, "   if (%s) *%s = pd->%s;\n",
                                                 prn, prn, prn);
                    }
               }
             else if ((ftype != EOLIAN_PROP_SET) && dfv)
               {
                  Eolian_Value val = eolian_expression_eval(src, dfv, EOLIAN_MASK_ALL);
                  if (val.type)
                    {
                       Eina_Stringshare *vals = eolian_expression_value_to_literal(&val);
                       eina_strbuf_append_printf(params_init, "   if (%s) *%s = %s;",
                                                 prn, prn, vals);
                       eina_stringshare_del(vals);
                       if (eolian_expression_type_get(dfv) == EOLIAN_EXPR_NAME)
                         {
                            Eina_Stringshare *vs = eolian_expression_serialize(dfv);
                            eina_strbuf_append_printf(params_init, " /* %s */", vs);
                            eina_stringshare_del(vs);
                         }
                       eina_strbuf_append_char(params_init, '\n');
                    }
               }

             eina_stringshare_del(ptn);
          }
Ejemplo n.º 3
0
Archivo: docs.c Proyecto: tasn/efl
static void
_generate_ref(const Eolian_State *state, const char *refn, Eina_Strbuf *wbuf)
{
   const Eolian_Object *decl = eolian_state_object_by_name_get(state, refn);
   if (decl)
     {
        char *n = strdup(eolian_object_name_get(decl));
        char *p = n;
        while ((p = strchr(p, '.'))) *p = '_';
        if (eolian_object_type_get(decl) == EOLIAN_OBJECT_VARIABLE)
          {
             const Eolian_Variable *v = (const Eolian_Variable *)decl;
             /* constants are emitted as macros */
             if (eolian_variable_type_get(v) == EOLIAN_VAR_CONSTANT)
               eina_str_toupper(&n);
          }
        eina_strbuf_append(wbuf, n);
        free(n);
        return;
     }

   /* not a plain declaration, so it must be struct/enum field or func */
   const char *sfx = strrchr(refn, '.');
   if (!sfx) goto noref;

   Eina_Stringshare *bname = eina_stringshare_add_length(refn, sfx - refn);

   const Eolian_Typedecl *tp = eolian_state_struct_by_name_get(state, bname);
   if (tp)
     {
        if (!eolian_typedecl_struct_field_get(tp, sfx + 1))
          {
             eina_stringshare_del(bname);
             goto noref;
          }
        _generate_ref(state, bname, wbuf);
        eina_strbuf_append(wbuf, sfx);
        eina_stringshare_del(bname);
        return;
     }

   tp = eolian_state_enum_by_name_get(state, bname);
   if (tp)
     {
        const Eolian_Enum_Type_Field *efl = eolian_typedecl_enum_field_get(tp, sfx + 1);
        if (!efl)
          {
             eina_stringshare_del(bname);
             goto noref;
          }
        Eina_Stringshare *str = eolian_typedecl_enum_field_c_name_get(efl);
        eina_strbuf_append(wbuf, str);
        eina_stringshare_del(bname);
        return;
     }

   const Eolian_Class *cl = eolian_state_class_by_name_get(state, bname);
   const Eolian_Function *fn = NULL;
   /* match methods and properties; we're only figuring out existence */
   Eolian_Function_Type ftype = EOLIAN_UNRESOLVED;
   if (!cl)
     {
        const char *mname = NULL;
        if (!strcmp(sfx, ".get")) ftype = EOLIAN_PROP_GET;
        else if (!strcmp(sfx, ".set")) ftype = EOLIAN_PROP_SET;
        if (ftype != EOLIAN_UNRESOLVED)
          {
             eina_stringshare_del(bname);
             mname = sfx - 1;
             while ((mname != refn) && (*mname != '.')) --mname;
             if (mname == refn) goto noref;
             bname = eina_stringshare_add_length(refn, mname - refn);
             cl = eolian_state_class_by_name_get(state, bname);
             eina_stringshare_del(bname);
          }
        if (cl)
          {
             char *meth = eina_strndup(mname + 1, sfx - mname - 1);
             fn = eolian_class_function_by_name_get(cl, meth, ftype);
             if (ftype == EOLIAN_UNRESOLVED)
               ftype = eolian_function_type_get(fn);
             free(meth);
          }
     }
   else
     {
        fn = eolian_class_function_by_name_get(cl, sfx + 1, ftype);
        ftype = eolian_function_type_get(fn);
     }

   if (!fn) goto noref;

   Eina_Stringshare *fcn = eolian_function_full_c_name_get(fn, ftype);
   if (!fcn) goto noref;
   eina_strbuf_append(wbuf, fcn);
   eina_stringshare_del(fcn);
   return;
noref:
   eina_strbuf_append(wbuf, refn);
}