This is an automated email from the ASF dual-hosted git repository.

bneradt pushed a commit to branch dev-1-0-12
in repository https://gitbox.apache.org/repos/asf/trafficserver-libswoc.git

commit 70f986b33dc05e24c543c6d6fd4d76aacea934b9
Author: Alan M. Carroll <[email protected]>
AuthorDate: Mon Feb 17 17:37:37 2020 -0600

    Updates to IPSpace property table example.
---
 unit_tests/ex_ipspace_properties.cc | 191 +++++++++++++++++++++++++-----------
 1 file changed, 133 insertions(+), 58 deletions(-)

diff --git a/unit_tests/ex_ipspace_properties.cc 
b/unit_tests/ex_ipspace_properties.cc
index 5a395da..35d591d 100644
--- a/unit_tests/ex_ipspace_properties.cc
+++ b/unit_tests/ex_ipspace_properties.cc
@@ -36,52 +36,101 @@ using swoc::MemArena;
 
 using W = swoc::LocalBufferWriter<256>;
 
-// Property maps for IPSpace.
+// ---
 
-/// A @c Property is a collection of names which are values of the property.
-class Property {
-  using self_type = Property;
+/** A "table" is conceptually a table with the rows labeled by IP address and 
a set of
+ * property columns that represent data for each IP address.
+ */
+class Table {
+  using self_type = Table; ///< Self reference type.
 public:
-  /// A handle to an instance.
-  using Handle = std::unique_ptr<self_type>;
+  static constexpr char SEP = ','; /// Value separator for input file.
 
-  /** Construct an instance.
-   *
-   * @param idx THe property index in a row.
+  /** A property is the description of data for an address.
+   * The table consists of an ordered list of properties, each corresponding 
to a column.
    */
-  Property(TextView  const& name) : _name(name) {};
-
-  virtual ~Property() = default;
-
-  virtual size_t size() const = 0;
-
-  unsigned idx() const { return _idx; }
-
-  virtual bool needs_localized_token() const { return false; }
-
-  self_type & assign_idx(unsigned idx) { _idx = idx; return *this; }
-  /// Assign the @a offset in bytes for this property.
-  self_type & assign_offset(size_t offset) { _offset = offset; return *this; }
-  size_t offset() const { return _offset; }
-
-  virtual bool parse(TextView token, MemSpan<std::byte> span) = 0;
-
-protected:
-  TextView _name;
-  unsigned _idx = std::numeric_limits<unsigned>::max(); ///< Column index.
-  size_t _offset = std::numeric_limits<size_t>::max(); ///< Offset into a row.
-};
-
-// ---
+  class Property {
+    using self_type = Property; ///< Self reference type.
+  public:
+    /// A handle to an instance.
+    using Handle = std::unique_ptr<self_type>;
+
+    /** Construct an instance.
+     *
+     * @param name Property name.
+     */
+    Property(TextView const& name) : _name(name) {};
+
+    /// Force virtual destructor.
+    virtual ~Property() = default;
+
+    /** The size of the property in bytes.
+     *
+     * @return The amount of data needed for a single instance of the property 
value.
+     */
+    virtual size_t size() const = 0;
+
+    /** The index in the table of the property.
+     *
+     * @return The column index.
+     */
+    unsigned idx() const { return _idx; }
+
+    /** Token persistence.
+     *
+     * @return @c true if the token needs to be preserved, @c false if not.
+     *
+     * If the token for the value is consumed, this should be left as is. 
However, if the token
+     * itself needs to be persistent for the lifetime of the table, this must 
be overridden to
+     * return @c true.
+     */
+    virtual bool needs_localized_token() const { return false; }
+
+    /// @return The row data offset in bytes for this property.
+    size_t offset() const { return _offset; }
+
+    /** Parse the @a token.
+     *
+     * @param token Value from the input file for this property.
+     * @param span Row data storage for this property.
+     * @return @c true if @a token was correctly parse, @c false if not.
+     *
+     * The table parses the input file and handles the fields in a line. Each 
value is passed to
+     * the corresponding property for parsing via this method. The method 
should update the data
+     * pointed at by @a span.
+     */
+    virtual bool parse(TextView token, MemSpan<std::byte> span) = 0;
 
-class Table {
-  using self_type = Table;
-public:
-  static constexpr char SEP = ',';
+  protected:
+    friend class Table;
+
+    TextView _name; ///< Name of the property.
+    unsigned _idx = std::numeric_limits<unsigned>::max(); ///< Column index.
+    size_t _offset = std::numeric_limits<size_t>::max(); ///< Offset into a 
row.
+
+    /** Set the column index.
+     *
+     * @param idx Index for this property.
+     * @return @a this.
+     *
+     * This is called from @c Table to indicate the column index.
+     */
+    self_type & assign_idx(unsigned idx) { _idx = idx; return *this; }
+
+    /** Set the row data @a offset.
+     *
+     * @param offset Offset in bytes.
+     * @return @a this
+     *
+     * This is called from @c Table to store the row data offset.
+     */
+    self_type & assign_offset(size_t offset) { _offset = offset; return *this; 
}
+  };
 
+  /// Construct an empty Table.
   Table() = default;
 
-  /** Add a column to the table.
+  /** Add a property column to the table.
    *
    * @param col Column descriptor.
    * @return @a this
@@ -100,25 +149,51 @@ public:
     MemSpan<std::byte> _data;
   };
 
+  /** Parse input.
+   *
+   * @param src The source to parse.
+   * @return @a true if parsing was successful, @c false if not.
+   *
+   * In general, @a src will be the contents of a file.
+   *
+   * @see swoc::file::load
+   */
   bool parse(TextView src);
 
+  /** Look up @a addr in the table.
+   *
+   * @param addr Address to find.
+   * @return A @c Row for the address, or @c nullptr if not found.
+   */
   Row* find(IPAddr const& addr);
 
+  /// @return The number of ranges in the container.
   size_t size() const { return _space.count(); }
 
-  /// Return the property for the column @a idx.
+  /** Property for column @a idx.
+   *
+   * @param idx Index.
+   * @return The property.
+   */
   Property * column(unsigned idx) { return _columns[idx].get(); }
 
 protected:
-  size_t _size = 0;
+  size_t _size = 0; ///< Size of row data.
+  /// Defined properties for columns.
   std::vector<Property::Handle> _columns;
 
+  /// IPSpace type.
   using space = IPSpace<Row>;
-  space _space;
+  space _space; ///< IPSpace instance.
 
-  MemArena _arena;
+  MemArena _arena; ///< Arena for storing rows.
 
-  TextView token(TextView & src);
+  /** Extract the next token from the line.
+   *
+   * @param line Current line [in,out]
+   * @return Extracted token.
+   */
+  TextView token(TextView & line);
 
   TextView localize(TextView const& src);
 };
@@ -137,22 +212,22 @@ TextView Table::localize(TextView const&src) {
   return span.view();
 }
 
-TextView Table::token(TextView & src) {
+TextView Table::token(TextView & line) {
   TextView::size_type idx = 0;
   // Characters of interest in a null terminated string.
   char sep_list[3] = {'"', SEP, 0};
   bool in_quote_p  = false;
-  while (idx < src.size()) {
+  while (idx < line.size()) {
     // Next character of interest.
-    idx = src.find_first_of(sep_list, idx);
+    idx = line.find_first_of(sep_list, idx);
     if (TextView::npos == idx) {
-      // no more, consume all of @a src.
+      // no more, consume all of @a line.
       break;
-    } else if ('"' == src[idx]) {
+    } else if ('"' == line[idx]) {
       // quote, skip it and flip the quote state.
       in_quote_p = !in_quote_p;
       ++idx;
-    } else if (SEP == src[idx]) { // separator.
+    } else if (SEP == line[idx]) { // separator.
       if (in_quote_p) {
         // quoted separator, skip and continue.
         ++idx;
@@ -164,7 +239,7 @@ TextView Table::token(TextView & src) {
   }
 
   // clip the token from @a src and trim whitespace, quotes
-  auto zret = src.take_prefix(idx).trim_if(&isspace).trim('"');
+  auto zret = line.take_prefix(idx).trim_if(&isspace).trim('"');
   return zret;
 }
 
@@ -204,9 +279,9 @@ bool operator == (Table::Row const&, Table::Row const&) { 
return false; }
 
 // ---
 
-class FlagProperty : public Property {
+class FlagProperty : public Table::Property {
   using self_type = FlagProperty;
-  using super_type = Property;
+  using super_type = Table::Property;
 public:
   static constexpr size_t SIZE = sizeof(bool);
 protected:
@@ -214,9 +289,9 @@ protected:
   bool parse(TextView token, MemSpan<std::byte> span) override;
 };
 
-class FlagGroupProperty : public Property {
+class FlagGroupProperty : public Table::Property {
   using self_type = FlagGroupProperty;
-  using super_type = Property;
+  using super_type = Table::Property;
 public:
   static constexpr size_t SIZE = sizeof(uint8_t);
   FlagGroupProperty(TextView const& name, std::initializer_list<TextView> 
tags);
@@ -228,9 +303,9 @@ protected:
   std::vector<TextView> _tags;
 };
 
-class TagProperty : public Property {
+class TagProperty : public Table::Property {
   using self_type = TagProperty;
-  using super_type = Property;
+  using super_type = Table::Property;
 public: // owner
   static constexpr size_t SIZE = sizeof(uint8_t);
   using super_type::super_type;
@@ -241,9 +316,9 @@ protected:
   bool parse(TextView token, MemSpan<std::byte> span) override;
 };
 
-class StringProperty : public Property {
+class StringProperty : public Table::Property {
   using self_type = StringProperty;
-  using super_type = Property;
+  using super_type = Table::Property;
 public:
   static constexpr size_t SIZE = sizeof(TextView);
   using super_type::super_type;

Reply via email to