Merge remote-tracking branch 'github/pr/2091'
authorFlorian Forster <octo@collectd.org>
Fri, 6 Oct 2017 11:14:01 +0000 (13:14 +0200)
committerFlorian Forster <octo@collectd.org>
Fri, 6 Oct 2017 11:14:01 +0000 (13:14 +0200)
1  2 
src/collectd.conf.in
src/collectd.conf.pod
src/ipmi.c

diff --combined src/collectd.conf.in
  #@BUILD_PLUGIN_DF_TRUE@LoadPlugin df
  #@BUILD_PLUGIN_DISK_TRUE@LoadPlugin disk
  #@BUILD_PLUGIN_DNS_TRUE@LoadPlugin dns
 +#@BUILD_PLUGIN_DPDKEVENTS_TRUE@LoadPlugin dpdkevents
  #@BUILD_PLUGIN_DPDKSTAT_TRUE@LoadPlugin dpdkstat
  #@BUILD_PLUGIN_DRBD_TRUE@LoadPlugin drbd
  #@BUILD_PLUGIN_EMAIL_TRUE@LoadPlugin email
  #@BUILD_PLUGIN_GRPC_TRUE@LoadPlugin grpc
  #@BUILD_PLUGIN_HDDTEMP_TRUE@LoadPlugin hddtemp
  #@BUILD_PLUGIN_HUGEPAGES_TRUE@LoadPlugin hugepages
 +#@BUILD_PLUGIN_INTEL_PMU_TRUE@LoadPlugin intel_pmu
  #@BUILD_PLUGIN_INTEL_RDT_TRUE@LoadPlugin intel_rdt
  @BUILD_PLUGIN_INTERFACE_TRUE@@BUILD_PLUGIN_INTERFACE_TRUE@LoadPlugin interface
  #@BUILD_PLUGIN_IPC_TRUE@LoadPlugin ipc
  #@BUILD_PLUGIN_LVM_TRUE@LoadPlugin lvm
  #@BUILD_PLUGIN_MADWIFI_TRUE@LoadPlugin madwifi
  #@BUILD_PLUGIN_MBMON_TRUE@LoadPlugin mbmon
 +#@BUILD_PLUGIN_MCELOG_TRUE@LoadPlugin mcelog
  #@BUILD_PLUGIN_MD_TRUE@LoadPlugin md
  #@BUILD_PLUGIN_MEMCACHEC_TRUE@LoadPlugin memcachec
  #@BUILD_PLUGIN_MEMCACHED_TRUE@LoadPlugin memcached
  #@BUILD_PLUGIN_OPENLDAP_TRUE@LoadPlugin openldap
  #@BUILD_PLUGIN_OPENVPN_TRUE@LoadPlugin openvpn
  #@BUILD_PLUGIN_ORACLE_TRUE@LoadPlugin oracle
 +#@BUILD_PLUGIN_OVS_EVENTS_TRUE@LoadPlugin ovs_events
 +#@BUILD_PLUGIN_OVS_STATS_TRUE@LoadPlugin ovs_stats
  #@BUILD_PLUGIN_PERL_TRUE@LoadPlugin perl
  #@BUILD_PLUGIN_PINBA_TRUE@LoadPlugin pinba
  #@BUILD_PLUGIN_PING_TRUE@LoadPlugin ping
  #@BUILD_PLUGIN_SIGROK_TRUE@LoadPlugin sigrok
  #@BUILD_PLUGIN_SMART_TRUE@LoadPlugin smart
  #@BUILD_PLUGIN_SNMP_TRUE@LoadPlugin snmp
 +#@BUILD_PLUGIN_SNMP_AGENT_TRUE@LoadPlugin snmp_agent
  #@BUILD_PLUGIN_STATSD_TRUE@LoadPlugin statsd
  #@BUILD_PLUGIN_SWAP_TRUE@LoadPlugin swap
  #@BUILD_PLUGIN_TABLE_TRUE@LoadPlugin table
  #  ReportByCpu true
  #  ReportByState true
  #  ValuesPercentage false
 +#  ReportNumCpu false
 +#  ReportGuestState false
 +#  SubtractGuestState true
  #</Plugin>
  #
  #<Plugin csv>
  #<Plugin curl_xml>
  #  <URL "http://localhost/stats.xml">
  #    Host "my_host"
 +#    #Plugin "stats"
  #    Instance "some_instance"
  #    User "collectd"
  #    Password "thaiNg0I"
  #      Type "magic_level"
  #      #InstancePrefix "prefix-"
  #      InstanceFrom "td[1]"
 +#      #PluginInstanceFrom "td[1]"
  #      ValuesFrom "td[2]/span[@class=\"level\"]"
  #    </XPath>
  #  </URL>
  #             </Result>
  #     </Query>
  #     <Database "customers_db">
 +#             #Plugin "mycompany"
  #             Driver "mysql"
  #             DriverOption "host" "localhost"
  #             DriverOption "username" "collectd"
  #     SelectNumericQueryTypes true
  #</Plugin>
  
 +#<Plugin "dpdkevents">
 +#  <EAL>
 +#    Coremask "0x1"
 +#    MemoryChannels "4"
 +#    FilePrefix "rte"
 +#  </EAL>
 +#  <Event "link_status">
 +#    SendEventsOnUpdate true
 +#    EnabledPortMask 0xffff
 +#    PortName "interface1"
 +#    PortName "interface2"
 +#    SendNotification false
 +#  </Event>
 +#  <Event "keep_alive">
 +#    SendEventsOnUpdate true
 +#    LCoreMask "0xf"
 +#    KeepAliveShmName "/dpdk_keepalive_shm_name"
 +#    SendNotification false
 +#  </Event>
 +#</Plugin>
 +
  #<Plugin dpdkstat>
 -#       Interval 1
 -#       Coremask "0xf"
 -#       ProcessType "secondary"
 -#       FilePrefix "rte"
 -#       EnabledPortMask 0xffff
 -#       PortName "interface1"
 -#       PortName "interface2"
 +#  <EAL>
 +#    Coremask "0x2"
 +#    MemoryChannels "4"
 +#    FilePrefix "rte"
 +#  </EAL>
 +#  SharedMemObj "dpdk_collectd_stats_0"
 +#  EnabledPortMask 0xffff
 +#  PortName "interface1"
 +#  PortName "interface2"
  #</Plugin>
  
  #<Plugin email>
  
  #<Plugin filecount>
  #     <Directory "/path/to/dir">
 +#             #Plugin "foo"
  #             Instance "foodir"
  #             Name "*.conf"
  #             MTime "-5m"
  #             Size "+10k"
  #             Recursive true
  #             IncludeHidden false
 +#             #FilesSizeType "bytes"
 +#             #FilesCountType "files"
 +#             #TypeInstance "instance"
  #     </Directory>
  #</Plugin>
  
  #    ValuesPercentage false
  #</Plugin>
  
 +#<Plugin intel_pmu>
 +#    ReportHardwareCacheEvents true
 +#    ReportKernelPMUEvents true
 +#    ReportSoftwareEvents true
 +#    EventList "/var/cache/pmu/GenuineIntel-6-2D-core.json"
 +#    HardwareEvents "L2_RQSTS.CODE_RD_HIT,L2_RQSTS.CODE_RD_MISS" "L2_RQSTS.ALL_CODE_RD"
 +#</Plugin>
 +
  #<Plugin "intel_rdt">
  #  Cores "0-2"
  #</Plugin>
  #     NotifySensorAdd false
  #     NotifySensorRemove true
  #     NotifySensorNotPresent false
+ #     SELEnabled false
+ #     SELClearEvent false
  #</Plugin>
  
  #<Plugin iptables>
  #     Port "411"
  #</Plugin>
  
 +#<Plugin mcelog>
 +#  <Memory>
 +#    McelogClientSocket "/var/run/mcelog-client"
 +#    PersistentNotification false
 +#  </Memory>
 +#  McelogLogfile "/var/log/mcelog"
 +#</Plugin>
 +
  #<Plugin md>
  #     Device "/dev/md0"
  #     IgnoreSelected false
  #             QoS 2
  #             Topic "collectd/#"
  #             CleanSession true
 +#             CACert "/etc/ssl/ca.crt"
 +#             CertificateFile "/etc/ssl/client.crt"
 +#             CertificateKeyFile "/etc/ssl/client.pem"
 +#             TLSProtocol "tlsv1.2"
 +#             CipherSuite "ciphers"
  #     </Subscribe>
  #</Plugin>
  
  #     CacheFlush 1800
  @LOAD_PLUGIN_NETWORK@</Plugin>
  
 +#<Plugin nfs>
 +#     ReportV2 false
 +#     #ReportV3 false
 +#     #ReportV4 false
 +#</Plugin>
 +
  #<Plugin nginx>
  #     URL "http://localhost/status?auto"
  #     User "www-user"
  
  #<Plugin nut>
  #     UPS "upsname@hostname:port"
 +#     ForceSSL true
 +#     VerifyPeer true
 +#     CAPath "/path/to/folder"
 +#     #ConnectTimeout 5000
  #</Plugin>
  
  #<Plugin olsrd>
  #    </Result>
  #  </Query>
  #  <Database "product_information">
 +#    #Plugin "warehouse"
  #    ConnectID "db01"
  #    Username "oracle"
  #    Password "secret"
  #  </Database>
  #</Plugin>
  
 +#<Plugin ovs_events>
 +#  Port "6640"
 +#  Address "127.0.0.1"
 +#  Socket "/var/run/openvswitch/db.sock"
 +#  Interfaces "br0" "veth0"
 +#  SendNotification true
 +#  DispatchValues false
 +#</Plugin>
 +
 +#<Plugin ovs_stats>
 +#  Port "6640"
 +#  Address "127.0.0.1"
 +#  Socket "/var/run/openvswitch/db.sock"
 +#  Bridges "br0" "br_ext"
 +#</Plugin>
 +
  #<Plugin perl>
  #     IncludeDir "/my/include/path"
  #     BaseName "Collectd::Plugins"
  #             StoreRates true
  #     </Writer>
  #     <Database foo>
 +#             #Plugin "kingdom"
  #             Host "hostname"
  #             Port "5432"
  #             User "username"
  #</Plugin>
  
  #<Plugin processes>
 +#     CollectFileDescriptor true
 +#     CollectContextSwitch true
 +#     CollectMemoryMaps true
  #     Process "name"
 +#     ProcessMatch "name" "regex"
 +#     <Process "collectd">
 +#             CollectFileDescriptor false
 +#             CollectContextSwitch false
 +#     </Process>
 +#     <ProcessMatch "name" "regex">
 +#             CollectFileDescriptor false
 +#             CollectContextSwitch true
 +#     </Process>
  #</Plugin>
  
  #<Plugin protocols>
  #   </Host>
  #</Plugin>
  
 +#<Plugin snmp_agent>
 +#  <Data "memAvailReal">
 +#    Plugin "memory"
 +#    Type "memory"
 +#    TypeInstance "free"
 +#    OIDs "1.3.6.1.4.1.2021.4.6.0"
 +#  </Data>
 +#  <Table "ifTable">
 +#    IndexOID "IF-MIB::ifIndex"
 +#    SizeOID "IF-MIB::ifNumber"
 +#    <Data "ifDescr">
 +#      Instance true
 +#      Plugin "interface"
 +#      OIDs "IF-MIB::ifDescr"
 +#    </Data>
 +#    <Data "ifOctets">
 +#      Plugin "interface"
 +#      Type "if_octets"
 +#      TypeInstance ""
 +#      OIDs "IF-MIB::ifInOctets" "IF-MIB::ifOutOctets"
 +#    </Data>
 +#  </Table>
 +#</Plugin>
 +
  #<Plugin statsd>
  #  Host "::"
  #  Port "8125"
  #     ReportBytes true
  #     ValuesAbsolute true
  #     ValuesPercentage false
 +#     ReportIO true
  #</Plugin>
  
  #<Plugin table>
  #     <Table "/proc/slabinfo">
 +#             #Plugin "table"
  #             Instance "slabinfo"
  #             Separator " "
  #             <Result>
  #        Bucket 0.5 1.0   # -> bucket-latency-foo-0.5_1
  #        Bucket 1.0 2.0   # -> bucket-latency-foo-1_2
  #        Bucket 2.0 0     # -> bucket-latency-foo-2_inf
 +#        #BucketType "bucket"
  #      </DSType>
  #      Type "latency"
  #      Instance "foo"
  #     SystemManagementInterrupt true
  #     DigitalTemperatureSensor true
  #     PackageThermalManagement true
 -#     RunningAveragePowerLimit "7"    
 +#     RunningAveragePowerLimit "7"
  #</Plugin>
  
  #<Plugin unixsock>
  #      CollectPurge false         # Varnish 2 only
  #      CollectSession false
  #      CollectSHM true
 -#      CollectSMA false           # Varnish 2 only
 +#      CollectSMA false           # Varnish 2 & 4 only
  #      CollectSMS false
  #      CollectSM false            # Varnish 2 only
  #      CollectStruct false
  #      CollectVCL false
  #      CollectVSM false           # Varnish 4 only
  #      CollectWorkers false
 +#      CollectLock false          # Varnish 4 only
 +#      CollectMempool false       # Varnish 4 only
 +#      CollectManagement false    # Varnish 4 only
 +#      CollectSMF false           # Varnish 4 only
 +#      CollectVBE false           # Varnish 4 only
  #   </Instance>
  #</Plugin>
  
  #     InterfaceFormat name
  #     PluginInstanceFormat name
  #     Instances 1
 +#     ExtraStats "cpu_util disk disk_err domain_state fs_info job_stats_background pcpu perf vcpupin"
  #</Plugin>
  
  #<Plugin vmem>
  #             Header "X-Custom-Header: custom_value"
  #             SSLVersion "TLSv1"
  #             Format "Command"
 +#             Attribute "key" "value"     # only available for KAIROSDB format
 +#             TTL 0   # data ttl, only available for KAIROSDB format
  #             Metrics true
  #             Notifications false
  #             StoreRates false
diff --combined src/collectd.conf.pod
@@@ -338,7 -338,7 +338,7 @@@ is enabled by default
  =item B<PostCacheChain> I<ChainName>
  
  Configure the name of the "pre-cache chain" and the "post-cache chain". Please
 -see L<FILTER CONFIGURATION> below on information on chains and how these
 +see L</"FILTER CONFIGURATION"> below on information on chains and how these
  setting change the daemon's behavior.
  
  =back
@@@ -1372,8 -1372,6 +1372,8 @@@ Select I<cgroup> based on the name. Whe
  collected or if they are ignored is controlled by the B<IgnoreSelected> option;
  see below.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> B<true>|B<false>
  
  Invert the selection: If set to true, all cgroups I<except> the ones that
@@@ -1474,19 -1472,6 +1474,19 @@@ in the un-aggregated (per-CPU, per-stat
  When set to B<true>, reports the number of available CPUs.
  Defaults to B<false>.
  
 +=item B<ReportGuestState> B<false>|B<true>
 +
 +When set to B<true>, reports the "guest" and "guest_nice" CPU states.
 +Defaults to B<false>.
 +
 +=item B<SubtractGuestState> B<false>|B<true>
 +
 +This option is only considered when B<ReportGuestState> is set to B<true>.
 +"guest" and "guest_nice" are included in respectively "user" and "nice".
 +If set to B<true>, "guest" will be subtracted from "user" and "guest_nice"
 +will be subtracted from "nice".
 +Defaults to B<true>.
 +
  =back
  
  =head2 Plugin C<cpufreq>
@@@ -1624,7 -1609,6 +1624,7 @@@ finance page and dispatch the value to 
  
    <Plugin curl>
      <Page "stock_quotes">
 +      Plugin "quotes"
        URL "http://finance.google.com/finance?q=NYSE%3AAMD"
        User "foo"
        Password "bar"
@@@ -1656,11 -1640,6 +1656,11 @@@ The following options are valid within 
  
  =over 4
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting values.
 +Defaults to C<curl>.
 +
  =item B<URL> I<URL>
  
  URL of the web site to retrieve. Since a regular expression will be used to
@@@ -1821,11 -1800,6 +1821,11 @@@ The following options are valid within 
  Use I<Name> as the host name when submitting values. Defaults to the global
  host name setting.
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting values.
 +Defaults to C<curl_json>.
 +
  =item B<Instance> I<Instance>
  
  Sets the plugin instance to I<Instance>.
@@@ -1888,7 -1862,6 +1888,7 @@@ The B<curl_xml plugin> uses B<libcurl> 
   <Plugin "curl_xml">
     <URL "http://localhost/stats.xml">
       Host "my_host"
 +     #Plugin "curl_xml"
       Instance "some_instance"
       User "collectd"
       Password "thaiNg0I"
         Type "magic_level"
         #InstancePrefix "prefix-"
         InstanceFrom "td[1]"
 +       #PluginInstanceFrom "td[1]"
         ValuesFrom "td[2]/span[@class=\"level\"]"
       </XPath>
     </URL>
@@@ -1928,16 -1900,10 +1928,16 @@@ Within the B<URL> block the following o
  Use I<Name> as the host name when submitting values. Defaults to the global
  host name setting.
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting values.
 +Defaults to 'curl_xml'.
 +
  =item B<Instance> I<Instance>
  
 -Use I<Instance> as the plugin instance when submitting values. Defaults to an
 -empty string (no plugin instance).
 +Use I<Instance> as the plugin instance when submitting values.
 +May be overridden by B<PluginInstanceFrom> option inside B<XPath> blocks.
 +Defaults to an empty string (no plugin instance).
  
  =item B<Namespace> I<Prefix> I<URL>
  
@@@ -2008,19 -1974,9 +2008,19 @@@ Specifies a XPath expression to use fo
  XPath expression must return exactly one element. The element's value is then
  used as I<type instance>, possibly prefixed with I<InstancePrefix> (see above).
  
 -This value is required. As a special exception, if the "base XPath expression"
 -(the argument to the B<XPath> block) returns exactly one argument, then this
 -option may be omitted.
 +=item B<PluginInstanceFrom> I<PluginInstanceFrom>
 +
 +Specifies a XPath expression to use for determining the I<plugin instance>. The
 +XPath expression must return exactly one element. The element's value is then
 +used as I<plugin instance>.
 +
 +=back
 +
 +If the "base XPath expression" (the argument to the B<XPath> block) returns
 +exactly one argument, then I<InstanceFrom> and I<PluginInstanceFrom> may be omitted.
 +Otherwise, at least one of I<InstanceFrom> or I<PluginInstanceFrom> is required.
 +
 +=over 4
  
  =item B<ValuesFrom> I<ValuesFrom> [I<ValuesFrom> ...]
  
@@@ -2029,7 -1985,6 +2029,7 @@@ number of XPath expressions must match 
  I<type> specified with B<Type> (see above). Each XPath expression must return
  exactly one element. The element's value is then parsed as a number and used as
  value for the appropriate value in the value list dispatched to the daemon.
 +This option is required.
  
  =back
  
@@@ -2060,7 -2015,6 +2060,7 @@@ than those of other plugins. It usuall
        </Result>
      </Query>
      <Database "product_information">
 +      #Plugin "warehouse"
        Driver "mysql"
        Interval 120
        DriverOption "host" "localhost"
@@@ -2242,11 -2196,6 +2242,11 @@@ the daemon. Other than that, that name 
  
  =over 4
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting query results from
 +this B<Database>. Defaults to C<dbi>.
 +
  =item B<Interval> I<Interval>
  
  Sets the interval (in seconds) in which the values will be collected from this
@@@ -2319,20 -2268,14 +2319,20 @@@ values. Defaults to the global hostnam
  
  Select partitions based on the devicename.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<MountPoint> I<Directory>
  
  Select partitions based on the mountpoint.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<FSType> I<FSType>
  
  Select partitions based on the filesystem type.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> B<true>|B<false>
  
  Invert the selection: If set to true, all partitions B<except> the ones that
@@@ -2394,8 -2337,6 +2394,8 @@@ is interpreted as a regular expression
    Disk "sdd"
    Disk "/hda[34]/"
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> B<true>|B<false>
  
  Sets whether selected disks, i.E<nbsp>e. the ones matches by any of the B<Disk>
@@@ -2442,123 -2383,6 +2442,123 @@@ Enabled by default, collects unknown (a
  
  =back
  
 +=head2 Plugin C<dpdkevents>
 +
 +The I<dpdkevents plugin> collects events from DPDK such as link status of
 +network ports and Keep Alive status of DPDK logical cores.
 +In order to get Keep Alive events following requirements must be met:
 +- DPDK >= 16.07
 +- support for Keep Alive implemented in DPDK application. More details can
 +be found here: http://dpdk.org/doc/guides/sample_app_ug/keep_alive.html
 +
 +B<Synopsis:>
 +
 + <Plugin "dpdkevents">
 +   <EAL>
 +     Coremask "0x1"
 +     MemoryChannels "4"
 +     FilePrefix "rte"
 +   </EAL>
 +   <Event "link_status">
 +     SendEventsOnUpdate true
 +     EnabledPortMask 0xffff
 +     PortName "interface1"
 +     PortName "interface2"
 +     SendNotification false
 +   </Event>
 +   <Event "keep_alive">
 +     SendEventsOnUpdate true
 +     LCoreMask "0xf"
 +     KeepAliveShmName "/dpdk_keepalive_shm_name"
 +     SendNotification false
 +   </Event>
 + </Plugin>
 +
 +B<Options:>
 +
 +
 +=head3 The EAL block
 +
 +=over 4
 +
 +=item B<Coremask> I<Mask>
 +
 +=item B<Memorychannels> I<Channels>
 +
 +Number of memory channels per processor socket.
 +
 +=item B<FilePrefix> I<File>
 +
 +The prefix text used for hugepage filenames. The filename will be set to
 +/var/run/.<prefix>_config where prefix is what is passed in by the user.
 +
 +=back
 +
 +=head3 The Event block
 +
 +The B<Event> block defines configuration for specific event. It accepts a
 +single argument which specifies the name of the event.
 +
 +=head4 Link Status event
 +
 +=over 4
 +
 +=item B<SendEventOnUpdate> I<true|false>
 +
 +If set to true link status value will be dispatched only when it is
 +different from previously read value. This is an optional argument - default
 +value is true.
 +
 +=item B<EnabledPortMask> I<Mask>
 +
 +A hexidecimal bit mask of the DPDK ports which should be enabled. A mask
 +of 0x0 means that all ports will be disabled. A bitmask of all F's means
 +that all ports will be enabled. This is an optional argument - by default
 +all ports are enabled.
 +
 +=item B<PortName> I<Name>
 +
 +A string containing an optional name for the enabled DPDK ports. Each PortName
 +option should contain only one port name; specify as many PortName options as
 +desired. Default naming convention will be used if PortName is blank. If there
 +are less PortName options than there are enabled ports, the default naming
 +convention will be used for the additional ports.
 +
 +=item B<SendNotification> I<true|false>
 +
 +If set to true, link status notifications are sent, instead of link status
 +being collected as a statistic. This is an optional argument - default
 +value is false.
 +
 +=back
 +
 +=head4 Keep Alive event
 +
 +=over 4
 +
 +=item B<SendEventOnUpdate> I<true|false>
 +
 +If set to true keep alive value will be dispatched only when it is
 +different from previously read value. This is an optional argument - default
 +value is true.
 +
 +=item B<LCoreMask> I<Mask>
 +
 +An hexadecimal bit mask of the logical cores to monitor keep alive state.
 +
 +=item B<KeepAliveShmName> I<Name>
 +
 +Shared memory name identifier that is used by secondary process to monitor
 +the keep alive cores state.
 +
 +=item B<SendNotification> I<true|false>
 +
 +If set to true, keep alive notifications are sent, instead of keep alive
 +information being collected as a statistic. This is an optional
 +argument - default value is false.
 +
 +=back
 +
  =head2 Plugin C<dpdkstat>
  
  The I<dpdkstat plugin> collects information about DPDK interfaces using the
@@@ -2567,22 -2391,17 +2567,22 @@@ extended NIC stats API in DPDK
  B<Synopsis:>
  
   <Plugin "dpdkstat">
 -    Coremask "0x4"
 -    MemoryChannels "4"
 -    ProcessType "secondary"
 -    FilePrefix "rte"
 -    EnabledPortMask 0xffff
 -    PortName "interface1"
 -    PortName "interface2"
 +   <EAL>
 +     Coremask "0x4"
 +     MemoryChannels "4"
 +     FilePrefix "rte"
 +     SocketMemory "1024"
 +   </EAL>
 +   SharedMemObj "dpdk_collectd_stats_0"
 +   EnabledPortMask 0xffff
 +   PortName "interface1"
 +   PortName "interface2"
   </Plugin>
  
  B<Options:>
  
 +=head3 The EAL block
 +
  =over 4
  
  =item B<Coremask> I<Mask>
@@@ -2594,6 -2413,10 +2594,6 @@@ core numbering can change between platf
  
  A string containing a number of memory channels per processor socket.
  
 -=item B<ProcessType> I<type>
 -
 -A string containing the type of DPDK process instance.
 -
  =item B<FilePrefix> I<File>
  
  The prefix text used for hugepage filenames. The filename will be set to
  =item B<SocketMemory> I<MB>
  
  A string containing amount of Memory to allocate from hugepages on specific
 -sockets in MB
 +sockets in MB. This is an optional value.
 +
 +=back
 +
 +=over 3
 +
 +=item B<SharedMemObj> I<Mask>
 +
 +A string containing the name of the shared memory object that should be used to
 +share stats from the DPDK secondary process to the collectd dpdkstat plugin.
 +Defaults to dpdk_collectd_stats if no other value is configured.
  
  =item B<EnabledPortMask> I<Mask>
  
@@@ -2779,16 -2592,12 +2779,16 @@@ blocks, the following options are recog
  
  =over 4
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting values.
 +Defaults to B<filecount>.
 +
  =item B<Instance> I<Instance>
  
 -Sets the plugin instance to I<Instance>. That instance name must be unique, but
 -it's your responsibility, the plugin doesn't check for that. If not given, the
 -instance is set to the directory name with all slashes replaced by underscores
 -and all leading underscores removed.
 +Sets the plugin instance to I<Instance>. If not given, the instance is set to
 +the directory name with all slashes replaced by underscores and all leading
 +underscores removed. Empty value is allowed.
  
  =item B<Name> I<Pattern>
  
@@@ -2834,21 -2643,6 +2834,21 @@@ Controls whether or not to include "hid
  "Hidden" files and directories are those, whose name begins with a dot.
  Defaults to I<false>, i.e. by default hidden files and directories are ignored.
  
 +=item B<FilesSizeType> I<Type>
 +
 +Sets the type used to dispatch files combined size. Empty value ("") disables
 +reporting. Defaults to B<bytes>.
 +
 +=item B<FilesCountType> I<Type>
 +
 +Sets the type used to dispatch number of files. Empty value ("") disables
 +reporting. Defaults to B<files>.
 +
 +=item B<TypeInstance> I<Instance>
 +
 +Sets the I<type instance> used to dispatch values. Defaults to an empty string
 +(no plugin instance).
 +
  =back
  
  =head2 Plugin C<GenericJMX>
@@@ -3141,92 -2935,6 +3141,92 @@@ Defaults to B<false>
  
  =back
  
 +=head2 Plugin C<intel_pmu>
 +
 +The I<intel_pmu> plugin collects performance counters data on Intel CPUs using
 +Linux perf interface. All events are reported on a per core basis.
 +
 +B<Synopsis:>
 +
 +  <Plugin intel_pmu>
 +    ReportHardwareCacheEvents true
 +    ReportKernelPMUEvents true
 +    ReportSoftwareEvents true
 +    EventList "/var/cache/pmu/GenuineIntel-6-2D-core.json"
 +    HardwareEvents "L2_RQSTS.CODE_RD_HIT,L2_RQSTS.CODE_RD_MISS" "L2_RQSTS.ALL_CODE_RD"
 +  </Plugin>
 +
 +B<Options:>
 +
 +=over 4
 +
 +=item B<ReportHardwareCacheEvents> B<false>|B<true>
 +
 +Enable or disable measuring of hardware CPU cache events:
 +  - L1-dcache-loads
 +  - L1-dcache-load-misses
 +  - L1-dcache-stores
 +  - L1-dcache-store-misses
 +  - L1-dcache-prefetches
 +  - L1-dcache-prefetch-misses
 +  - L1-icache-loads
 +  - L1-icache-load-misses
 +  - L1-icache-prefetches
 +  - L1-icache-prefetch-misses
 +  - LLC-loads
 +  - LLC-load-misses
 +  - LLC-stores
 +  - LLC-store-misses
 +  - LLC-prefetches
 +  - LLC-prefetch-misses
 +  - dTLB-loads
 +  - dTLB-load-misses
 +  - dTLB-stores
 +  - dTLB-store-misses
 +  - dTLB-prefetches
 +  - dTLB-prefetch-misses
 +  - iTLB-loads
 +  - iTLB-load-misses
 +  - branch-loads
 +  - branch-load-misses
 +
 +=item B<ReportKernelPMUEvents> B<false>|B<true>
 +
 +Enable or disable measuring of the following events:
 +  - cpu-cycles
 +  - instructions
 +  - cache-references
 +  - cache-misses
 +  - branches
 +  - branch-misses
 +  - bus-cycles
 +
 +=item B<ReportSoftwareEvents> B<false>|B<true>
 +
 +Enable or disable measuring of software events provided by kernel:
 +  - cpu-clock
 +  - task-clock
 +  - context-switches
 +  - cpu-migrations
 +  - page-faults
 +  - minor-faults
 +  - major-faults
 +  - alignment-faults
 +  - emulation-faults
 +
 +=item B<EventList> I<filename>
 +
 +JSON performance counter event list file name. To be able to monitor all Intel
 +CPU specific events JSON event list file should be downloaded. Use the pmu-tools
 +event_download.py script to download event list for current CPU.
 +
 +=item B<HardwareEvents> I<events>
 +
 +This field is a list of event names or groups of comma separated event names.
 +This option requires B<EventList> option to be configured.
 +
 +=back
 +
  =head2 Plugin C<intel_rdt>
  
  The I<intel_rdt> plugin collects information provided by monitoring features of
@@@ -3241,10 -2949,6 +3241,10 @@@ allows to monitor instructions per cloc
  Monitor events are hardware dependant. Monitoring capabilities are detected on
  plugin initialization and only supported events are monitored.
  
 +B<Note:> I<intel_rdt> plugin is using model-specific registers (MSRs), which
 +require an additional capability to be enabled if collectd is run as a service.
 +Please refer to I<contrib/systemd.collectd.service> file for more details.
 +
  B<Synopsis:>
  
    <Plugin "intel_rdt">
@@@ -3294,11 -2998,9 +3294,11 @@@ than 1 sec
  Select this interface. By default these interfaces will then be collected. For
  a more detailed description see B<IgnoreSelected> below.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> I<true>|I<false>
  
 -If no configuration if given, the B<interface>-plugin will collect data from
 +If no configuration is given, the B<interface>-plugin will collect data from
  all interfaces. This may not be practical, especially for loopback- and
  similar interfaces. Thus, you can use the B<Interface>-option to pick the
  interfaces you're interested in. Sometimes, however, it's easier/preferred
@@@ -3357,8 -3059,6 +3357,8 @@@ This option is only available on Solari
  
  Selects sensors to collect or to ignore, depending on B<IgnoreSelected>.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> I<true>|I<false>
  
  If no configuration if given, the B<ipmi> plugin will collect data from all
@@@ -3381,6 -3081,19 +3381,19 @@@ If a sensor disappears a notification i
  If you have for example dual power supply and one of them is (un)plugged then
  a notification is sent.
  
+ =item B<SELEnabled> I<true>|I<false>
+ If system event log (SEL) is enabled, plugin will listen for sensor threshold
+ and discrete events. When event is received the notification is sent.
+ Defaults to B<false>.
+ =item B<SELClearEvent> I<true>|I<false>
+ If SEL clear event is enabled, plugin will delete event from SEL list after
+ it is received and successfully handled. In this case other tools that are
+ subscribed for SEL events will receive an empty event.
+ Defaults to B<false>.
  =back
  
  =head2 Plugin C<iptables>
@@@ -3415,8 -3128,6 +3428,8 @@@ comment or the number
  Select this irq. By default these irqs will then be collected. For a more
  detailed description see B<IgnoreSelected> below.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> I<true>|I<false>
  
  If no configuration if given, the B<irq>-plugin will collect data from all
@@@ -3624,47 -3335,6 +3637,47 @@@ TCP-Port to connect to. Defaults to B<4
  
  =back
  
 +=head2 Plugin C<mcelog>
 +
 +The C<mcelog plugin> uses mcelog to retrieve machine check exceptions.
 +
 +By default the plugin connects to B<"/var/run/mcelog-client"> to check if the
 +mcelog server is running. When the server is running, the plugin will tail the
 +specified logfile to retrieve machine check exception information and send a
 +notification with the details from the logfile. The plugin will use the mcelog
 +client protocol to retrieve memory related machine check exceptions. Note that
 +for memory exceptions, notifications are only sent when there is a change in
 +the number of corrected/uncorrected memory errors.
 +
 +=head3 The Memory block
 +
 +Note: these options cannot be used in conjunction with the logfile options, they are mutually
 +exclusive.
 +
 +=over 3
 +
 +=item B<McelogClientSocket> I<Path>
 +Connect to the mcelog client socket using the UNIX domain socket at I<Path>.
 +Defaults to B<"/var/run/mcelog-client">.
 +
 +=item B<PersistentNotification> B<true>|B<false>
 +Override default configuration to only send notifications when sent when there
 +is a change in the number of corrected/uncorrected memory errors. When set to
 +true notifications will be sent for every read cycle. Default is false. Does
 +not affect the stats being dispatched.
 +
 +=back
 +
 +=over 4
 +
 +=item B<McelogLogfile> I<Path>
 +
 +The mcelog file to parse. Defaults to B<"/var/log/mcelog">. Note: this option
 +cannot be used in conjunction with the memory block options, they are mutually
 +exclusive.
 +
 +=back
 +
  =head2 Plugin C<md>
  
  The C<md plugin> collects information from Linux Software-RAID devices (md).
@@@ -3681,8 -3351,6 +3694,8 @@@ Select md devices based on device name
  the device, i.e. the name of the block device without the leading C</dev/>.
  See B<IgnoreSelected> for more details.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> B<true>|B<false>
  
  Invert device selection: If set to B<true>, all md devices B<except> those
@@@ -3709,7 -3377,6 +3722,7 @@@ Synopsis of the configuration
     <Page "plugin_instance">
       Server "localhost"
       Key "page_key"
 +     Plugin "plugin_name"
       <Match>
         Regex "(\\d+) bytes sent"
         DSType CounterAdd
@@@ -3737,11 -3404,6 +3750,11 @@@ B<Page> block
  
  When connected to the memcached server, asks for the page I<Key>.
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting values.
 +Defaults to C<memcachec>.
 +
  =item E<lt>B<Match>E<gt>
  
  Match blocks define which strings to look for and how matches substrings are
@@@ -4247,18 -3909,18 +4260,18 @@@ the B<collectd> branch
  Path to the PEM-encoded CA certificate file. Setting this option enables TLS
  communication with the MQTT broker, and as such, B<Port> should be the TLS-enabled
  port of the MQTT broker.
 -A valid TLS configuration requires B<CACert>, B<CertificateFile> and B<CertificateKeyFile>.
 +This option enables the use of TLS.
  
  =item B<CertificateFile> I<file>
  
  Path to the PEM-encoded certificate file to use as client certificate when
  connecting to the MQTT broker.
 -A valid TLS configuration requires B<CACert>, B<CertificateFile> and B<CertificateKeyFile>.
 +Only valid if B<CACert> and B<CertificateKeyFile> are also set.
  
  =item B<CertificateKeyFile> I<file>
  
  Path to the unencrypted PEM-encoded key file corresponding to B<CertificateFile>.
 -A valid TLS configuration requires B<CACert>, B<CertificateFile> and B<CertificateKeyFile>.
 +Only valid if B<CACert> and B<CertificateFile> are also set.
  
  =item B<TLSProtocol> I<protocol>
  
@@@ -4266,14 -3928,13 +4279,14 @@@ If configured, this specifies the strin
  C<tlsv1.2>) to use for the TLS connection to the broker. If not set a default
  version is used which depends on the version of OpenSSL the Mosquitto library
  was linked against.
 +Only valid if B<CACert> is set.
  
  =item B<CipherSuite> I<ciphersuite>
  
  A string describing the ciphers available for use. See L<ciphers(1)> and the
  C<openssl ciphers> utility for more information. If unset, the default ciphers
  will be used.
 -
 +Only valid if B<CACert> is set.
  
  =back
  
@@@ -4403,11 -4064,11 +4416,11 @@@ If enabled, the plugin sends a notifica
  or SQL threads are not running. Defaults to B<false>.
  
  =item B<WsrepStats> I<true|false>
 - 
 +
   Enable the collection of wsrep plugin statistics, used in Master-Master
   replication setups like in MySQL Galera/Percona XtraDB Cluster.
   User needs only privileges to execute 'SHOW GLOBAL STATUS'
 - 
 +
  =item B<ConnectTimeout> I<Seconds>
  
  Sets the connect timeout for the MySQL client.
@@@ -4853,8 -4514,6 +4866,8 @@@ regular and exact matching are case sen
  If no volume was specified at all for either of the three options, that data
  will be collected for all available volumes.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelectedIO> B<true>|B<false>
  
  =item B<IgnoreSelectedOps> B<true>|B<false>
@@@ -5040,8 -4699,6 +5053,8 @@@ Here are some examples to help you unde
      Filter "ppp0" "u32-1:0"
    </Plugin>
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected>
  
  The behavior is the same as with all other similar plugins: If nothing is
@@@ -5234,32 -4891,13 +5247,32 @@@ so the values will not loop
  =item B<ReportStats> B<true>|B<false>
  
  The network plugin cannot only receive and send statistics, it can also create
 -statistics about itself. Collected data included the number of received and
 +statistics about itself. Collectd data included the number of received and
  sent octets and packets, the length of the receive queue and the number of
  values handled. When set to B<true>, the I<Network plugin> will make these
  statistics available. Defaults to B<false>.
  
  =back
  
 +=head2 Plugin C<nfs>
 +
 +The I<nfs plugin> collects information about the usage of the Network File
 +System (NFS). It counts the number of procedure calls for each procedure,
 +grouped by version and whether the system runs as server or client.
 +
 +It is possibly to omit metrics for a specific NFS version by setting one or
 +more of the following options to B<false> (all of them default to B<true>).
 +
 +=over 4
 +
 +=item B<ReportV2> B<true>|B<false>
 +
 +=item B<ReportV3> B<true>|B<false>
 +
 +=item B<ReportV4> B<true>|B<false>
 +
 +=back
 +
  =head2 Plugin C<nginx>
  
  This plugin collects the number of connections and requests handled by the
@@@ -5461,40 -5099,6 +5474,40 @@@ making it through
  Add a UPS to collect data from. The format is identical to the one accepted by
  L<upsc(8)>.
  
 +=item B<ForceSSL> B<true>|B<false>
 +
 +Stops connections from falling back to unsecured if an SSL connection
 +cannot be established. Defaults to false if undeclared.
 +
 +=item B<VerifyPeer> I<true>|I<false>
 +
 +If set to true, requires a CAPath be provided. Will use the CAPath to find
 +certificates to use as Trusted Certificates to validate a upsd server certificate.
 +If validation of the upsd server certificate fails, the connection will not be
 +established. If ForceSSL is undeclared or set to false, setting VerifyPeer to true
 +will override and set ForceSSL to true.
 +
 +=item B<CAPath> I/path/to/certs/folder
 +
 +If VerifyPeer is set to true, this is required. Otherwise this is ignored.
 +The folder pointed at must contain certificate(s) named according to their hash.
 +Ex: XXXXXXXX.Y where X is the hash value of a cert and Y is 0. If name collisions
 +occur because two different certs have the same hash value, Y can be  incremented
 +in order to avoid conflict. To create a symbolic link to a certificate the following
 +command can be used from within the directory where the cert resides:
 +
 +C<ln -s some.crt ./$(openssl x509 -hash -noout -in some.crt).0>
 +
 +Alternatively, the package openssl-perl provides a command C<c_rehash> that will
 +generate links like the one described above for ALL certs in a given folder.
 +Example usage:
 +C<c_rehash /path/to/certs/folder>
 +
 +=item B<ConnectTimeout> I<Milliseconds>
 +
 +The B<ConnectTimeout> option sets the connect timeout, in milliseconds.
 +By default, the configured B<Interval> is used to set the timeout.
 +
  =back
  
  =head2 Plugin C<olsrd>
@@@ -5617,8 -5221,6 +5630,8 @@@ C</10.F10FCA000800/temperature>). B<Ign
  As there can be multiple devices on the bus you can list multiple sensor (use
  multiple B<Sensor> elements).
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> I<true>|I<false>
  
  If no configuration is given, the B<onewire> plugin will collect data from all
@@@ -5730,12 -5332,15 +5743,12 @@@ The OpenVPN plugin reads a status file 
  traffic statistics about connected clients.
  
  To set up OpenVPN to write to the status file periodically, use the
 -B<--status> option of OpenVPN. Since OpenVPN can write two different formats,
 -you need to set the required format, too. This is done by setting
 -B<--status-version> to B<2>.
 +B<--status> option of OpenVPN.
  
  So, in a nutshell you need:
  
    openvpn $OTHER_OPTIONS \
 -    --status "/var/run/openvpn-status" 10 \
 -    --status-version 2
 +    --status "/var/run/openvpn-status" 10
  
  Available options:
  
@@@ -5790,7 -5395,6 +5803,7 @@@ plugin's documentation above for detail
        </Result>
      </Query>
      <Database "product_information">
 +      #Plugin "warehouse"
        ConnectID "db01"
        Username "oracle"
        Password "secret"
@@@ -5813,11 -5417,6 +5826,11 @@@ values submitted to the daemon. Other t
  
  =over 4
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting query results from
 +this B<Database>. Defaults to C<oracle>.
 +
  =item B<ConnectID> I<ID>
  
  Defines the "database alias" or "service name" to connect to. Usually, these
@@@ -5845,123 -5444,6 +5858,123 @@@ refer to them from
  
  =back
  
 +=head2 Plugin C<ovs_events>
 +
 +The I<ovs_events> plugin monitors the link status of I<Open vSwitch> (OVS)
 +connected interfaces, dispatches the values to collectd and sends the
 +notification whenever the link state change occurs. This plugin uses OVS
 +database to get a link state change notification.
 +
 +B<Synopsis:>
 +
 + <Plugin "ovs_events">
 +   Port 6640
 +   Address "127.0.0.1"
 +   Socket "/var/run/openvswitch/db.sock"
 +   Interfaces "br0" "veth0"
 +   SendNotification true
 +   DispatchValues false
 + </Plugin>
 +
 +The plugin provides the following configuration options:
 +
 +=over 4
 +
 +=item B<Address> I<node>
 +
 +The address of the OVS DB server JSON-RPC interface used by the plugin. To
 +enable the interface, OVS DB daemon should be running with C<--remote=ptcp:>
 +option. See L<ovsdb-server(1)> for more details. The option may be either
 +network hostname, IPv4 numbers-and-dots notation or IPv6 hexadecimal string
 +format. Defaults to C<localhost>.
 +
 +=item B<Port> I<service>
 +
 +TCP-port to connect to. Either a service name or a port number may be given.
 +Defaults to B<6640>.
 +
 +=item B<Socket> I<path>
 +
 +The UNIX domain socket path of OVS DB server JSON-RPC interface used by the
 +plugin. To enable the interface, the OVS DB daemon should be running with
 +C<--remote=punix:> option. See L<ovsdb-server(1)> for more details. If this
 +option is set, B<Address> and B<Port> options are ignored.
 +
 +=item B<Interfaces> [I<ifname> ...]
 +
 +List of interface names to be monitored by this plugin. If this option is not
 +specified or is empty then all OVS connected interfaces on all bridges are
 +monitored.
 +
 +Default: empty (all interfaces on all bridges are monitored)
 +
 +=item B<SendNotification> I<true|false>
 +
 +If set to true, OVS link notifications (interface status and OVS DB connection
 +terminate) are sent to collectd. Default value is true.
 +
 +=item B<DispatchValues> I<true|false>
 +
 +Dispatch the OVS DB interface link status value with configured plugin interval.
 +Defaults to false. Please note, if B<SendNotification> and B<DispatchValues>
 +options are false, no OVS information will be provided by the plugin.
 +
 +=back
 +
 +B<Note:> By default, the global interval setting is used within which to
 +retrieve the OVS link status. To configure a plugin-specific interval, please
 +use B<Interval> option of the OVS B<LoadPlugin> block settings. For milliseconds
 +simple divide the time by 1000 for example if the desired interval is 50ms, set
 +interval to 0.05.
 +
 +=head2 Plugin C<ovs_stats>
 +
 +The I<ovs_stats> plugin collects statistics of OVS connected interfaces.
 +This plugin uses OVSDB management protocol (RFC7047) monitor mechanism to get
 +statistics from OVSDB
 +
 +B<Synopsis:>
 +
 + <Plugin "ovs_stats">
 +   Port 6640
 +   Address "127.0.0.1"
 +   Socket "/var/run/openvswitch/db.sock"
 +   Bridges "br0" "br_ext"
 + </Plugin>
 +
 +The plugin provides the following configuration options:
 +
 +=over 4
 +
 +=item B<Address> I<node>
 +
 +The address of the OVS DB server JSON-RPC interface used by the plugin. To
 +enable the interface, OVS DB daemon should be running with C<--remote=ptcp:>
 +option. See L<ovsdb-server(1)> for more details. The option may be either
 +network hostname, IPv4 numbers-and-dots notation or IPv6 hexadecimal string
 +format. Defaults to C<localhost>.
 +
 +=item B<Port> I<service>
 +
 +TCP-port to connect to. Either a service name or a port number may be given.
 +Defaults to B<6640>.
 +
 +=item B<Socket> I<path>
 +
 +The UNIX domain socket path of OVS DB server JSON-RPC interface used by the
 +plugin. To enable the interface, the OVS DB daemon should be running with
 +C<--remote=punix:> option. See L<ovsdb-server(1)> for more details. If this
 +option is set, B<Address> and B<Port> options are ignored.
 +
 +=item B<Bridges> [I<brname> ...]
 +
 +List of OVS bridge names to be monitored by this plugin. If this option is
 +omitted or is empty then all OVS bridges will be monitored.
 +
 +Default: empty (monitor all bridges)
 +
 +=back
 +
  =head2 Plugin C<perl>
  
  This plugin embeds a Perl-interpreter into collectd and provides an interface
@@@ -6063,10 -5545,10 +6076,10 @@@ multiple hosts
  =item B<Interval> I<Seconds>
  
  Sets the interval in which to send ICMP echo packets to the configured hosts.
 -This is B<not> the interval in which statistics are queries from the plugin but
 -the interval in which the hosts are "pinged". Therefore, the setting here
 -should be smaller than or equal to the global B<Interval> setting. Fractional
 -times, such as "1.24" are allowed.
 +This is B<not> the interval in which metrics are read from the plugin but the
 +interval in which the hosts are "pinged". Therefore, the setting here should be
 +smaller than or equal to the global B<Interval> setting. Fractional times, such
 +as "1.24" are allowed.
  
  Default: B<1.0>
  
@@@ -6171,7 -5653,6 +6184,7 @@@ L<http://www.postgresql.org/docs/manual
      </Writer>
  
      <Database foo>
 +      Plugin "kingdom"
        Host "hostname"
        Port "5432"
        User "username"
@@@ -6493,11 -5974,6 +6506,11 @@@ activating this option. The draw-back i
  amount of time will be lost, for example, if a single statement within the
  transaction fails or if the database server crashes.
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting query results from
 +this B<Database>. Defaults to C<postgresql>.
 +
  =item B<Instance> I<name>
  
  Specify the plugin instance name that should be used instead of the database
@@@ -6756,16 -6232,9 +6769,16 @@@ C<I<prefix>/var/run/collectd-powerdns>
  =item B<Process> I<Name>
  
  Select more detailed statistics of processes matching this name. The statistics
 -collected for these selected processes are size of the resident segment size
 -(RSS), user- and system-time used, number of processes and number of threads,
 -io data (where available) and minor and major pagefaults.
 +collected for these selected processes are:
 + - size of the resident segment size (RSS)
 + - user- and system-time used
 + - number of processes
 + - number of threads
 + - number of open files (under Linux)
 + - number of memory mapped files (under Linux)
 + - io data (where available)
 + - context switches (under Linux)
 + - minor and major pagefaults.
  
  Some platforms have a limit on the length of process names. I<Name> must stay
  below this limit.
@@@ -6783,12 -6252,6 +6796,12 @@@ slashes
  
  Collect context switch of the process.
  
 +=item B<CollectMemoryMaps> I<Boolean>
 +
 +Collect the number of memory mapped files of the process.
 +The limit for this number is configured via F</proc/sys/vm/max_map_count> in
 +the Linux kernel.
 +
  =back
  
  =head2 Plugin C<protocols>
@@@ -6817,8 -6280,6 +6830,8 @@@ Whether only matched values are selecte
  depends on the B<IgnoreSelected>. By default, only matched values are selected.
  If no value is configured at all, all values will be selected.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> B<true>|B<false>
  
  If set to B<true>, inverts the selection made by B<Value>, i.E<nbsp>e. all
@@@ -7172,20 -6633,14 +7185,20 @@@ one (exclusive)
  
  When the C<rrdtool> plugin uses a cache (by setting B<CacheTimeout>, see below)
  it writes all values for a certain RRD-file if the oldest value is older than
 -(or equal to) the number of seconds specified. If some RRD-file is not updated
 +(or equal to) the number of seconds specified by B<CacheTimeout>.
 +That check happens on new values arriwal. If some RRD-file is not updated
  anymore for some reason (the computer was shut down, the network is broken,
 -etc.) some values may still be in the cache. If B<CacheFlush> is set, then the
 -entire cache is searched for entries older than B<CacheTimeout> seconds and
 -written to disk every I<Seconds> seconds. Since this is kind of expensive and
 -does nothing under normal circumstances, this value should not be too small.
 -900 seconds might be a good value, though setting this to 7200 seconds doesn't
 -normally do much harm either.
 +etc.) some values may still be in the cache. If B<CacheFlush> is set, then
 +every I<Seconds> seconds the entire cache is searched for entries older than
 +B<CacheTimeout> + B<RandomTimeout> seconds. The entries found are written to
 +disk. Since scanning the entire cache is kind of expensive and does nothing
 +under normal circumstances, this value should not be too small. 900 seconds
 +might be a good value, though setting this to 7200 seconds doesn't normally
 +do much harm either.
 +
 +Defaults to 10x B<CacheTimeout>.
 +B<CacheFlush> must be larger than or equal to B<CacheTimeout>, otherwise the
 +above default is used.
  
  =item B<CacheTimeout> I<Seconds>
  
@@@ -7253,8 -6708,6 +7266,8 @@@ on the B<IgnoreSelected> below. For exa
  I<it8712-isa-0290/voltage-in1>" will cause collectd to gather data for the
  voltage sensor I<in1> of the I<it8712> on the isa bus at the address 0290.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> I<true>|I<false>
  
  If no configuration if given, the B<sensors>-plugin will collect data from all
@@@ -7364,8 -6817,6 +7377,8 @@@ is interpreted as a regular expression
    Disk "sdd"
    Disk "/hda[34]/"
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> B<true>|B<false>
  
  Sets whether selected disks, i.E<nbsp>e. the ones matches by any of the B<Disk>
@@@ -7399,122 -6850,6 +7412,122 @@@ Since the configuration of the C<snmp p
  other plugins, its documentation has been moved to an own manpage,
  L<collectd-snmp(5)>. Please see there for details.
  
 +=head2 Plugin C<snmp_agent>
 +
 +The I<snmp_agent> plugin is an AgentX subagent that receives and handles queries
 +from SNMP master agent and returns the data collected by read plugins.
 +The I<snmp_agent> plugin handles requests only for OIDs specified in
 +configuration file. To handle SNMP queries the plugin gets data from collectd
 +and translates requested values from collectd's internal format to SNMP format.
 +This plugin is a generic plugin and cannot work without configuration.
 +For more details on AgentX subagent see
 +<http://www.net-snmp.org/tutorial/tutorial-5/toolkit/demon/>
 +
 +B<Synopsis:>
 +
 +  <Plugin snmp_agent>
 +    <Data "memAvailReal">
 +      Plugin "memory"
 +      #PluginInstance "some"
 +      Type "memory"
 +      TypeInstance "free"
 +      OIDs "1.3.6.1.4.1.2021.4.6.0"
 +    </Data>
 +    <Table "ifTable">
 +      IndexOID "IF-MIB::ifIndex"
 +      SizeOID "IF-MIB::ifNumber"
 +      <Data "ifDescr">
 +        Instance true
 +        Plugin "interface"
 +        OIDs "IF-MIB::ifDescr"
 +      </Data>
 +      <Data "ifOctets">
 +        Plugin "interface"
 +        Type "if_octets"
 +        TypeInstance ""
 +        OIDs "IF-MIB::ifInOctets" "IF-MIB::ifOutOctets"
 +      </Data>
 +    </Table>
 +  </Plugin>
 +
 +There are two types of blocks that can be contained in the
 +C<E<lt>PluginE<nbsp> snmp_agentE<gt>> block: B<Data> and B<Table>:
 +
 +=head3 The B<Data> block
 +
 +The B<Data> block defines a list OIDs that are to be handled. This block can
 +define scalar or table OIDs. If B<Data> block is defined inside of B<Table>
 +block it reperesents table OIDs.
 +The following options can be set:
 +
 +=over 4
 +
 +=item B<Instance> I<true|false>
 +
 +When B<Instance> is set to B<true>, the value for requested OID is copied from
 +plugin instance field of corresponding collectd value. If B<Data> block defines
 +scalar data type B<Instance> has no effect and can be omitted.
 +
 +=item B<Plugin> I<String>
 +
 +Read plugin name whose collected data will be mapped to specified OIDs.
 +
 +=item B<PluginInstance> I<String>
 +
 +Read plugin instance whose collected data will be mapped to specified OIDs.
 +The field is optional and by default there is no plugin instance check.
 +Allowed only if B<Data> block defines scalar data type.
 +
 +=item B<Type> I<String>
 +
 +Collectd's type that is to be used for specified OID, e.E<nbsp>g. "if_octets"
 +for example. The types are read from the B<TypesDB> (see L<collectd.conf(5)>).
 +
 +=item B<TypeInstance> I<String>
 +
 +Collectd's type-instance that is to be used for specified OID.
 +
 +=item B<OIDs> I<OID> [I<OID> ...]
 +
 +Configures the OIDs to be handled by I<snmp_agent> plugin. Values for these OIDs
 +are taken from collectd data type specified by B<Plugin>, B<PluginInstance>,
 +B<Type>, B<TypeInstance> fields of this B<Data> block. Number of the OIDs
 +configured should correspond to number of values in specified B<Type>.
 +For example two OIDs "IF-MIB::ifInOctets" "IF-MIB::ifOutOctets" can be mapped to
 +"rx" and "tx" values of "if_octets" type.
 +
 +=item B<Scale> I<Value>
 +
 +The values taken from collectd are multiplied by I<Value>. The field is optional
 +and the default is B<1.0>.
 +
 +=item B<Shift> I<Value>
 +
 +I<Value> is added to values from collectd after they have been multiplied by
 +B<Scale> value. The field is optional and the default value is B<0.0>.
 +
 +=back
 +
 +=head3 The B<Table> block
 +
 +The B<Table> block defines a collection of B<Data> blocks that belong to one
 +snmp table. In addition to multiple B<Data> blocks the following options can be
 +set:
 +
 +=over 4
 +
 +=item B<IndexOID> I<OID>
 +
 +OID that is handled by the plugin and is mapped to numerical index value that is
 +generated by the plugin for each table record.
 +
 +=item B<SizeOID> I<OID>
 +
 +OID that is handled by the plugin. Returned value is the number of records in
 +the table. The field is optional.
 +
 +=back
 +
  =head2 Plugin C<statsd>
  
  The I<statsd plugin> listens to a UDP socket, reads "events" in the statsd
@@@ -7618,13 -6953,6 +7631,13 @@@ available and free. Defaults to B<false
  This is useful for deploying I<collectd> in a heterogeneous environment, where
  swap sizes differ and you want to specify generic thresholds or similar.
  
 +=item B<ReportIO> B<true>|B<false>
 +
 +Enables or disables reporting swap IO. Defaults to B<true>.
 +
 +This is useful for the cases when swap IO is not neccessary, is not available,
 +or is not reliable.
 +
  =back
  
  =head2 Plugin C<syslog>
@@@ -7660,7 -6988,6 +7673,7 @@@ filesystem or CSV (comma separated valu
  
    <Plugin table>
      <Table "/proc/slabinfo">
 +      #Plugin "slab"
        Instance "slabinfo"
        Separator " "
        <Result>
@@@ -7687,14 -7014,10 +7700,14 @@@ The following options are available ins
  
  =over 4
  
 +=item B<Plugin> I<Plugin>
 +
 +If specified, I<Plugin> is used as the plugin name when submitting values.
 +Defaults to B<table>.
 +
  =item B<Instance> I<instance>
  
 -If specified, I<instance> is used as the plugin instance. So, in the above
 -example, the plugin name C<table-slabinfo> would be used. If omitted, the
 +If specified, I<instance> is used as the plugin instance. If omitted, the
  filename of the table is used instead, with all special characters replaced
  with an underscore (C<_>).
  
@@@ -7764,7 -7087,6 +7777,7 @@@ user using (extended) regular expressio
  
    <Plugin "tail">
      <File "/var/log/exim4/mainlog">
 +      Plugin "mail"
        Instance "exim"
        Interval 60
        <Match>
          <DSType "Distribution">
            Percentile 99
            Bucket 0 100
 +          #BucketType "bucket"
          </DSType>
          Type "latency"
          Instance "foo"
@@@ -7797,13 -7118,11 +7810,13 @@@ The config consists of one or more B<Fi
  logfile to parse. Within each B<File> block, there are one or more B<Match>
  blocks, which configure a regular expression to search for.
  
 -The B<Instance> option in the B<File> block may be used to set the plugin
 -instance. So in the above example the plugin name C<tail-foo> would be used.
 -This plugin instance is for all B<Match> blocks that B<follow> it, until the
 -next B<Instance> option. This way you can extract several plugin instances from
 -one logfile, handy when parsing syslog and the like.
 +The B<Plugin> and B<Instance> options in the B<File> block may be used to set
 +the plugin name and instance respectively. So in the above example the plugin name
 +C<mail-exim> would be used.
 +
 +These options are applied for all B<Match> blocks that B<follow> it, until the
 +next B<Plugin> or B<Instance> option. This way you can extract several plugin
 +instances from one logfile, handy when parsing syslog and the like.
  
  The B<Interval> option allows you to define the length of time between reads. If
  this is not set, the default Interval will be used.
@@@ -7907,7 -7226,6 +7920,7 @@@ B<Synopsis:
    <DSType "Distribution">
      Percentile 99
      Bucket 0 100
 +    BucketType "bucket"
    </DSType>
  
  =over 4
@@@ -7944,17 -7262,11 +7957,17 @@@ the following schema
    Bucket  20  50
    Bucket  50   0
  
 -Metrics are reported with the I<type> C<bucket> and the I<type instance>
 +Metrics are reported with the I<type> set by B<BucketType> option (C<bucket> 
 +by default) and the I<type instance>
  C<E<lt>TypeE<gt>[-E<lt>InstanceE<gt>]-E<lt>lower_boundE<gt>_E<lt>upper_boundE<gt>>.
  
  This option may be repeated to calculate more than one rate.
  
 +=item B<BucketType> I<Type>
 +
 +Sets the type used to dispatch B<Bucket> metrics.
 +Optional, by default C<bucket> will be used.
 +
  =back
  
  =back
@@@ -7991,8 -7303,7 +8004,8 @@@ B<Synopsis:
         Index 1
     </Metric>
     <File "/var/log/snort/snort.stats">
 -       Instance "snort-eth0"
 +       Plugin "snortstats"
 +       Instance "eth0"
         Interval 600
         Collect "snort-dropped"
     </File>
@@@ -8044,11 -7355,6 +8057,11 @@@ I<File> block but there can be multipl
  
  =over 4
  
 +=item B<Plugin> I<Plugin>
 +
 +Use I<Plugin> as the plugin name when submitting values.
 +Defaults to C<tail_csv>.
 +
  =item B<Instance> I<PluginInstance>
  
  Sets the I<plugin instance> used when dispatching the values.
@@@ -8198,8 -7504,6 +8211,8 @@@ Selects the name of the thermal device 
  depending on the value of the B<IgnoreSelected> option. This option may be
  used multiple times to specify a list of devices.
  
 +See F</"IGNORELISTS"> for details.
 +
  =item B<IgnoreSelected> I<true>|I<false>
  
  Invert the selection: If set to true, all devices B<except> the ones that
@@@ -8312,9 -7616,9 +8325,9 @@@ collections. The different bits of thi
  
  Boolean enabling the use of logical core numbering for per core statistics.
  When enabled, C<cpuE<lt>nE<gt>> is used as plugin instance, where I<n> is a
 -sequential number assigned by the kernel. Otherwise, C<coreE<lt>nE<gt>> is used
 -where I<n> is the n-th core of the socket, causing name conflicts when there is
 -more than one socket.
 +dynamic number assigned by the kernel. Otherwise, C<coreE<lt>nE<gt>> is used
 +if there is only one package and C<pkgE<lt>nE<gt>-coreE<lt>mE<gt>> if there is
 +more than one, where I<n> is the n-th core of package I<m>.
  
  =back
  
@@@ -8420,11 -7724,6 +8433,11 @@@ Synopsis
       CollectVCL         false
       CollectVSM         false
       CollectWorkers     false
 +     CollectLock        false
 +     CollectMempool     false
 +     CollectManagement  false
 +     CollectSMF         false
 +     CollectVBE         false
     </Instance>
   </Plugin>
  
@@@ -8500,10 -7799,7 +8513,10 @@@ log messages which is flushed to disk w
  =item B<CollectSMA> B<true>|B<false>
  
  malloc or umem (umem_alloc(3MALLOC) based) storage statistics. The umem storage
 -component is Solaris specific. Only available with Varnish 2.x. False by
 +component is Solaris specific.
 +Note: SMA and SMF share counters, enable only the one used by the Varnish
 +instance.
 +Only available with Varnish 2.x. False by
  default.
  
  =item B<CollectSMS> B<true>|B<false>
@@@ -8513,8 -7809,7 +8526,8 @@@ component is used internally only. Fals
  
  =item B<CollectSM> B<true>|B<false>
  
 -file (memory mapped file) storage statistics. Only available with Varnish 2.x.
 +file (memory mapped file) storage statistics. Only available with Varnish 2.x.,
 +in varnish 4.x. use CollectSMF.
  False by default.
  
  =item B<CollectStruct> B<true>|B<false>
@@@ -8545,38 -7840,15 +8558,38 @@@ statistics subsystems). Only available 
  
  Collect statistics about worker threads. False by default.
  
 +=item B<CollectVBE> B<true>|B<false>
 +
 +Backend counters. Only available with Varnish 4.x. False by default.
 +
 +=item B<CollectSMF> B<true>|B<false>
 +
 +file (memory mapped file) storage statistics. Only available with Varnish 4.x.
 +Note: SMA and SMF share counters, enable only the one used by the Varnish
 +instance.
 +Used to be called SM in Varnish 2.x. False by default.
 +
 +=item B<CollectManagement> B<true>|B<false>
 +
 +Management process counters. Only available with Varnish 4.x. False by default.
 +
 +=item B<CollectLock> B<true>|B<false>
 +
 +Lock counters. Only available with Varnish 4.x. False by default.
 +
 +=item B<CollectMempool> B<true>|B<false>
 +
 +Memory pool counters. Only available with Varnish 4.x. False by default.
 +
  =back
  
  =head2 Plugin C<virt>
  
 -This plugin allows CPU, disk and network load to be collected for virtualized
 -guests on the machine. This means that these metrics can be collected for guest
 -systems without installing any software on them - I<collectd> only runs on the
 -host system. The statistics are collected through libvirt
 -(L<http://libvirt.org/>).
 +This plugin allows CPU, disk, network load and other metrics to be collected for
 +virtualized guests on the machine. The statistics are collected through libvirt
 +API (L<http://libvirt.org/>). Majority of metrics can be gathered without
 +installing any additional software on guests, especially I<collectd>, which runs
 +only on the host system.
  
  Only I<Connection> is required.
  
@@@ -8632,7 -7904,7 +8645,7 @@@ will be collected
  =item B<BlockDeviceFormat> B<target>|B<source>
  
  If I<BlockDeviceFormat> is set to B<target>, the default, then the device name
 -seen by the guest will be used for reporting metrics. 
 +seen by the guest will be used for reporting metrics.
  This corresponds to the C<E<lt>targetE<gt>> node in the XML definition of the
  domain.
  
@@@ -8720,55 -7992,6 +8733,55 @@@ How many read instances you want to us
  and the sensible setting is a multiple of the B<ReadThreads> value.
  If you are not sure, just use the default setting.
  
 +=item B<ExtraStats> B<string>
 +
 +Report additional extra statistics. The default is no extra statistics, preserving
 +the previous behaviour of the plugin. If unsure, leave the default. If enabled,
 +allows the plugin to reported more detailed statistics about the behaviour of
 +Virtual Machines. The argument is a space-separated list of selectors.
 +
 +Currently supported selectors are:
 +
 +=over 4
 +
 +=item B<cpu_util>: report CPU utilization per domain in percentage.
 +
 +=item B<disk>: report extra statistics like number of flush operations and total
 +service time for read, write and flush operations. Requires libvirt API version
 +I<0.9.5> or later.
 +
 +=item B<disk_err>: report disk errors if any occured. Requires libvirt API version
 +I<0.9.10> or later.
 +
 +=item B<domain_state>: report domain state and reason in human-readable format as
 +a notification. If libvirt API version I<0.9.2> or later is available, domain
 +reason will be included in notification.
 +
 +=item B<fs_info>: report file system information as a notification. Requires
 +libvirt API version I<1.2.11> or later. Can be collected only if I<Guest Agent>
 +is installed and configured inside VM. Make sure that installed I<Guest Agent>
 +version supports retrieving  file system information.
 +
 +=item B<job_stats_background>: report statistics about progress of a background
 +job on a domain. Only one type of job statistics can be collected at the same time.
 +Requires libvirt API version I<1.2.9> or later.
 +
 +=item B<job_stats_completed>: report statistics about a recently completed job on
 +a domain. Only one type of job statistics can be collected at the same time.
 +Requires libvirt API version I<1.2.9> or later.
 +
 +=item B<pcpu>: report the physical user/system cpu time consumed by the hypervisor, per-vm.
 +Requires libvirt API version I<0.9.11> or later.
 +
 +=item B<perf>: report performance monitoring events. To collect performance
 +metrics they must be enabled for domain and supported by the platform. Requires
 +libvirt API version I<1.3.3> or later.
 +B<Note>: I<perf> metrics can't be collected if I<intel_rdt> plugin is enabled.
 +
 +=item B<vcpupin>: report pinning of domain VCPUs to host physical CPUs.
 +
 +=back
 +
  =back
  
  =head2 Plugin C<vmem>
@@@ -8939,8 -8162,6 +8952,8 @@@ packets
  Synopsis:
  
   <Plugin write_tsdb>
 +   ResolveInterval 60
 +   ResolveJitter 60
     <Node "example">
       Host "tsd-1.my.domain"
       Port "4242"
   </Plugin>
  
  The configuration consists of one or more E<lt>B<Node>E<nbsp>I<Name>E<gt>
 -blocks. Inside the B<Node> blocks, the following options are recognized:
 +blocks and global directives.
 +
 +Global directives are:
 +
 +=over 4
 +
 +=item B<ResolveInterval> I<seconds>
 +
 +=item B<ResolveJitter> I<seconds>
 +
 +When I<collectd> connects to a TSDB node, it will request the hostname from
 +DNS. This can become a problem if the TSDB node is unavailable or badly
 +configured because collectd will request DNS in order to reconnect for every
 +metric, which can flood your DNS. So you can cache the last value for
 +I<ResolveInterval> seconds.
 +Defaults to the I<Interval> of the I<write_tsdb plugin>, e.g. 10E<nbsp>seconds.
 +
 +You can also define a jitter, a random interval to wait in addition to
 +I<ResolveInterval>. This prevents all your collectd servers to resolve the
 +hostname at the same time when the connection fails.
 +Defaults to the I<Interval> of the I<write_tsdb plugin>, e.g. 10E<nbsp>seconds.
 +
 +B<Note:> If the DNS resolution has already been successful when the socket
 +closes, the plugin will try to reconnect immediately with the cached
 +information. DNS is queried only when the socket is closed for a longer than
 +I<ResolveInterval> + I<ResolveJitter> seconds.
 +
 +=back
 +
 +Inside the B<Node> blocks, the following options are recognized:
  
  =over 4
  
@@@ -9195,23 -8387,6 +9208,23 @@@ create output in the I<JavaScript Objec
  
  Defaults to B<Command>.
  
 +=item B<Attribute> I<String> I<String>
 +
 +Only available for the KAIROSDB output format.
 +
 +Consider the two given strings to be the key and value of an additional tag for
 +each metric being sent out.
 +
 +You can add multiple B<Attribute>.
 +
 +=item B<TTL> I<Int>
 +
 +Only available for the KAIROSDB output format.
 +
 +Sets the Cassandra ttl for the data points.
 +
 +Please refer to L<http://kairosdb.github.io/docs/build/html/restapi/AddDataPoints.html?highlight=ttl>
 +
  =item B<Metrics> B<true>|B<false>
  
  Controls whether I<metrics> are POSTed to this location. Defaults to B<true>.
@@@ -9393,7 -8568,6 +9406,7 @@@ Synopsis
          Prefix "collectd/"
          Database 1
          MaxSetSize -1
 +        MaxSetDuration -1
          StoreRates true
      </Node>
    </Plugin>
@@@ -9456,12 -8630,6 +9469,12 @@@ to C<0>
  The B<MaxSetSize> option limits the number of items that the I<Sorted Sets> can
  hold. Negative values for I<Items> sets no limit, which is the default behavior.
  
 +=item B<MaxSetDuration> I<Seconds>
 +
 +The B<MaxSetDuration> option limits the duration of items that the
 +I<Sorted Sets> can hold. Negative values for I<Items> sets no duration, which
 +is the default behavior.
 +
  =item B<StoreRates> B<true>|B<false>
  
  If set to B<true> (the default), convert counter values to rates. If set to
@@@ -10706,48 -9874,6 +10719,48 @@@ be an FQDN
     Target "write"
   </Chain>
  
 +=head1 IGNORELISTS
 +
 +B<Ignorelists> are a generic framework to either ignore some metrics or report
 +specific metircs only. Plugins usually provide one or more options to specify
 +the items (mounts points, devices, ...) and the boolean option
 +C<IgnoreSelected>.
 +
 +=over 4
 +
 +=item B<Select> I<String>
 +
 +Selects the item I<String>. This option often has a plugin specific name, e.g.
 +B<Sensor> in the C<sensors> plugin. It is also plugin specific what this string
 +is compared to. For example, the C<df> plugin's B<MountPoint> compares it to a
 +mount point and the C<sensors> plugin's B<Sensor> compares it to a sensor name.
 +
 +By default, this option is doing a case-sensitive full-string match. The
 +following config will match C<foo>, but not C<Foo>:
 +
 +  Select "foo"
 +
 +If I<String> starts and ends with C</> (a slash), the string is compiled as a
 +I<regular expression>. For example, so match all item starting with C<foo>, use
 +could use the following syntax:
 +
 +  Select "/^foo/"
 +
 +The regular expression is I<not> anchored, i.e. the following config will match
 +C<foobar>, C<barfoo> and C<AfooZ>:
 +
 +  Select "/foo/"
 +
 +The B<Select> option may be repeated to select multiple items.
 +
 +=item B<IgnoreSelected> B<true>|B<false>
 +
 +If set to B<true>, matching metrics are I<ignored> and all other metrics are
 +collected. If set to B<false>, matching metrics are I<collected> and all other
 +metrics are ignored.
 +
 +=back
 +
  =head1 SEE ALSO
  
  L<collectd(1)>,
diff --combined src/ipmi.c
@@@ -59,16 -59,22 +59,22 @@@ static int c_ipmi_init_in_progress = 0
  static int c_ipmi_active = 0;
  static pthread_t thread_id = (pthread_t)0;
  
- static const char *config_keys[] = {"Sensor", "IgnoreSelected",
-                                     "NotifySensorAdd", "NotifySensorRemove",
-                                     "NotifySensorNotPresent"};
+ static const char *config_keys[] = {"Sensor",
+                                     "IgnoreSelected",
+                                     "NotifySensorAdd",
+                                     "NotifySensorRemove",
+                                     "NotifySensorNotPresent",
+                                     "SELEnabled",
+                                     "SELClearEvent"};
  static int config_keys_num = STATIC_ARRAY_SIZE(config_keys);
  
  static ignorelist_t *ignorelist = NULL;
  
- static int c_ipmi_nofiy_add = 0;
- static int c_ipmi_nofiy_remove = 0;
- static int c_ipmi_nofiy_notpresent = 0;
+ static _Bool c_ipmi_notify_add = 0;
+ static _Bool c_ipmi_notify_remove = 0;
+ static _Bool c_ipmi_notify_notpresent = 0;
+ static _Bool c_ipmi_sel_enabled = 0;
+ static _Bool c_ipmi_sel_clear_event = 0;
  
  /*
   * Misc private functions
@@@ -83,7 -89,7 +89,7 @@@ static void c_ipmi_error(const char *fu
    }
  
    if (errbuf[0] == 0) {
 -    ssnprintf(errbuf, sizeof(errbuf), "Unknown error %#x", status);
 +    snprintf(errbuf, sizeof(errbuf), "Unknown error %#x", status);
    }
    errbuf[sizeof(errbuf) - 1] = 0;
  
@@@ -115,7 -121,7 +121,7 @@@ static void sensor_read_handler(ipmi_se
               "not present.",
               list_item->sensor_name);
  
-         if (c_ipmi_nofiy_notpresent) {
+         if (c_ipmi_notify_notpresent) {
            notification_t n = {
                NOTIF_WARNING, cdtime(), "", "", "ipmi", "", "", "", NULL};
  
            sstrncpy(n.type_instance, list_item->sensor_name,
                     sizeof(n.type_instance));
            sstrncpy(n.type, list_item->sensor_type, sizeof(n.type));
 -          ssnprintf(n.message, sizeof(n.message), "sensor %s not present",
 -                    list_item->sensor_name);
 +          snprintf(n.message, sizeof(n.message), "sensor %s not present",
 +                   list_item->sensor_name);
  
            plugin_dispatch_notification(&n);
          }
      INFO("ipmi plugin: sensor_read_handler: sensor %s present.",
           list_item->sensor_name);
  
-     if (c_ipmi_nofiy_notpresent) {
+     if (c_ipmi_notify_notpresent) {
        notification_t n = {NOTIF_OKAY, cdtime(), "", "",  "ipmi",
                            "",         "",       "", NULL};
  
        sstrncpy(n.type_instance, list_item->sensor_name,
                 sizeof(n.type_instance));
        sstrncpy(n.type, list_item->sensor_type, sizeof(n.type));
 -      ssnprintf(n.message, sizeof(n.message), "sensor %s present",
 -                list_item->sensor_name);
 +      snprintf(n.message, sizeof(n.message), "sensor %s present",
 +               list_item->sensor_name);
  
        plugin_dispatch_notification(&n);
      }
    plugin_dispatch_values(&vl);
  } /* void sensor_read_handler */
  
 -    ssnprintf(sensor_name, sizeof(sensor_name), "%s %s", temp,
 -              entity_id_string);
+ static void sensor_get_name(ipmi_sensor_t *sensor, char *buffer, int buf_len) {
+   char temp[DATA_MAX_NAME_LEN] = {0};
+   ipmi_entity_t *ent = ipmi_sensor_get_entity(sensor);
+   const char *entity_id_string = ipmi_entity_get_entity_id_string(ent);
+   char sensor_name[DATA_MAX_NAME_LEN] = "";
+   char *sensor_name_ptr;
+   if ((buffer == NULL) || (buf_len == 0))
+     return;
+   ipmi_sensor_get_name(sensor, temp, sizeof(temp));
+   temp[sizeof(temp) - 1] = 0;
+   if (entity_id_string != NULL && strlen(temp))
 -        ssnprintf(sensor_name, sizeof(sensor_name), "%s %s", sensor_name_ptr,
 -                  sensor_id_ptr);
++    snprintf(sensor_name, sizeof(sensor_name), "%s %s", temp, entity_id_string);
+   else if (entity_id_string != NULL)
+     sstrncpy(sensor_name, entity_id_string, sizeof(sensor_name));
+   else
+     sstrncpy(sensor_name, temp, sizeof(sensor_name));
+   if (strlen(temp)) {
+     sstrncpy(temp, sensor_name, sizeof(temp));
+     sensor_name_ptr = strstr(temp, ").");
+     if (sensor_name_ptr != NULL) {
+       /* If name is something like "foo (123).bar",
+        * change that to "bar (123)".
+        * Both, sensor_name_ptr and sensor_id_ptr point to memory within the
+        * `temp' array, which holds a copy of the current `sensor_name'. */
+       char *sensor_id_ptr;
+       /* `sensor_name_ptr' points to ").bar". */
+       sensor_name_ptr[1] = 0;
+       /* `temp' holds "foo (123)\0bar\0". */
+       sensor_name_ptr += 2;
+       /* `sensor_name_ptr' now points to "bar". */
+       sensor_id_ptr = strstr(temp, "(");
+       if (sensor_id_ptr != NULL) {
+         /* `sensor_id_ptr' now points to "(123)". */
++        snprintf(sensor_name, sizeof(sensor_name), "%s %s", sensor_name_ptr,
++                 sensor_id_ptr);
+       }
+       /* else: don't touch sensor_name. */
+     }
+   }
+   sstrncpy(buffer, sensor_name, buf_len);
+ }
  static int sensor_list_add(ipmi_sensor_t *sensor) {
    ipmi_sensor_id_t sensor_id;
    c_ipmi_sensor_list_t *list_item;
    c_ipmi_sensor_list_t *list_prev;
  
    char buffer[DATA_MAX_NAME_LEN] = {0};
-   const char *entity_id_string;
-   char sensor_name[DATA_MAX_NAME_LEN];
-   char *sensor_name_ptr;
+   char *sensor_name_ptr = buffer;
    int sensor_type;
    const char *type;
-   ipmi_entity_t *ent = ipmi_sensor_get_entity(sensor);
  
    sensor_id = ipmi_sensor_convert_to_id(sensor);
-   ipmi_sensor_get_name(sensor, buffer, sizeof(buffer));
-   buffer[sizeof(buffer) - 1] = 0;
-   entity_id_string = ipmi_entity_get_entity_id_string(ent);
-   if (entity_id_string == NULL)
-     sstrncpy(sensor_name, buffer, sizeof(sensor_name));
-   else
-     snprintf(sensor_name, sizeof(sensor_name), "%s %s", buffer,
-              entity_id_string);
-   sstrncpy(buffer, sensor_name, sizeof(buffer));
-   sensor_name_ptr = strstr(buffer, ").");
-   if (sensor_name_ptr != NULL) {
-     /* If name is something like "foo (123).bar",
-      * change that to "bar (123)".
-      * Both, sensor_name_ptr and sensor_id_ptr point to memory within the
-      * `buffer' array, which holds a copy of the current `sensor_name'. */
-     char *sensor_id_ptr;
-     /* `sensor_name_ptr' points to ").bar". */
-     sensor_name_ptr[1] = 0;
-     /* `buffer' holds "foo (123)\0bar\0". */
-     sensor_name_ptr += 2;
-     /* `sensor_name_ptr' now points to "bar". */
-     sensor_id_ptr = strstr(buffer, "(");
-     if (sensor_id_ptr != NULL) {
-       /* `sensor_id_ptr' now points to "(123)". */
-       snprintf(sensor_name, sizeof(sensor_name), "%s %s", sensor_name_ptr,
-                sensor_id_ptr);
-     }
-     /* else: don't touch sensor_name. */
-   }
-   sensor_name_ptr = sensor_name;
+   sensor_get_name(sensor, buffer, sizeof(buffer));
  
    /* Both `ignorelist' and `plugin_instance' may be NULL. */
    if (ignorelist_match(ignorelist, sensor_name_ptr) != 0)
 -    return (0);
 +    return 0;
  
    /* FIXME: Use rate unit or base unit to scale the value */
  
           "because I don't know how to handle its type (%#x, %s). "
           "If you need this sensor, please file a bug report.",
           sensor_name_ptr, sensor_type, sensor_type_str);
 -    return (-1);
 +    return -1;
    }
    } /* switch (sensor_type) */
  
  
    if (list_item != NULL) {
      pthread_mutex_unlock(&sensor_list_lock);
 -    return (0);
 +    return 0;
    }
  
    list_item = (c_ipmi_sensor_list_t *)calloc(1, sizeof(c_ipmi_sensor_list_t));
    if (list_item == NULL) {
      pthread_mutex_unlock(&sensor_list_lock);
 -    return (-1);
 +    return -1;
    }
  
    list_item->sensor_id = ipmi_sensor_convert_to_id(sensor);
  
    pthread_mutex_unlock(&sensor_list_lock);
  
-   if (c_ipmi_nofiy_add && (c_ipmi_init_in_progress == 0)) {
+   if (c_ipmi_notify_add && (c_ipmi_init_in_progress == 0)) {
      notification_t n = {NOTIF_OKAY, cdtime(), "", "", "ipmi", "", "", "", NULL};
  
      sstrncpy(n.host, hostname_g, sizeof(n.host));
      sstrncpy(n.type_instance, list_item->sensor_name, sizeof(n.type_instance));
      sstrncpy(n.type, list_item->sensor_type, sizeof(n.type));
 -    ssnprintf(n.message, sizeof(n.message), "sensor %s added",
 -              list_item->sensor_name);
 +    snprintf(n.message, sizeof(n.message), "sensor %s added",
 +             list_item->sensor_name);
  
      plugin_dispatch_notification(&n);
    }
  
 -  return (0);
 +  return 0;
  } /* int sensor_list_add */
  
  static int sensor_list_remove(ipmi_sensor_t *sensor) {
  
    if (list_item == NULL) {
      pthread_mutex_unlock(&sensor_list_lock);
 -    return (-1);
 +    return -1;
    }
  
    if (list_prev == NULL)
  
    pthread_mutex_unlock(&sensor_list_lock);
  
-   if (c_ipmi_nofiy_remove && c_ipmi_active) {
+   if (c_ipmi_notify_remove && c_ipmi_active) {
      notification_t n = {NOTIF_WARNING, cdtime(), "", "", "ipmi", "", "", "",
                          NULL};
  
      sstrncpy(n.host, hostname_g, sizeof(n.host));
      sstrncpy(n.type_instance, list_item->sensor_name, sizeof(n.type_instance));
      sstrncpy(n.type, list_item->sensor_type, sizeof(n.type));
 -    ssnprintf(n.message, sizeof(n.message), "sensor %s removed",
 -              list_item->sensor_name);
 +    snprintf(n.message, sizeof(n.message), "sensor %s removed",
 +             list_item->sensor_name);
  
      plugin_dispatch_notification(&n);
    }
  
    free(list_item);
 -  return (0);
 +  return 0;
  } /* int sensor_list_remove */
  
  static int sensor_list_read_all(void) {
  
    pthread_mutex_unlock(&sensor_list_lock);
  
 -  return (0);
 +  return 0;
  } /* int sensor_list_read_all */
  
  static int sensor_list_remove_all(void) {
      list_item = list_next;
    } /* while (list_item) */
  
 -  return (0);
 +  return 0;
  } /* int sensor_list_remove_all */
  
 -  int _severity = NOTIF_OKAY;
 -
+ static int sensor_convert_threshold_severity(enum ipmi_thresh_e severity) {
 -    _severity = NOTIF_OKAY;
 -    break;
+   switch (severity) {
+   case IPMI_LOWER_NON_CRITICAL:
+   case IPMI_UPPER_NON_CRITICAL:
 -    _severity = NOTIF_WARNING;
 -    break;
++    return NOTIF_OKAY;
+   case IPMI_LOWER_CRITICAL:
+   case IPMI_UPPER_CRITICAL:
 -    _severity = NOTIF_FAILURE;
 -    break;
++    return NOTIF_WARNING;
+   case IPMI_LOWER_NON_RECOVERABLE:
+   case IPMI_UPPER_NON_RECOVERABLE:
 -    break;
++    return NOTIF_FAILURE;
+   default:
 -
 -  return (_severity);
++    return NOTIF_OKAY;
+   } /* switch (severity) */
 -    return (IPMI_EVENT_NOT_HANDLED);
+ } /* int sensor_convert_threshold_severity */
+ static void add_event_common_data(notification_t *n, ipmi_sensor_t *sensor,
+                                   enum ipmi_event_dir_e dir,
+                                   ipmi_event_t *event) {
+   ipmi_entity_t *ent = ipmi_sensor_get_entity(sensor);
+   plugin_notification_meta_add_string(n, "entity_name",
+                                       ipmi_entity_get_entity_id_string(ent));
+   plugin_notification_meta_add_signed_int(n, "entity_id",
+                                           ipmi_entity_get_entity_id(ent));
+   plugin_notification_meta_add_signed_int(n, "entity_instance",
+                                           ipmi_entity_get_entity_instance(ent));
+   plugin_notification_meta_add_boolean(n, "assert", dir == IPMI_ASSERTION);
+   if (event)
+     plugin_notification_meta_add_signed_int(n, "event_type",
+                                             ipmi_event_get_type(event));
+ } /* void add_event_sensor_meta_data */
+ static int sensor_threshold_event_handler(
+     ipmi_sensor_t *sensor, enum ipmi_event_dir_e dir,
+     enum ipmi_thresh_e threshold, enum ipmi_event_value_dir_e high_low,
+     enum ipmi_value_present_e value_present, unsigned int raw_value,
+     double value, void *cb_data, ipmi_event_t *event) {
+   /* From the IPMI specification Chapter 2: Events.
+    * If a callback handles the event, then all future callbacks called due to
+    * the event will receive a NULL for the event. So be ready to handle a NULL
+    * event in all your event handlers. A NULL may also be passed to an event
+    * handler if the callback was not due to an event. */
+   if (event == NULL)
 -    ssnprintf(n.message, sizeof(n.message),
 -              "sensor %s received event: %s, value is %f", n.type_instance,
 -              event_state, value);
++    return IPMI_EVENT_NOT_HANDLED;
+   /* offset is a table index and it's represented as enum of strings that are
+      organized in the way - high and low for each threshold severity level */
+   notification_t n = {NOTIF_OKAY, cdtime(), "", "", "ipmi", "", "", "", NULL};
+   unsigned int offset = (2 * threshold) + high_low;
+   unsigned int event_type = ipmi_sensor_get_event_reading_type(sensor);
+   unsigned int sensor_type = ipmi_sensor_get_sensor_type(sensor);
+   const char *event_state =
+       ipmi_get_reading_name(event_type, sensor_type, offset);
+   sensor_get_name(sensor, n.type_instance, sizeof(n.type_instance));
+   if (value_present != IPMI_NO_VALUES_PRESENT)
 -    ssnprintf(n.message, sizeof(n.message),
 -              "sensor %s received event: %s, value not provided",
 -              n.type_instance, event_state);
++    snprintf(n.message, sizeof(n.message),
++             "sensor %s received event: %s, value is %f", n.type_instance,
++             event_state, value);
+   else
 -    /* both values present, so fall-through to add raw value too */
++    snprintf(n.message, sizeof(n.message),
++             "sensor %s received event: %s, value not provided",
++             n.type_instance, event_state);
+   DEBUG("Threshold event received for sensor %s", n.type_instance);
+   sstrncpy(n.host, hostname_g, sizeof(n.host));
+   sstrncpy(n.type, ipmi_sensor_get_sensor_type_string(sensor), sizeof(n.type));
+   n.severity = sensor_convert_threshold_severity(threshold);
+   n.time = NS_TO_CDTIME_T(ipmi_event_get_timestamp(event));
+   plugin_notification_meta_add_string(&n, "severity",
+                                       ipmi_get_threshold_string(threshold));
+   plugin_notification_meta_add_string(&n, "direction",
+                                       ipmi_get_value_dir_string(high_low));
+   switch (value_present) {
+   case IPMI_BOTH_VALUES_PRESENT:
+     plugin_notification_meta_add_double(&n, "val", value);
 -    return (IPMI_EVENT_HANDLED);
++  /* both values present, so fall-through to add raw value too */
+   case IPMI_RAW_VALUE_PRESENT: {
+     char buf[DATA_MAX_NAME_LEN] = {0};
+     snprintf(buf, sizeof(buf), "0x%2.2x", raw_value);
+     plugin_notification_meta_add_string(&n, "raw", buf);
+   } break;
+   default:
+     break;
+   } /* switch (value_present) */
+   add_event_common_data(&n, sensor, dir, event);
+   plugin_dispatch_notification(&n);
+   plugin_notification_meta_free(n.meta);
+   /* Delete handled ipmi event from the list */
+   if (c_ipmi_sel_clear_event) {
+     ipmi_event_delete(event, NULL, NULL);
 -  return (IPMI_EVENT_NOT_HANDLED);
++    return IPMI_EVENT_HANDLED;
+   }
 -    return (IPMI_EVENT_NOT_HANDLED);
++  return IPMI_EVENT_NOT_HANDLED;
+ } /* int sensor_threshold_event_handler */
+ static int sensor_discrete_event_handler(ipmi_sensor_t *sensor,
+                                          enum ipmi_event_dir_e dir, int offset,
+                                          int severity, int prev_severity,
+                                          void *cb_data, ipmi_event_t *event) {
+   /* From the IPMI specification Chapter 2: Events.
+    * If a callback handles the event, then all future callbacks called due to
+    * the event will receive a NULL for the event. So be ready to handle a NULL
+    * event in all your event handlers. A NULL may also be passed to an event
+    * handler if the callback was not due to an event. */
+   if (event == NULL)
 -  ssnprintf(n.message, sizeof(n.message), "sensor %s received event: %s",
 -            n.type_instance, event_state);
++    return IPMI_EVENT_NOT_HANDLED;
+   notification_t n = {NOTIF_OKAY, cdtime(), "", "", "ipmi", "", "", "", NULL};
+   unsigned int event_type = ipmi_sensor_get_event_reading_type(sensor);
+   unsigned int sensor_type = ipmi_sensor_get_sensor_type(sensor);
+   const char *event_state =
+       ipmi_get_reading_name(event_type, sensor_type, offset);
+   sensor_get_name(sensor, n.type_instance, sizeof(n.type_instance));
 -    return (IPMI_EVENT_HANDLED);
++  snprintf(n.message, sizeof(n.message), "sensor %s received event: %s",
++           n.type_instance, event_state);
+   DEBUG("Discrete event received for sensor %s", n.type_instance);
+   sstrncpy(n.host, hostname_g, sizeof(n.host));
+   sstrncpy(n.type, ipmi_sensor_get_sensor_type_string(sensor), sizeof(n.type));
+   n.time = NS_TO_CDTIME_T(ipmi_event_get_timestamp(event));
+   plugin_notification_meta_add_signed_int(&n, "offset", offset);
+   if (severity != -1)
+     plugin_notification_meta_add_signed_int(&n, "severity", severity);
+   if (prev_severity != -1)
+     plugin_notification_meta_add_signed_int(&n, "prevseverity", prev_severity);
+   add_event_common_data(&n, sensor, dir, event);
+   plugin_dispatch_notification(&n);
+   plugin_notification_meta_free(n.meta);
+   /* Delete handled ipmi event from the list */
+   if (c_ipmi_sel_clear_event) {
+     ipmi_event_delete(event, NULL, NULL);
 -  return (IPMI_EVENT_NOT_HANDLED);
++    return IPMI_EVENT_HANDLED;
+   }
++  return IPMI_EVENT_NOT_HANDLED;
+ } /* int sensor_discrete_event_handler */
  /*
   * Entity handlers
   */
@@@ -431,8 -609,39 +601,39 @@@ static void entity_sensor_update_handle
    if ((op == IPMI_ADDED) || (op == IPMI_CHANGED)) {
      /* Will check for duplicate entries.. */
      sensor_list_add(sensor);
+     if (c_ipmi_sel_enabled) {
+       int status = 0;
+       /* register threshold event if threshold sensor support events */
+       if ((ipmi_sensor_get_event_reading_type(sensor) ==
+            IPMI_EVENT_READING_TYPE_THRESHOLD) &&
+           (ipmi_sensor_get_threshold_access(sensor) !=
+            IPMI_THRESHOLD_ACCESS_SUPPORT_NONE))
+         status = ipmi_sensor_add_threshold_event_handler(
+             sensor, sensor_threshold_event_handler, NULL);
+       /* register discrete handler if discrete/specific sensor support events */
+       else if (ipmi_sensor_get_event_support(sensor) != IPMI_EVENT_SUPPORT_NONE)
+         status = ipmi_sensor_add_discrete_event_handler(
+             sensor, sensor_discrete_event_handler, NULL);
+       if (status) {
+         char buf[DATA_MAX_NAME_LEN] = {0};
+         sensor_get_name(sensor, buf, sizeof(buf));
+         ERROR("Unable to add sensor %s event handler, status: %d", buf, status);
+       }
+     }
    } else if (op == IPMI_DELETED) {
      sensor_list_remove(sensor);
+     if (c_ipmi_sel_enabled) {
+       if (ipmi_sensor_get_event_reading_type(sensor) ==
+           IPMI_EVENT_READING_TYPE_THRESHOLD)
+         ipmi_sensor_remove_threshold_event_handler(
+             sensor, sensor_threshold_event_handler, NULL);
+       else
+         ipmi_sensor_remove_discrete_event_handler(
+             sensor, sensor_discrete_event_handler, NULL);
+     }
    }
  } /* void entity_sensor_update_handler */
  
@@@ -459,6 -668,23 +660,23 @@@ static void domain_entity_update_handle
    }
  } /* void domain_entity_update_handler */
  
 -static void smi_event_handler(ipmi_con_t __attribute__((unused)) *ipmi,
 -                              const ipmi_addr_t __attribute__((unused)) *addr,
++static void smi_event_handler(ipmi_con_t __attribute__((unused)) * ipmi,
++                              const ipmi_addr_t __attribute__((unused)) * addr,
+                               unsigned int __attribute__((unused)) addr_len,
+                               ipmi_event_t *event, void *cb_data) {
+   unsigned int type = ipmi_event_get_type(event);
+   ipmi_domain_t *domain = cb_data;
+   DEBUG("%s: Event received: type %u", __FUNCTION__, type);
+   if (type != 0x02)
+     /* It's not a standard IPMI event. */
+     return;
+   /* force domain to reread SELs */
+   ipmi_domain_reread_sels(domain, NULL, NULL);
+ }
  static void domain_connection_change_handler(ipmi_domain_t *domain, int err,
                                               unsigned int conn_num,
                                               unsigned int port_num,
    if (status != 0) {
      c_ipmi_error("ipmi_domain_add_entity_update_handler", status);
    }
+   ipmi_con_t *smi_connection = user_data;
+   status = smi_connection->add_event_handler(smi_connection, smi_event_handler,
+                                              (void *)domain);
+   if (status != 0)
+     c_ipmi_error("Failed to register smi event handler", status);
  } /* void domain_connection_change_handler */
  
  static int thread_init(os_handler_t **ret_os_handler) {
    os_handler = ipmi_posix_thread_setup_os_handler(SIGIO);
    if (os_handler == NULL) {
      ERROR("ipmi plugin: ipmi_posix_thread_setup_os_handler failed.");
 -    return (-1);
 +    return -1;
    }
  
    ipmi_init(os_handler);
                                /* user data = */ NULL, &smi_connection);
    if (status != 0) {
      c_ipmi_error("ipmi_smi_setup_con", status);
 -    return (-1);
 +    return -1;
    }
  
 -  ipmi_open_option_t open_option[1] = {
 -      [0] = {.option = IPMI_OPEN_OPTION_ALL, {.ival = 1}}};
 +  ipmi_open_option_t open_option[1] = {[0] = {.option = IPMI_OPEN_OPTION_ALL,
 +                                              {.ival = 1}}};
  
    status = ipmi_open_domain(
        "mydomain", &smi_connection, /* num_con = */ 1,
-       domain_connection_change_handler, /* user data = */ NULL,
+       domain_connection_change_handler,
+       /* user data = */ (void *)smi_connection,
        /* domain_fully_up_handler = */ NULL, /* user data = */ NULL, open_option,
        sizeof(open_option) / sizeof(open_option[0]), &domain_id);
    if (status != 0) {
      c_ipmi_error("ipmi_open_domain", status);
 -    return (-1);
 +    return -1;
    }
  
    *ret_os_handler = os_handler;
 -  return (0);
 +  return 0;
  } /* int thread_init */
  
  static void *thread_main(void __attribute__((unused)) * user_data) {
    status = thread_init(&os_handler);
    if (status != 0) {
      ERROR("ipmi plugin: thread_init failed.\n");
 -    return ((void *)-1);
 +    return (void *)-1;
    }
  
    while (c_ipmi_active != 0) {
  
    ipmi_posix_thread_free_os_handler(os_handler);
  
 -  return ((void *)0);
 +  return (void *)0;
  } /* void *thread_main */
  
  static int c_ipmi_config(const char *key, const char *value) {
    if (ignorelist == NULL)
      ignorelist = ignorelist_create(/* invert = */ 1);
    if (ignorelist == NULL)
 -    return (1);
 +    return 1;
  
    if (strcasecmp("Sensor", key) == 0) {
      ignorelist_add(ignorelist, value);
    } else if (strcasecmp("IgnoreSelected", key) == 0) {
-     int invert = 1;
-     if (IS_TRUE(value))
-       invert = 0;
-     ignorelist_set_invert(ignorelist, invert);
+     ignorelist_set_invert(ignorelist, !IS_TRUE(value));
    } else if (strcasecmp("NotifySensorAdd", key) == 0) {
-     if (IS_TRUE(value))
-       c_ipmi_nofiy_add = 1;
+     c_ipmi_notify_add = IS_TRUE(value);
    } else if (strcasecmp("NotifySensorRemove", key) == 0) {
-     if (IS_TRUE(value))
-       c_ipmi_nofiy_remove = 1;
+     c_ipmi_notify_remove = IS_TRUE(value);
    } else if (strcasecmp("NotifySensorNotPresent", key) == 0) {
-     if (IS_TRUE(value))
-       c_ipmi_nofiy_notpresent = 1;
+     c_ipmi_notify_notpresent = IS_TRUE(value);
+   } else if (strcasecmp("SELEnabled", key) == 0) {
+     c_ipmi_sel_enabled = IS_TRUE(value);
+   } else if (strcasecmp("SELClearEvent", key) == 0) {
+     c_ipmi_sel_clear_event = IS_TRUE(value);
    } else {
 -    return (-1);
 +    return -1;
    }
  
 -  return (0);
 +  return 0;
  } /* int c_ipmi_config */
  
  static int c_ipmi_init(void) {
      c_ipmi_active = 0;
      thread_id = (pthread_t)0;
      ERROR("ipmi plugin: pthread_create failed.");
 -    return (-1);
 +    return -1;
    }
  
 -  return (0);
 +  return 0;
  } /* int c_ipmi_init */
  
  static int c_ipmi_read(void) {
    if ((c_ipmi_active == 0) || (thread_id == (pthread_t)0)) {
      INFO("ipmi plugin: c_ipmi_read: I'm not active, returning false.");
 -    return (-1);
 +    return -1;
    }
  
    sensor_list_read_all();
    else
      c_ipmi_init_in_progress = 0;
  
 -  return (0);
 +  return 0;
  } /* int c_ipmi_read */
  
  static int c_ipmi_shutdown(void) {
  
    sensor_list_remove_all();
  
 -  return (0);
 +  return 0;
  } /* int c_ipmi_shutdown */
  
  void module_register(void) {