src: Made strieq(T, S) template

This commit is contained in:
Tatsuhiro Tsujikawa 2016-03-25 22:45:33 +09:00
parent 9272e80fa6
commit 3e6c38e3be
3 changed files with 48 additions and 40 deletions

View File

@ -39,23 +39,27 @@ HtmlParser::HtmlParser(const std::string &base_uri)
HtmlParser::~HtmlParser() { htmlFreeParserCtxt(parser_ctx_); } HtmlParser::~HtmlParser() { htmlFreeParserCtxt(parser_ctx_); }
namespace { namespace {
const char *get_attr(const xmlChar **attrs, const char *name) { StringRef get_attr(const xmlChar **attrs, const StringRef &name) {
if (attrs == nullptr) { if (attrs == nullptr) {
return nullptr; return StringRef{};
} }
for (; *attrs; attrs += 2) { for (; *attrs; attrs += 2) {
if (util::strieq(reinterpret_cast<const char *>(attrs[0]), name)) { if (util::strieq(StringRef{attrs[0], strlen(reinterpret_cast<const char *>(
return reinterpret_cast<const char *>(attrs[1]); attrs[0]))},
name)) {
return StringRef{attrs[1],
strlen(reinterpret_cast<const char *>(attrs[1]))};
} }
} }
return nullptr; return StringRef{};
} }
} // namespace } // namespace
namespace { namespace {
void add_link(ParserData *parser_data, const char *uri, ResourceType res_type) { void add_link(ParserData *parser_data, const StringRef &uri,
ResourceType res_type) {
auto u = xmlBuildURI( auto u = xmlBuildURI(
reinterpret_cast<const xmlChar *>(uri), reinterpret_cast<const xmlChar *>(uri.c_str()),
reinterpret_cast<const xmlChar *>(parser_data->base_uri.c_str())); reinterpret_cast<const xmlChar *>(parser_data->base_uri.c_str()));
if (u) { if (u) {
parser_data->links.push_back( parser_data->links.push_back(
@ -66,32 +70,34 @@ void add_link(ParserData *parser_data, const char *uri, ResourceType res_type) {
} // namespace } // namespace
namespace { namespace {
void start_element_func(void *user_data, const xmlChar *name, void start_element_func(void *user_data, const xmlChar *src_name,
const xmlChar **attrs) { const xmlChar **attrs) {
auto parser_data = static_cast<ParserData *>(user_data); auto parser_data = static_cast<ParserData *>(user_data);
if (util::strieq(reinterpret_cast<const char *>(name), "head")) { auto name =
StringRef{src_name, strlen(reinterpret_cast<const char *>(src_name))};
if (util::strieq_l("head", name)) {
++parser_data->inside_head; ++parser_data->inside_head;
} }
if (util::strieq(reinterpret_cast<const char *>(name), "link")) { if (util::strieq_l("link", name)) {
auto rel_attr = get_attr(attrs, "rel"); auto rel_attr = get_attr(attrs, StringRef::from_lit("rel"));
auto href_attr = get_attr(attrs, "href"); auto href_attr = get_attr(attrs, StringRef::from_lit("href"));
if (!href_attr) { if (rel_attr.empty() || href_attr.empty()) {
return; return;
} }
if (util::strieq(rel_attr, "shortcut icon")) { if (util::strieq_l("shortcut icon", rel_attr)) {
add_link(parser_data, href_attr, REQ_OTHERS); add_link(parser_data, href_attr, REQ_OTHERS);
} else if (util::strieq(rel_attr, "stylesheet")) { } else if (util::strieq_l("stylesheet", rel_attr)) {
add_link(parser_data, href_attr, REQ_CSS); add_link(parser_data, href_attr, REQ_CSS);
} }
} else if (util::strieq(reinterpret_cast<const char *>(name), "img")) { } else if (util::strieq_l("img", name)) {
auto src_attr = get_attr(attrs, "src"); auto src_attr = get_attr(attrs, StringRef::from_lit("src"));
if (!src_attr) { if (src_attr.empty()) {
return; return;
} }
add_link(parser_data, src_attr, REQ_IMG); add_link(parser_data, src_attr, REQ_IMG);
} else if (util::strieq(reinterpret_cast<const char *>(name), "script")) { } else if (util::strieq_l("script", name)) {
auto src_attr = get_attr(attrs, "src"); auto src_attr = get_attr(attrs, StringRef::from_lit("src"));
if (!src_attr) { if (src_attr.empty()) {
return; return;
} }
if (parser_data->inside_head) { if (parser_data->inside_head) {
@ -106,7 +112,9 @@ void start_element_func(void *user_data, const xmlChar *name,
namespace { namespace {
void end_element_func(void *user_data, const xmlChar *name) { void end_element_func(void *user_data, const xmlChar *name) {
auto parser_data = static_cast<ParserData *>(user_data); auto parser_data = static_cast<ParserData *>(user_data);
if (util::strieq(reinterpret_cast<const char *>(name), "head")) { if (util::strieq_l(
"head",
StringRef{name, strlen(reinterpret_cast<const char *>(name))})) {
--parser_data->inside_head; --parser_data->inside_head;
} }
} }

View File

@ -437,25 +437,29 @@ int alpn_select_proto_cb(SSL *ssl, const unsigned char **out,
} // namespace } // namespace
#endif // OPENSSL_VERSION_NUMBER >= 0x10002000L #endif // OPENSSL_VERSION_NUMBER >= 0x10002000L
namespace { struct TLSProtocol {
constexpr const char *tls_names[] = {"TLSv1.2", "TLSv1.1", "TLSv1.0"}; StringRef name;
constexpr size_t tls_namelen = array_size(tls_names); long int mask;
constexpr long int tls_masks[] = {SSL_OP_NO_TLSv1_2, SSL_OP_NO_TLSv1_1, };
SSL_OP_NO_TLSv1};
} // namespace constexpr TLSProtocol TLS_PROTOS[] = {
TLSProtocol{StringRef::from_lit("TLSv1.2"), SSL_OP_NO_TLSv1_2},
TLSProtocol{StringRef::from_lit("TLSv1.1"), SSL_OP_NO_TLSv1_1},
TLSProtocol{StringRef::from_lit("TLSv1.0"), SSL_OP_NO_TLSv1}};
long int create_tls_proto_mask(const std::vector<std::string> &tls_proto_list) { long int create_tls_proto_mask(const std::vector<std::string> &tls_proto_list) {
long int res = 0; long int res = 0;
for (size_t i = 0; i < tls_namelen; ++i) { for (auto &supported : TLS_PROTOS) {
size_t j; auto ok = false;
for (j = 0; j < tls_proto_list.size(); ++j) { for (auto &name : tls_proto_list) {
if (util::strieq(tls_names[i], tls_proto_list[j])) { if (util::strieq(supported.name, name)) {
ok = true;
break; break;
} }
} }
if (j == tls_proto_list.size()) { if (!ok) {
res |= tls_masks[i]; res |= supported.mask;
} }
} }
return res; return res;

View File

@ -287,12 +287,8 @@ bool strieq(InputIt1 first1, InputIt1 last1, InputIt2 first2, InputIt2 last2) {
return std::equal(first1, last1, first2, CaseCmp()); return std::equal(first1, last1, first2, CaseCmp());
} }
inline bool strieq(const std::string &a, const std::string &b) { template <typename T, typename S> bool strieq(const T &a, const S &b) {
return strieq(std::begin(a), std::end(a), std::begin(b), std::end(b)); return strieq(a.begin(), a.end(), b.begin(), b.end());
}
inline bool strieq(const StringRef &a, const StringRef &b) {
return strieq(std::begin(a), std::end(a), std::begin(b), std::end(b));
} }
template <typename CharT, typename InputIt, size_t N> template <typename CharT, typename InputIt, size_t N>