X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=input.cpp;h=81bc2dc4ea4d396ce6d9d7855b211919aff878e4;hb=941a7e35cd1b51dcd15159e23cc4a1e82ae4808b;hp=0ee7d1ce918af18a9999a414cc9014a97ae07f7d;hpb=70c47a998c5aa2eb536c3c8f71f3178cd217a14d;p=cubemap diff --git a/input.cpp b/input.cpp index 0ee7d1c..81bc2dc 100644 --- a/input.cpp +++ b/input.cpp @@ -30,6 +30,13 @@ void split_user_host(const string &user_host, string *user, string *host) // Extremely rudimentary URL parsing. bool parse_url(const string &url, string *protocol, string *user, string *host, string *port, string *path) { + // pipe:foo (or pipe:"foo"). + if (url.find("pipe:") == 0) { + *protocol = "pipe"; + *path = string(url.begin() + 5, url.end()); + return true; + } + size_t split = url.find("://"); if (split == string::npos) { return false; @@ -37,8 +44,30 @@ bool parse_url(const string &url, string *protocol, string *user, string *host, *protocol = string(url.begin(), url.begin() + split); string rest = string(url.begin() + split + 3, url.end()); - split = rest.find_first_of(":/"); - if (split == string::npos) { + + // Split at the first slash, or the first colon that's not within []. + bool within_brackets = false; + for (split = 0; split < rest.size(); ++split) { + if (rest[split] == '[') { + if (within_brackets) { + // Can't nest brackets. + return false; + } + within_brackets = true; + } else if (rest[split] == ']') { + if (!within_brackets) { + // ] without matching [. + return false; + } + within_brackets = false; + } else if (rest[split] == '/') { + break; + } else if (rest[split] == ':' && !within_brackets) { + break; + } + } + + if (split == rest.size()) { // http://foo split_user_host(rest, user, host); *port = *protocol; @@ -72,34 +101,35 @@ bool parse_url(const string &url, string *protocol, string *user, string *host, return true; } -Input *create_input(const std::string &url) +Input *create_input(const string &url, Input::Encoding encoding) { string protocol, user, host, port, path; if (!parse_url(url, &protocol, &user, &host, &port, &path)) { - return NULL; + return nullptr; } - if (protocol == "http") { - return new HTTPInput(url); + if (protocol == "http" || protocol == "pipe") { + return new HTTPInput(url, encoding); } if (protocol == "udp") { + assert(encoding == Input::INPUT_ENCODING_RAW); return new UDPInput(url); } - return NULL; + return nullptr; } Input *create_input(const InputProto &serialized) { string protocol, user, host, port, path; if (!parse_url(serialized.url(), &protocol, &user, &host, &port, &path)) { - return NULL; + return nullptr; } - if (protocol == "http") { + if (protocol == "http" || protocol == "pipe") { return new HTTPInput(serialized); } if (protocol == "udp") { return new UDPInput(serialized); } - return NULL; + return nullptr; } Input::~Input() {}