Public Member Functions | Private Member Functions

ACE_Ini_ImpExp Class Reference

Imports the configuration database from filename as strings. Allows non-typed values. (no #, dword: hex:, etc. prefixes) and skips whitespace (tabs and spaces) as in standard .ini and .conf files. Values (to right of equal sign) can be double quote delimited to embed tabs and spaces in the string. Caller must convert string to type. More...

#include <Configuration_Import_Export.h>

Inheritance diagram for ACE_Ini_ImpExp:
Inheritance graph
[legend]
Collaboration diagram for ACE_Ini_ImpExp:
Collaboration graph
[legend]

List of all members.

Public Member Functions

 ACE_Ini_ImpExp (ACE_Configuration &)
virtual ~ACE_Ini_ImpExp (void)
virtual int import_config (const ACE_TCHAR *filename)
virtual int export_config (const ACE_TCHAR *filename)

Private Member Functions

int export_section (const ACE_Configuration_Section_Key &section, const ACE_TString &path, FILE *out)
ACE_TCHARsquish (ACE_TCHAR *src)
 ACE_Ini_ImpExp (const ACE_Ini_ImpExp &)
ACE_Ini_ImpExpoperator= (const ACE_Ini_ImpExp &)

Detailed Description

Imports the configuration database from filename as strings. Allows non-typed values. (no #, dword: hex:, etc. prefixes) and skips whitespace (tabs and spaces) as in standard .ini and .conf files. Values (to right of equal sign) can be double quote delimited to embed tabs and spaces in the string. Caller must convert string to type.

This method allows for lines in the .ini or .conf file like this:

TimeToLive = 100 Delay = FALSE Flags = FF34 Heading = "ACE - Adaptive Communication Environment"

(note leading whitespace (tabs) in examples below)

SeekIndex = 14 TraceLevel = 6 # Can comment lines like this Justification = left_justified

The caller can then retrieve the string with the regular <get_string_value> function and convert the string to the desired data type.

Todo:
  • Strings with embedded newlines cause the import to fail
  • Strings with embedded quotes " cause the import to fail
  • Importing/exporting for values in the root section does not work
  • Add dynamic buffer when importing. currently it will not allow importing of values greater than a fixed ammount (4096 bytes)

Definition at line 162 of file Configuration_Import_Export.h.


Constructor & Destructor Documentation

ACE_Ini_ImpExp::ACE_Ini_ImpExp ( ACE_Configuration config  ) 

Construction

Definition at line 392 of file Configuration_Import_Export.cpp.

    : ACE_Config_ImpExp_Base (config)
{
}

ACE_Ini_ImpExp::~ACE_Ini_ImpExp ( void   )  [virtual]

Destructor

Definition at line 397 of file Configuration_Import_Export.cpp.

{
}

ACE_Ini_ImpExp::ACE_Ini_ImpExp ( const ACE_Ini_ImpExp  )  [private]

Member Function Documentation

int ACE_Ini_ImpExp::export_config ( const ACE_TCHAR filename  )  [virtual]

This method exports the entire configuration database to filename. Once the file is opened this method calls export_section() passing the root section.

Implements ACE_Config_ImpExp_Base.

Definition at line 503 of file Configuration_Import_Export.cpp.

{
  if (0 == filename)
    {
      errno = EINVAL;
      return -1;
    }
  int result = -1;

  FILE* out = ACE_OS::fopen (filename, ACE_TEXT ("w"));
  if (out)
    {
      result = this->export_section (config_.root_section (),
                                     ACE_TEXT (""),
                                     out);
      // The data may have been buffered and will be flush on close,
      // so we need to check that the close succeeds.
      if (ACE_OS::fclose (out) < 0)
        result = -7;
    }
  return result;
}

int ACE_Ini_ImpExp::export_section ( const ACE_Configuration_Section_Key section,
const ACE_TString path,
FILE *  out 
) [private]

Method provided by derived classes in order to write one section to the file specified. Called by export_config() when exporting the entire configuration object.

Definition at line 531 of file Configuration_Import_Export.cpp.

{
  // don't export the root
  if (path.length ())
    {
      // Write out the section header
      ACE_TString header = ACE_TEXT ("[");
      header += path;
      header += ACE_TEXT ("]\n");
      if (ACE_OS::fputs (header.fast_rep (), out) < 0)
        return -1;
      // Write out each value
      int index = 0;
      ACE_TString name;
      ACE_Configuration::VALUETYPE type;
      ACE_TString line;
      ACE_TCHAR int_value[32];
      ACE_TCHAR bin_value[3];
      void* binary_data;
      size_t binary_length;
      ACE_TString string_value;
      while (!config_.enumerate_values (section, index, name, type))
        {
          line = name + ACE_TEXT ("=");
          switch (type)
            {
            case ACE_Configuration::INTEGER:
              {
                u_int value;
                if (config_.get_integer_value (section, name.fast_rep (), value))
                  return -2;
                ACE_OS::sprintf (int_value, ACE_TEXT ("%08x"), value);
                line += int_value;
                break;
              }
            case ACE_Configuration::STRING:
              {
                if (config_.get_string_value (section,
                                              name.fast_rep (),
                                              string_value))
                  return -2;
                line += string_value;
                break;
              }
#ifdef _WIN32
            case ACE_Configuration::INVALID:
              break;  // JDO added break.  Otherwise INVALID is processed
              // like BINARY. If that's correct, please remove the
              // break and these comments
#endif
            case ACE_Configuration::BINARY:
              {
                // not supported yet - maybe use BASE64 codeing?
                if (config_.get_binary_value (section,
                                              name.fast_rep (),
                                              binary_data,
                                              binary_length))
                  return -2;
                line += ACE_TEXT ("\"");
                unsigned char* ptr = (unsigned char*)binary_data;
                while (binary_length)
                  {
                    if (ptr != binary_data)
                      {
                        line += ACE_TEXT (",");
                      }
                    ACE_OS::sprintf (bin_value, ACE_TEXT ("%02x"), *ptr);
                    line += bin_value;
                    --binary_length;
                    ++ptr;
                  }
                line += ACE_TEXT ("\"");
                delete [] (char *) binary_data;
                break;
              }
            default:
              return -3;

            }// end switch on type

          line += ACE_TEXT ("\n");
          if (ACE_OS::fputs (line.fast_rep (), out) < 0)
            return -4;
          ++index;
        }// end while enumerating values
    }
  // Export all sub sections
  int index = 0;
  ACE_TString name;
  ACE_Configuration_Section_Key sub_key;
  ACE_TString sub_section;
  while (!config_.enumerate_sections (section, index, name))
    {
      ACE_TString sub_section (path);
      if (path.length ())
        sub_section += ACE_TEXT ("\\");
      sub_section += name;
      if (config_.open_section (section, name.fast_rep (), 0, sub_key))
        return -5;
      if (export_section (sub_key, sub_section.fast_rep (), out))
        return -6;
      ++index;
    }
  return 0;

}

int ACE_Ini_ImpExp::import_config ( const ACE_TCHAR filename  )  [virtual]

Imports the configuration database from filename. No existing data is removed.

Implements ACE_Config_ImpExp_Base.

Definition at line 403 of file Configuration_Import_Export.cpp.

{
  if (0 == filename)
    {
      errno = EINVAL;
      return -1;
    }
  FILE* in = ACE_OS::fopen (filename, ACE_TEXT ("r"));
  if (!in)
    return -1;

  // @@ Make this a dynamic size!
  ACE_TCHAR buffer[4096];
  ACE_Configuration_Section_Key section;
  while (ACE_OS::fgets (buffer, sizeof buffer, in))
    {
      ACE_TCHAR *line = this->squish (buffer);
      // Check for a comment and blank line
      if (line[0] == ACE_TEXT (';')  ||
          line[0] == ACE_TEXT ('#')  ||
          line[0] == '\0')
        continue;

      if (line[0] == ACE_TEXT ('['))
        {
          // We have a new section here, strip out the section name
          ACE_TCHAR* end = ACE_OS::strrchr (line, ACE_TEXT (']'));
          if (!end)
            {
              ACE_OS::fclose (in);
              return -3;
            }
          *end = 0;

          if (config_.expand_path (config_.root_section (),
                                   line + 1,
                                   section,
                                   1))
            {
              ACE_OS::fclose (in);
              return -3;
            }

          continue;
        }

      // We have a line; name ends at equal sign.
      ACE_TCHAR *end = ACE_OS::strchr (line, ACE_TEXT ('='));
      if (end == 0)                            // No '='
        {
          ACE_OS::fclose (in);
          return -3;
        }
      *end++ = '\0';
      ACE_TCHAR *name = this->squish (line);
#if 0
      if (ACE_OS::strlen (name) == 0)          // No name; just an '='
        {
          ACE_OS::fclose (in);
          return -3;
        }
#endif
      // Now find the start of the value
      ACE_TCHAR *value = this->squish (end);
      size_t value_len = ACE_OS::strlen (value);
      if (value_len > 0)
        {
          // ACE 5.2 (and maybe earlier) exported strings may be enclosed
          // in quotes. If string is quote-delimited, strip the quotes.
          // Newer exported files don't have quote delimiters.
          if (value[0] == ACE_TEXT ('"') &&
              value[value_len - 1] == ACE_TEXT ('"'))
            {
              // Strip quotes off both ends.
              value[value_len - 1] = '\0';
              ++value;
            }
        }

      if (config_.set_string_value (section, name, value))
        {
          ACE_OS::fclose (in);
          return -4;
        }
    }             // end while fgets

  if (ferror (in))
    {
      ACE_OS::fclose (in);
      return -1;
    }

  ACE_OS::fclose (in);
  return 0;
}

ACE_Ini_ImpExp& ACE_Ini_ImpExp::operator= ( const ACE_Ini_ImpExp  )  [private]
ACE_TCHAR * ACE_Ini_ImpExp::squish ( ACE_TCHAR src  )  [private]

Method to squish leading and trailing whitespaces in a string. Whitespace is defined as: spaces (' '), tabs ('\t') or cr/lf. Returns a pointer to the first non-whitespace character in the buffer provided, or a pointer to the terminating null if the string is all whitespace. The terminating null is moved forward to the first character past the last non-whitespace.

Definition at line 648 of file Configuration_Import_Export.cpp.

{
  ACE_TCHAR *cp = 0;

  if (src == 0)
    return 0;

  // Start at the end and work backwards over all whitespace.
  for (cp = src + ACE_OS::strlen (src) - 1;
       cp != src;
       --cp)
    if (!ACE_OS::ace_isspace (*cp))
      break;
  cp[1] = '\0';          // Chop trailing whitespace

  // Now start at the beginning and move over all whitespace.
  for (cp = src; ACE_OS::ace_isspace (*cp); ++cp)
    continue;

  return cp;
}


The documentation for this class was generated from the following files:
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines