Anuket Project

Skip to end of metadata
Go to start of metadata

You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 19 Next »

 

An Overview of the architecture of a collectd plugin exists here: https://collectd.org/wiki/index.php/Plugin_architecture

 

To start off creating a plugin, create a c file under the src directory in collectd, the c file should have:

  1. A config function
  2. An init function
  3. A read function
  4. A shutdown function
  5. A function to register callbacks for all the functions above.

 

 

#include "collectd.h"
#include "common.h"
 
#define PLUGIN_NAME "my_plugin"
 
static _Bool g_enable_option1;
static char g_option2 [DATA_MAX_NAME_LEN];
 
static int my_config_function(oconfig_item_t *ci) {
  int ret = 0;
 
  INFO (PLUGIN_NAME ": %s:%d", __FUNCTION__, __LINE__);
 
  for (int i = 0; i < ci->children_num; i++) {
    oconfig_item_t *child = ci->children + i;
 
    if (strcasecmp("Option1", child->key) == 0) {
      ret = cf_util_get_boolean(child, & g_enable_option1);
    } else if (strcasecmp("Option2", child->key) == 0) {
      ret = cf_util_get_string_buffer(child, g_option2,
                                sizeof(g_option2));
 
    }else {
      ERROR(PLUGIN_NAME ": Unknown configuration parameter \"%s\".", child->key);
      ret = (-1);
    }
 
    if (ret != 0) {
      INFO (PLUGIN_NAME ": %s:%d ret=%d", __FUNCTION__, __LINE__, ret);
      return ret;
    }
  }
 
  return (0);
}
 
 
static int my_read_function(__attribute__((unused)) user_data_t *ud) {
 
  INFO (PLUGIN_NAME ": %s:%d", __FUNCTION__, __LINE__);
  /*  In order to dispatch values to the collectd daemon you need to fill out a value list and use plugin_dispatch_values() An example is provided below
   *
   *  value_list_t vl = VALUE_LIST_INIT;
   *
   *  vl.values = &(value_t){.derive = value}; //NOTE please change value to the actual value and use an appropriate type: checkout https://wiki.opnfv.org/display/fastpath/Collectd+101 for more info
   *
   *  vl.values_len = 1;
   *  sstrncpy(vl.host, hostname_g, sizeof(vl.host));
   *  sstrncpy(vl.plugin, PLUGIN_NAME, sizeof(vl.plugin));
   *  sstrncpy(vl.plugin_instance, "my_plugin_instance", sizeof(vl.plugin_instance)); // replace my_plugin_instance with an appropriate string/instance... see the end of this wiki
   *  sstrncpy(vl.type, "my_plugin_type", sizeof(vl.type));// replace my_plugin_type with an appropriate string... see the end of this wiki
   *
   *  plugin_dispatch_values(&vl);
   *
   *
   * To dispatch a notification you need to fill out a notification structure and use plugin_dispatch_notification()
   *  notification_t n = {
   *      .severity = severity, // where severity is one of NOTIF_OKAY, NOTIF_WARNING, NOTIF_FAILURE
   *      .time = cdtime(), 
   *      .message = "Some message",
   *      .plugin = PLUGIN_NAME}; 
   *
   *  sstrncpy(n.host, hostname_g, sizeof(n.host));
   *  sstrncpy(n.plugin_instance, "my_plugin_instance", sizeof(n.plugin_instance)); // replace my_plugin_instance with an appropriate string... see the end of this wiki
   *
   *  plugin_dispatch_notification(&n);
   */


  return (0);
}
 
 
static int my_shutdown_function (void) {
 
  INFO (PLUGIN_NAME ": %s:%d", __FUNCTION__, __LINE__);
 
  return (0);
}
 
static int my_init_function(void) {
  INFO(PLUGIN_NAME ": %s:%d", __FUNCTION__, __LINE__);
 
  return (0);
}
 
 
void module_register(void) {
 plugin_register_init("my_plugin", my_init_function);
  plugin_register_complex_config("my_plugin", my_config_function);
  plugin_register_complex_read(NULL, "my_plugin", my_read_function, 0, NULL);
  plugin_register_shutdown("my_plugin", my_shutdown_function);
}
 

 

Modify the types.db file to include a new type

my_plugin_type            value:DERIVE:0:U

 

Modify the Makefile.am file to build your plugin

if BUILD_PLUGIN_MY_PLUGIN
pkglib_LTLIBRARIES += my_plugin.la
my_plugin_la_SOURCES = src/my_plugin.c
my_plugin_la_CFLAGS = $(AM_CFLAGS)
my_plugin_la_LDFLAGS = $(PLUGIN_LDFLAGS)
endif

 

 

Modify the configure.ac file to include your plugin (search for plugin_ascent="no" and add it in the correct place alphpbetically), and set it to disabled (so it doesn’t build on all platforms):

 

plugin_my_plugin="no"

 

 

configure (in configure.ac)  your plugin so that it’s enabled on linux under:

# Linux
if test "x$ac_system" = "xLinux"; then
 
plugin_my_plugin="yes"

 

Configure (in configure.ac)  your plugin to report if it’s enabled or not:

AC_PLUGIN([my_plugin],           [$plugin_my_plugin],     [plugin desc])

 

 

In configure.ac under: “AC_MSG_RESULT([  Modules:])”, enable reporting on the plugin status from the configuration step:

AC_MSG_RESULT([    my_plugin. . . . . . $enable_my_plugin])

 

Finally it’s time to configure the configuration stanzas for your new plugin. By modifygin collectd.conf.in to include:

#@BUILD_PLUGIN_MY_PLUGIN_TRUE@LoadPlugin my_plugin


#<Plugin my_plugin>
#    Option1 true
#    Option2 “example”
#</Plugin>

 

 

Update the plugin configuration description in collectd.conf.pod

=head2 Plugin C<my_plugin>


The I< my_plugin > plugin collects TBD.


B<Synopsis:>


  <Plugin my_plugin>
    Option1 true
    Option2 “example”
  </Plugin>


B<Options:>


=over 2


=item B<Option1> B<false>|B<true>


TBD.


=item B< Option2> I<some_string>


TBD.


=back

 

you should now be able to build your simple collectd plugin:

$ ./build.sh
$ ./configure --prefix=$HOME/clct
$ make
$ make -j install

 

This will install collectd to $HOME/clct.

 

To run your new plugin:

$ cd $HOME/clct

 

Edit etc/collectd.conf to include:

LoadPlugin my_plugin
LoadPlugin logfile

<Plugin logfile>
        LogLevel debug
        File STDOUT
        Timestamp true
        PrintSeverity false
</Plugin>

<Plugin my_plugin>
    Option1 true
    Option2 “example”
</Plugin>

 

Run collectd:

sbin/collectd -f -C etc/collectd.conf

 

Extra Challenge:

  1. Try to add a double plugin configuration option and read it in with: cf_util_get_double
  2. Write the configuration parameters to the collectd logfile

 

Statistics in collectd

Statistics in collectd consist of a value list. A value list includes:

 

Value listExamplecomment
Values 99.8999percentage
Value lengththe number of values in the data set.  
Timetimestamp at which the value was collected.1475837857epoch
Intervalinterval at which to expect a new value.10interval
Hostused to identify the host.localhostcan be uuid for vm or host… or can give host a name
Pluginused to identify the plugin.cpu 
Plugin instance (optional)used to group a set of values together. For e.g. values belonging to a DPDK interface.0 
Typeunit used to measure a value. In other words used to refer to a data set.percent 
Type instance (optional)used to distinguish between values that have an identical type.user 
meta dataan opaque data structure that enables the passing of additional information about a value list. “Meta data in the global cache can be used to store arbitrary information about an identifier”   

Notifications in collectd


Notifications in collectd are generic messages containing:

An associated severity, which can be one of OKAY, WARNING, and FAILURE.
A time.      
A Message     
A host.      
A plugin.      
A plugin instance (optional).    
A type.      
A types instance (optional).    
Meta-data.     
  • No labels