X-Git-Url: https://git.saurik.com/apt.git/blobdiff_plain/3f807f6c39dd6056fca04264ae896990a83c7244..319810767180e5c57c296b06c93e3ebec9f36a8e:/apt-pkg/contrib/configuration.cc?ds=sidebyside diff --git a/apt-pkg/contrib/configuration.cc b/apt-pkg/contrib/configuration.cc index 3140be446..7588b041c 100644 --- a/apt-pkg/contrib/configuration.cc +++ b/apt-pkg/contrib/configuration.cc @@ -22,14 +22,8 @@ #include #include -#include #include #include - -#include -#include -#include -#include using namespace std; /*}}}*/ @@ -85,7 +79,7 @@ Configuration::~Configuration() /* This will lookup a single item by name below another item. It is a helper function for the main lookup function */ Configuration::Item *Configuration::Lookup(Item *Head,const char *S, - unsigned long Len,bool Create) + unsigned long const &Len,bool const &Create) { int Res = 1; Item *I = Head->Child; @@ -118,7 +112,7 @@ Configuration::Item *Configuration::Lookup(Item *Head,const char *S, // --------------------------------------------------------------------- /* This performs a fully scoped lookup of a given name, possibly creating new items */ -Configuration::Item *Configuration::Lookup(const char *Name,bool Create) +Configuration::Item *Configuration::Lookup(const char *Name,bool const &Create) { if (Name == 0) return Root->Child; @@ -182,9 +176,9 @@ string Configuration::FindFile(const char *Name,const char *Default) const if (Itm == 0 || Itm->Value.empty() == true) { if (Default == 0) - return ""; + return rootDir; else - return Default; + return rootDir + Default; } string val = Itm->Value; @@ -223,10 +217,29 @@ string Configuration::FindDir(const char *Name,const char *Default) const return Res; } /*}}}*/ +// Configuration::FindVector - Find a vector of values /*{{{*/ +// --------------------------------------------------------------------- +/* Returns a vector of config values under the given item */ +vector Configuration::FindVector(const char *Name) const +{ + vector Vec; + const Item *Top = Lookup(Name); + if (Top == NULL) + return Vec; + + Item *I = Top->Child; + while(I != NULL) + { + Vec.push_back(I->Value); + I = I->Next; + } + return Vec; +} + /*}}}*/ // Configuration::FindI - Find an integer value /*{{{*/ // --------------------------------------------------------------------- /* */ -int Configuration::FindI(const char *Name,int Default) const +int Configuration::FindI(const char *Name,int const &Default) const { const Item *Itm = Lookup(Name); if (Itm == 0 || Itm->Value.empty() == true) @@ -243,7 +256,7 @@ int Configuration::FindI(const char *Name,int Default) const // Configuration::FindB - Find a boolean type /*{{{*/ // --------------------------------------------------------------------- /* */ -bool Configuration::FindB(const char *Name,bool Default) const +bool Configuration::FindB(const char *Name,bool const &Default) const { const Item *Itm = Lookup(Name); if (Itm == 0 || Itm->Value.empty() == true) @@ -319,7 +332,7 @@ void Configuration::Set(const char *Name,const string &Value) // Configuration::Set - Set an integer value /*{{{*/ // --------------------------------------------------------------------- /* */ -void Configuration::Set(const char *Name,int Value) +void Configuration::Set(const char *Name,int const &Value) { Item *Itm = Lookup(Name,true); if (Itm == 0) @@ -332,7 +345,7 @@ void Configuration::Set(const char *Name,int Value) // Configuration::Clear - Clear an single value from a list /*{{{*/ // --------------------------------------------------------------------- /* */ -void Configuration::Clear(const string Name, int Value) +void Configuration::Clear(string const &Name, int const &Value) { char S[300]; snprintf(S,sizeof(S),"%i",Value); @@ -342,7 +355,7 @@ void Configuration::Clear(const string Name, int Value) // Configuration::Clear - Clear an single value from a list /*{{{*/ // --------------------------------------------------------------------- /* */ -void Configuration::Clear(const string Name, string Value) +void Configuration::Clear(string const &Name, string const &Value) { Item *Top = Lookup(Name.c_str(),false); if (Top == 0 || Top->Child == 0) @@ -373,7 +386,7 @@ void Configuration::Clear(const string Name, string Value) // Configuration::Clear - Clear an entire tree /*{{{*/ // --------------------------------------------------------------------- /* */ -void Configuration::Clear(string Name) +void Configuration::Clear(string const &Name) { Item *Top = Lookup(Name.c_str(),false); if (Top == 0) @@ -488,8 +501,8 @@ string Configuration::Item::FullTag(const Item *Stop) const sections like 'zone "foo.org" { .. };' This causes each section to be added in with a tag like "zone::foo.org" instead of being split tag/value. AsSectional enables Sectional parsing.*/ -bool ReadConfigFile(Configuration &Conf,const string &FName,bool AsSectional, - unsigned Depth) +bool ReadConfigFile(Configuration &Conf,const string &FName,bool const &AsSectional, + unsigned const &Depth) { // Open the stream for reading ifstream F(FName.c_str(),ios::in); @@ -511,6 +524,8 @@ bool ReadConfigFile(Configuration &Conf,const string &FName,bool AsSectional, std::string Input; // The input line with comments stripped. std::string Fragment; + + // Grab the next line of F and place it in Input. do { char *Buffer = new char[1024]; @@ -519,12 +534,13 @@ bool ReadConfigFile(Configuration &Conf,const string &FName,bool AsSectional, F.getline(Buffer,sizeof(Buffer) / 2); Input += Buffer; + delete[] Buffer; } while (F.fail() && !F.eof()); + // Expand tabs in the input line and remove leading and trailing + // whitespace. { - // Allocate enough space to expand an entire line of tabs - // below. const int BufferSize = Input.size() * 8 + 1; char *Buffer = new char[BufferSize]; try @@ -544,6 +560,9 @@ bool ReadConfigFile(Configuration &Conf,const string &FName,bool AsSectional, } CurLine++; + // Now strip comments; if the whole line is contained in a + // comment, skip this line. + // The first meaningful character in the current fragment; will // be adjusted below as we remove bytes from the front. std::string::const_iterator Start = Input.begin(); @@ -576,9 +595,11 @@ bool ReadConfigFile(Configuration &Conf,const string &FName,bool AsSectional, InQuote = !InQuote; if (InQuote == true) continue; - - if (*I == '/' && I + 1 != End && I[1] == '/') - { + + if ((*I == '/' && I + 1 != End && I[1] == '/') || + (*I == '#' && strcmp(string(I,I+6).c_str(),"#clear") != 0 && + strcmp(string(I,I+8).c_str(),"#include") != 0)) + { End = I; break; } @@ -623,34 +644,28 @@ bool ReadConfigFile(Configuration &Conf,const string &FName,bool AsSectional, if (Fragment.empty()) continue; - // We now have a valid line fragment. Walk down it and - // interpret it. + // The line has actual content; interpret what it means. InQuote = false; Start = Fragment.begin(); End = Fragment.end(); for (std::string::const_iterator I = Start; I != End; ++I) { - if(Start > End) - { - _error->Error("Why is Start > End?"); - } - if (*I == '"') InQuote = !InQuote; if (InQuote == false && (*I == '{' || *I == ';' || *I == '}')) { // Put the last fragment into the buffer - std::string::const_iterator FirstNonWhitespace = Start; - std::string::const_iterator LastNonWhitespace = I; - for (; FirstNonWhitespace != I && isspace(*FirstNonWhitespace) != 0; FirstNonWhitespace++) + std::string::const_iterator NonWhitespaceStart = Start; + std::string::const_iterator NonWhitespaceStop = I; + for (; NonWhitespaceStart != I && isspace(*NonWhitespaceStart) != 0; NonWhitespaceStart++) ; - for (; LastNonWhitespace != FirstNonWhitespace && isspace(LastNonWhitespace[-1]) != 0; LastNonWhitespace--) + for (; NonWhitespaceStop != NonWhitespaceStart && isspace(NonWhitespaceStop[-1]) != 0; NonWhitespaceStop--) ; - if (LineBuffer.empty() == false && LastNonWhitespace - FirstNonWhitespace != 0) + if (LineBuffer.empty() == false && NonWhitespaceStop - NonWhitespaceStart != 0) LineBuffer += ' '; - LineBuffer += string(FirstNonWhitespace, LastNonWhitespace); + LineBuffer += string(NonWhitespaceStart, NonWhitespaceStop); // Drop this from the input string, saving the character // that terminated the construct we just closed. (i.e., a @@ -814,39 +829,10 @@ bool ReadConfigFile(Configuration &Conf,const string &FName,bool AsSectional, // ReadConfigDir - Read a directory of config files /*{{{*/ // --------------------------------------------------------------------- /* */ -bool ReadConfigDir(Configuration &Conf,const string &Dir,bool AsSectional, - unsigned Depth) -{ - DIR *D = opendir(Dir.c_str()); - if (D == 0) - return _error->Errno("opendir",_("Unable to read %s"),Dir.c_str()); - - vector List; - - for (struct dirent *Ent = readdir(D); Ent != 0; Ent = readdir(D)) - { - if (Ent->d_name[0] == '.') - continue; - - // Skip bad file names ala run-parts - const char *C = Ent->d_name; - for (; *C != 0; C++) - if (isalpha(*C) == 0 && isdigit(*C) == 0 && *C != '_' && *C != '-') - break; - if (*C != 0) - continue; - - // Make sure it is a file and not something else - string File = flCombine(Dir,Ent->d_name); - struct stat St; - if (stat(File.c_str(),&St) != 0 || S_ISREG(St.st_mode) == 0) - continue; - - List.push_back(File); - } - closedir(D); - - sort(List.begin(),List.end()); +bool ReadConfigDir(Configuration &Conf,const string &Dir, + bool const &AsSectional, unsigned const &Depth) +{ + vector const List = GetListOfFilesInDir(Dir, "conf", true, true); // Read the files for (vector::const_iterator I = List.begin(); I != List.end(); I++)