Clang magic for Anjuta

Moritz Lüdecke

Clang is a compiler front-end for the LLVM compiler. It helps to analyse C, C++, Objective C and Objective C++ code and find mistakes just in time. I want bring Clang magic to anjuta. For more details see Google Summer of Code Proposal.

The Clang plugin isn't complete yet. Most of the time I spent to merge same code of the language support plugins.

What I've done

  • Split up the language-support plugins in an indentation part (indent-c-style, indent-python-style) and the support part: bug #676084

  • Improve calltips and resolve its dependencies from cpp-java plugin bug #678551

  • Merging same code of the language support plugins bug #680466

  • Documentation of the language support plugin bug #682140

  • Clang plugin bug #682139

Status reports

You can also take a look at my code on github.

The new architecture of the language support plugins

The new architecture of the language support plugins

The new architecture of the language support plugins

Now all same behaviour of the language plugins like when you start typing and got proposals are merged to one code base. The language support plugins implement their language-specific code through the new subinterface IAnjutaLanguageProvider.

The new architecture of a language support plugin

The new architecture of a language support plugin

The support class AnjutaLanguageProvider uses this implemented interface and executes the mechanism, which is all the same in each language support plugin. Additionally the language support plugins implement the IAnjutaLanguageProvider with the methods of AnjutaLanguageProvider. It's a little bit complicated, but look at the examples below.

Implementation of preference keys

The following keys have to be implemented as boolean in a GSetting file:

  • calltip-enable

  • completion-enable

  • completion-space-after-func

  • completion-brace-after-func

  • completion-closebrace-after-func

Implementation of IAnjutaProvider

assist->lang_prov is an AnjutaLanguageProvider object.

   1 static void
   2 iprovider_activate (IAnjutaProvider* self,
   3                    IAnjutaIterable* iter,
   4                    gpointer data,
   5                    GError** e)
   6 {
   7         LanguageAssist* assist = LANGUAGE_ASSIST (self);
   8         anjuta_language_provider_activate (assist->lang_prov, self, iter, data);
   9 }
  11 static void
  12 iprovider_populate (IAnjutaProvider* self,
  13                    IAnjutaIterable* cursor,
  14                    GError** e)
  15 {
  16         LanguageAssist* assist = LANGUAGE_ASSIST (self);
  17         anjuta_language_provider_populate (assist->lang_prov, self, cursor);
  18 }
  20 static const gchar*
  21 iprovider_get_name (IAnjutaProvider* self,
  22                    GError** e)
  23 {
  24         return _("Language name");
  25 }
  27 static IAnjutaIterable*
  28 iprovider_get_start_iter (IAnjutaProvider* self,
  29                          GError** e)
  30 {
  31         LanguageAssist* assist = LANGUAGE_ASSIST (self);
  32         return anjuta_language_provider_get_start_iter (assist->lang_prov);
  33 }
  35 static void
  36 iprovider_iface_init (IAnjutaProviderIface* iface)
  37 {
  38         iface->activate = iprovider_activate;
  39         iface->populate = iprovider_populate;
  40         iface->get_name = iprovider_get_name;
  41         iface->get_start_iter = iprovider_get_start_iter;
  42 }

Implementation of IAnjutaLanguageProvider

   1 static GList*
   2 ilanguage_provider_get_calltip_cache (IAnjutaLanguageProvider* self,
   3                                      gchar* call_context,
   4                                      GError** e)
   5 {
   6         /* language-specific code */
   7 }
   9 static gchar*
  10 ilanguage_provider_get_calltip_context (IAnjutaLanguageProvider *self,
  11                                        IAnjutaIterable *iter,
  12                                        GError** e)
  13 {
  14         /* language-specific code */
  15 }
  17 static void
  18 ilanguage_provider_new_calltip (IAnjutaLanguageProvider* self,
  19                                gchar* call_context,
  20                                IAnjutaIterable* cursor,
  21                                GError** e)
  22 {
  23         /* language-specific code */
  24 }
  26 static IAnjutaIterable*
  27 ilanguage_provider_populate_language (IAnjutaLanguageProvider* self,
  28                                      IAnjutaIterable* cursor,
  29                                      GError** e)
  30 {
  31         /* language-specific code */
  32 }
  34 static void
  35 ilanguage_provider_iface_init (IAnjutaLanguageProviderIface* iface)
  36 {
  37         iface->get_calltip_cache = ilanguage_provider_get_calltip_cache;
  38         iface->get_calltip_context = ilanguage_provider_get_calltip_context;
  39         iface->new_calltip = ilanguage_provider_new_calltip;
  40         iface->populate_language = ilanguage_provider_populate_language;
  41 }

When you call ianjuta_editor_assist_proposals() you have to set the elements of the proposal list in the right way:

   1 GList* list = NULL;
   2 IAnjutaEditorAssistProposal* proposal = g_new0 (IAnjutaEditorAssistProposal, 1);
   3 AnjutaLanguageProviderProposalData* data = g_new0 (AnjutaLanguageProviderProposalData, 1);
   5 /* set data->name, data->is_func and data->has_para */
   7 proposal->data = data;
   8 list = g_list_append (list, proposal);

See also The new architecture of the language support plugins from 26.07.

Some other improvements

Improve completion behaviour for C/C++ in Anjuta

See also Improve completion behaviour for C/C++ in Anjuta from 21.06.

Same behaviour and own preferences widget for each language plugin

The Python preferences before and after

The Python preferences before and after

As part of merging code and unifying the behaviour of each language plugin I improved the Vala plugin. Calltips show method names and return types now instead of only the parameters of the function as it was before.

Additionally the vala plugin has its own preferences widget now. Before it used the preferences of the cpp-java plugin. As a consequence the Vala plugin no longer depends on the cpp-java plugin. While doing this work I learned, how I can integrate C interfaces in a plugin, which is written in Vala.

But the Vala plugin is not the only one which got an update. The Python plugin has the “Add ‘)’ after function call autocompletion” option now. With this new option the Python plugin has the same functionality as the other language plugins and so I made the preference widget looking like the preferences widget of the other plugins.

See also Vala and Python from 26.06.




  • Email: <ritze AT skweez DOT net>

  • Blog:

  • IRC: ritze

Outreach/SummerOfCode/2012/Projects/MoritzLuedecke_Anjuta_Clang (last edited 2013-12-03 18:33:52 by WilliamJonMcCann)