00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #ifndef PCAP_LIST_HXX_
00023 # define PCAP_LIST_HXX_
00024
00025 # include "list.hh"
00026
00027 namespace wpl
00028 {
00029
00030 namespace pcap
00031 {
00032
00033 template <class Stream, class Bottom>
00034 list<Stream, Bottom>::list(const std::string& stream_names)
00035 {
00036 typedef std::vector<std::string> stream_vect_t;
00037 typedef std::pair<stream_vect_t, std::string> parse_res_t;
00038
00039 const parse_res_t pres = parse(stream_names);
00040 const stream_vect_t& names = pres.first;
00041
00042 std::string summary;
00043
00044 if (not pres.second.empty())
00045 meta_.add("addr", pres.second);
00046 switch (names.size())
00047 {
00048 case 0:
00049 summary = "[]";
00050 break;
00051 case 1:
00052 summary = names.front();
00053 break;
00054 default:
00055 {
00056 size_t len = 0;
00057 bool cont = true;
00058
00059 while (cont and len <= names.front().size())
00060 {
00061 const std::string ref = names.front().substr(0, ++len);
00062
00063 for (size_t i = 1; cont and i < names.size(); ++i)
00064 if (names[i].substr(0, len) != ref)
00065 cont = false;
00066 }
00067 summary = '[' + names.front().substr(0, len - 1) + "*]";
00068 break;
00069 }
00070 }
00071 meta_.add("name", summary);
00072
00073 BOOST_FOREACH(const std::string& s, names)
00074 push_back(Stream (s));
00075
00076 update_meta(this);
00077 }
00078
00079 template <class Stream, class Bottom>
00080 list<Stream, Bottom>::list(const list& other):
00081 super_type (static_cast<const super_type&> (other)),
00082 meta_ (other.meta_)
00083 {
00084 update_meta(this);
00085 }
00086
00087 template<class Stream, class Bottom>
00088 list<Stream, Bottom>&
00089 list<Stream, Bottom>::operator = (const list& rhs)
00090 {
00091 if (&rhs == this)
00092 return *this;
00093
00094 super_type::operator = (rhs);
00095 meta_ = rhs.meta_;
00096 update_meta(this);
00097 }
00098
00099 template <class Stream, class Bottom>
00100 std::ostream&
00101 list<Stream, Bottom>::print(std::ostream& os) const
00102 {
00103 return os << meta_["name"].get<std::string>();
00104 }
00105
00106 template <class Stream, class Bottom>
00107 pkt::type
00108 list<Stream, Bottom>::type() const
00109 {
00110 if (this->empty())
00111 {
00112 std::ostringstream os;
00113
00114 os << *this << "is empty";
00115 throw std::invalid_argument (os.str());
00116 }
00117 return this->get(0).type();
00118 }
00119
00120 template <class Stream, class Bottom>
00121 void
00122 list<Stream, Bottom>::expect(typename pkt::type t) const
00123 {
00124 for (size_t i = 0; i < this->size(); ++i)
00125 this->get(i).expect(t);
00126 }
00127
00128 template <class Stream, class Bottom>
00129 const opt::list&
00130 list<Stream, Bottom>::meta() const
00131 {
00132 return meta_;
00133 }
00134
00135 template <class Stream, class Bottom>
00136 std::pair<std::string, size_t>
00137 list<Stream, Bottom>::parse_word(const std::string& stream_names,
00138 const size_t start,
00139 const std::set<char>& stop_seps)
00140 {
00141 std::string w;
00142 size_t i;
00143
00144 for (i = start;
00145 i < stream_names.size() and not stop_seps.count(stream_names[i]);
00146 ++i)
00147 {
00148 if (stream_names[i] == escape_char)
00149 ++i;
00150 if (i < stream_names.size())
00151 w.push_back(stream_names[i]);
00152 }
00153 return std::make_pair(w, i);
00154 }
00155
00156 template <class Stream, class Bottom>
00157 std::pair<std::vector<std::string>, std::string>
00158 list<Stream, Bottom>::parse(const std::string& stream_names)
00159 {
00160 std::vector<std::string> names;
00161 std::string addr;
00162 std::set<char> stop_sep_tname;
00163
00164 stop_sep_tname.insert(trace_name_sep);
00165 stop_sep_tname.insert(addr_sep);
00166
00167 size_t i = 0;
00168
00169 while (i < stream_names.size() and stream_names[i] != addr_sep)
00170 {
00171 std::pair<std::string, size_t> w = parse_word(stream_names, i,
00172 stop_sep_tname);
00173 names.push_back(w.first);
00174 i = w.second;
00175 if (i < stream_names.size() and stream_names[i] == trace_name_sep)
00176 ++i;
00177 }
00178 if (i < stream_names.size() and stream_names[i] == addr_sep)
00179 addr = parse_word(stream_names, i + 1, std::set<char> ()).first;
00180 return std::make_pair(names, addr);
00181 }
00182
00183 template <class Stream, class Bottom>
00184 void
00185 list<Stream, Bottom>::update_meta(list* p)
00186 {
00187 for (unsigned i = 0; i < this->size(); ++i)
00188 this->get(i).meta().add("list", p);
00189 }
00190
00191 template <class S, class B>
00192 std::ostream&
00193 operator << (std::ostream& os, const list<S, B>& l)
00194 {
00195 return l.print(os);
00196 }
00197
00198 }
00199
00200 }
00201
00202 #endif // ! PCAP_LIST_HXX_