Create Filters class to store filter functions

Enhanced the generated code to now store the filter functions within an
array contained in a struct similar to other configured parameters.
This allows the generated property watches to use an index within that
array to access a pointer to a Filters class containing a given set of
filter functions. The set of filter functions would then be applied
against all the properties being watched.

Tested:
    Generated code provides structure needed to access filter functions
    Filter functions filter property values that fail the filter(s)

Change-Id: I8f1f882704de521f2ab393530ad7ef096314975d
Signed-off-by: Matthew Barth <msbarth@us.ibm.com>
diff --git a/src/templates/generated.mako.hpp b/src/templates/generated.mako.hpp
index a6c33bf..7b1bf69 100644
--- a/src/templates/generated.mako.hpp
+++ b/src/templates/generated.mako.hpp
@@ -120,6 +120,30 @@
     }
 };
 
+struct ConfigPropertyFilters
+{
+    using PropertyFilters = std::array<std::unique_ptr<Filters>, ${len(filters)}>;
+
+    static auto& get()
+    {
+        static const PropertyFilters propertyFilters =
+        {
+% for f in filters:
+            std::make_unique<OperandFilters<${f.datatype}>>(
+                std::vector<std::function<bool(${f.datatype})>>{
+    % for o in f.filters:
+                    [](const auto& val){
+                        return val ${o.op} ${o.argument(loader, indent=indent +1)};
+                    },
+    % endfor
+                }
+            ),
+% endfor
+        };
+        return propertyFilters;
+    }
+};
+
 struct ConfigPropertyIndicies
 {
     using PropertyIndicies = std::array<PropertyIndex, ${len(instancegroups)}>;
@@ -230,22 +254,22 @@
         {
 % for w in watches:
             std::make_unique<PropertyWatchOfType<${w.datatype}, SDBusPlus>>(
-    % if w.filters:
-                std::vector<std::function<bool(${w.datatype})>>{
-        % for f in w.filters:
-                    [](const auto& val){
-                        return val ${f.op} ${f.argument(loader, indent=indent +1)};
-                    },
-        % endfor
-                },
-    % else:
-                std::vector<std::function<bool(${w.datatype})>>{},
-    % endif
     % if w.callback is None:
+        % if w.filters is None:
                 ConfigPropertyIndicies::get()[${w.instances}]),
+        % else:
+                ConfigPropertyIndicies::get()[${w.instances}],
+                ConfigPropertyFilters::get()[${w.filters}].get()),
+        % endif
     % else:
+        % if w.filters is None:
                 ConfigPropertyIndicies::get()[${w.instances}],
                 *ConfigPropertyCallbacks::get()[${w.callback}]),
+        % else:
+                ConfigPropertyIndicies::get()[${w.instances}],
+                *ConfigPropertyCallbacks::get()[${w.callback}],
+                ConfigPropertyFilters::get()[${w.filters}].get()),
+        % endif
     % endif
 % endfor
         };