/*
 * plugin.h: plugin handling
 *
 * Copyright (c) 2011 Cisco and/or its affiliates.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at:
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef __included_plugin_h__
#define __included_plugin_h__

#include <vlib/vlib.h>
#include <vlib/unix/unix.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>

/*
 * vlib plugin scheme
 *
 * Almost anything which can be made to work in a vlib unix
 * application will also work in a vlib plugin.
 *
 * The elf-section magic which registers static objects
 * works so long as plugins are preset when the vlib unix process
 * starts. But wait: there's more...
 *
 * If an application calls vlib_load_new_plugins() -- possibly after
 * changing vlib_plugin_main.plugin_path / vlib_plugin_main.plugin_name_filter,
 * -- new plugins will be loaded. That, in turn, allows considerable
 * flexibility in terms of adding feature code or fixing bugs without
 * requiring the data-plane process to restart.
 *
 * When the plugin mechanism loads a plugin, it uses dlsym to locate
 * and call the plugin's function vlib_plugin_register() if it exists.
 * A plugin which expects to be loaded after the vlib application
 * starts uses this callback to modify the application. If vlib_plugin_register
 * returns non-zero, the plugin mechanism dlclose()'s the plugin.
 *
 * Applications control the plugin search path and name filter by
 * declaring the variables vlib_plugin_path and vlib_plugin_name_filter.
 * libvlib.la supplies weak references for these symbols which
 * effectively disable the scheme. In order for the elf-section magic to
 * work, static plugins must be loaded at the earliest possible moment.
 *
 * An application can change these parameters at any time and call
 * vlib_load_new_plugins().
 */

typedef struct
{
  u8 default_disabled : 1;
  u8 deep_bind : 1;
  const char version[32];
  const char version_required[32];
  const char overrides[256];
  const char *early_init;
  const char *description;
} __clib_packed vlib_plugin_registration_t;

/*
 * Plugins may also use this registration format, which is
 * easy enough to emit from e.g. a golang compiler.
 */
typedef struct
{
  uword data_segment_offset;
  uword length;
} vlib_r2_string_t;

typedef struct
{
  int default_disabled;
  vlib_r2_string_t version;
  vlib_r2_string_t version_required;
  vlib_r2_string_t overrides;
  vlib_r2_string_t early_init;
  vlib_r2_string_t description;
} vlib_plugin_r2_t;

#define foreach_r2_string_field                 \
_(version)                                      \
_(version_required)                             \
_(overrides)                                    \
_(early_init)                                   \
_(description)

typedef struct
{
  u8 *name;
  u8 *filename;
  struct stat file_info;
  void *handle;

  /* plugin registration */
  vlib_plugin_registration_t *reg;
  char *version;
} plugin_info_t;

typedef struct
{
  char *name;
  u8 is_disabled;
  u8 is_enabled;
  u8 skip_version_check;
} plugin_config_t;

typedef struct
{
  /* loaded plugin info */
  plugin_info_t *plugin_info;
  uword *plugin_by_name_hash;
  uword *plugin_overrides_by_name_hash;

  /* paths and name filters */
  u8 *plugin_path;
  u8 *plugin_path_add;
  u8 *plugin_name_filter;
  u8 *vat_plugin_path;
  u8 *vat_plugin_name_filter;
  u8 plugins_default_disable;

  /* plugin configs and hash by name */
  plugin_config_t *configs;
  uword *config_index_by_name;

  /* Plugin log, avoid filling syslog w/ junk */
  vlib_log_class_t logger;

  /* usual */
  vlib_main_t *vlib_main;
} plugin_main_t;

extern plugin_main_t vlib_plugin_main;

clib_error_t *vlib_plugin_config (vlib_main_t * vm, unformat_input_t * input);
int vlib_plugin_early_init (vlib_main_t * vm);
int vlib_load_new_plugins (plugin_main_t * pm, int from_early_init);
void *vlib_get_plugin_symbol (char *plugin_name, char *symbol_name);
u8 *vlib_get_vat_plugin_path (void);

#define VLIB_PLUGIN_REGISTER() \
  vlib_plugin_registration_t vlib_plugin_registration \
  CLIB_NOSANITIZE_PLUGIN_REG_SECTION \
  __clib_export __clib_section(".vlib_plugin_registration")

/* Call a plugin init function: used for init function dependencies. */
#define vlib_call_plugin_init_function(vm,p,x)                  \
({                                                              \
  clib_error_t *(*_f)(vlib_main_t *);                           \
  uword *_fptr = 0;                                             \
  clib_error_t * _error = 0;                                    \
  _fptr= vlib_get_plugin_symbol                                 \
    (p, CLIB_STRING_MACRO(_vlib_init_function_##x));            \
  if (_fptr == 0)                                               \
    {                                                           \
      _error = clib_error_return                                \
        (0, "Plugin %s and/or symbol %s not found.",            \
         p, CLIB_STRING_MACRO(_vlib_init_function_##x));        \
    }                                                           \
  else                                                          \
    {                                                           \
      _f = (void *)(_fptr[0]);                                  \
    }                                                           \
  if (_fptr && ! hash_get (vm->init_functions_called, _f))      \
    {                                                           \
      hash_set1 (vm->init_functions_called, _f);                \
      _error = _f (vm);                                         \
    }                                                           \
  _error;                                                       \
 })

#endif /* __included_plugin_h__ */

/*
 * fd.io coding-style-patch-verification: ON
 *
 * Local Variables:
 * eval: (c-set-style "gnu")
 * End:
 */
