| 1978 | } |
| 1979 | |
| 1980 | inline bool is_valid_path(const std::string &path) { |
| 1981 | size_t level = 0; |
| 1982 | size_t i = 0; |
| 1983 | |
| 1984 | // Skip slash |
| 1985 | while (i < path.size() && path[i] == '/') { |
| 1986 | i++; |
| 1987 | } |
| 1988 | |
| 1989 | while (i < path.size()) { |
| 1990 | // Read component |
| 1991 | auto beg = i; |
| 1992 | while (i < path.size() && path[i] != '/') { |
| 1993 | i++; |
| 1994 | } |
| 1995 | |
| 1996 | auto len = i - beg; |
| 1997 | assert(len > 0); |
| 1998 | |
| 1999 | if (!path.compare(beg, len, ".")) { |
| 2000 | ; |
| 2001 | } else if (!path.compare(beg, len, "..")) { |
| 2002 | if (level == 0) { return false; } |
| 2003 | level--; |
| 2004 | } else { |
| 2005 | level++; |
| 2006 | } |
| 2007 | |
| 2008 | // Skip slash |
| 2009 | while (i < path.size() && path[i] == '/') { |
| 2010 | i++; |
| 2011 | } |
| 2012 | } |
| 2013 | |
| 2014 | return true; |
| 2015 | } |
| 2016 | |
| 2017 | inline std::string encode_query_param(const std::string &value) { |
| 2018 | std::ostringstream escaped; |
no test coverage detected