src: Eliminate use of snprintf

This commit is contained in:
Tatsuhiro Tsujikawa 2014-05-14 22:39:28 +09:00
parent be4c75a7e9
commit e47b976691
9 changed files with 95 additions and 44 deletions

View File

@ -1585,8 +1585,9 @@ int start_listen(event_base *evbase, Sessions *sessions, const Config *config)
{ {
addrinfo hints; addrinfo hints;
int r; int r;
char service[10];
snprintf(service, sizeof(service), "%u", config->port); auto service = util::utos(config->port);
memset(&hints, 0, sizeof(addrinfo)); memset(&hints, 0, sizeof(addrinfo));
hints.ai_family = AF_UNSPEC; hints.ai_family = AF_UNSPEC;
hints.ai_socktype = SOCK_STREAM; hints.ai_socktype = SOCK_STREAM;
@ -1600,7 +1601,7 @@ int start_listen(event_base *evbase, Sessions *sessions, const Config *config)
auto listen_handler = listen_handler_store.get(); auto listen_handler = listen_handler_store.get();
addrinfo *res, *rp; addrinfo *res, *rp;
r = getaddrinfo(nullptr, service, &hints, &res); r = getaddrinfo(nullptr, service.c_str(), &hints, &res);
if(r != 0) { if(r != 0) {
std::cerr << "getaddrinfo() failed: " << gai_strerror(r) << std::endl; std::cerr << "getaddrinfo() failed: " << gai_strerror(r) << std::endl;
return -1; return -1;

View File

@ -118,6 +118,7 @@ int main(int argc, char* argv[])
shrpx::test_util_to_base64) || shrpx::test_util_to_base64) ||
!CU_add_test(pSuite, "util_percent_encode_token", !CU_add_test(pSuite, "util_percent_encode_token",
shrpx::test_util_percent_encode_token) || shrpx::test_util_percent_encode_token) ||
!CU_add_test(pSuite, "util_utox", shrpx::test_util_utox) ||
!CU_add_test(pSuite, "gzip_inflate", test_nghttp2_gzip_inflate)) { !CU_add_test(pSuite, "gzip_inflate", test_nghttp2_gzip_inflate)) {
CU_cleanup_registry(); CU_cleanup_registry();
return CU_get_error(); return CU_get_error();

View File

@ -83,9 +83,8 @@ int resolve_hostname(sockaddr_union *addr, size_t *addrlen,
{ {
addrinfo hints; addrinfo hints;
int rv; int rv;
char service[10];
snprintf(service, sizeof(service), "%u", port); auto service = util::utos(port);
memset(&hints, 0, sizeof(addrinfo)); memset(&hints, 0, sizeof(addrinfo));
hints.ai_family = family; hints.ai_family = family;
@ -95,7 +94,7 @@ int resolve_hostname(sockaddr_union *addr, size_t *addrlen,
#endif // AI_ADDRCONFIG #endif // AI_ADDRCONFIG
addrinfo *res; addrinfo *res;
rv = getaddrinfo(hostname, service, &hints, &res); rv = getaddrinfo(hostname, service.c_str(), &hints, &res);
if(rv != 0) { if(rv != 0) {
LOG(FATAL) << "Unable to resolve address for " << hostname LOG(FATAL) << "Unable to resolve address for " << hostname
<< ": " << gai_strerror(rv); << ": " << gai_strerror(rv);
@ -136,8 +135,8 @@ evconnlistener* create_evlistener(ListenHandler *handler, int family)
addrinfo hints; addrinfo hints;
int fd = -1; int fd = -1;
int r; int r;
char service[10];
snprintf(service, sizeof(service), "%u", get_config()->port); auto service = util::utos(get_config()->port);
memset(&hints, 0, sizeof(addrinfo)); memset(&hints, 0, sizeof(addrinfo));
hints.ai_family = family; hints.ai_family = family;
hints.ai_socktype = SOCK_STREAM; hints.ai_socktype = SOCK_STREAM;
@ -147,7 +146,7 @@ evconnlistener* create_evlistener(ListenHandler *handler, int family)
#endif // AI_ADDRCONFIG #endif // AI_ADDRCONFIG
addrinfo *res, *rp; addrinfo *res, *rp;
r = getaddrinfo(get_config()->host, service, &hints, &res); r = getaddrinfo(get_config()->host, service.c_str(), &hints, &res);
if(r != 0) { if(r != 0) {
if(LOG_ENABLED(INFO)) { if(LOG_ENABLED(INFO)) {
LOG(INFO) << "Unable to get IPv" << (family == AF_INET ? "4" : "6") LOG(INFO) << "Unable to get IPv" << (family == AF_INET ? "4" : "6")
@ -1253,15 +1252,25 @@ int main(int argc, char **argv)
} }
} }
char hostport[NI_MAXHOST+16];
bool downstream_ipv6_addr = bool downstream_ipv6_addr =
is_ipv6_numeric_addr(get_config()->downstream_host); is_ipv6_numeric_addr(get_config()->downstream_host);
snprintf(hostport, sizeof(hostport), "%s%s%s:%u",
downstream_ipv6_addr ? "[" : "", std::string hostport;
get_config()->downstream_host,
downstream_ipv6_addr ? "]" : "", if(downstream_ipv6_addr) {
get_config()->downstream_port); hostport += "[";
set_config_str(&mod_config()->downstream_hostport, hostport); }
hostport += get_config()->downstream_host;
if(downstream_ipv6_addr) {
hostport += "]";
}
hostport += ":";
hostport += util::utos(get_config()->downstream_port);
set_config_str(&mod_config()->downstream_hostport, hostport.c_str());
if(LOG_ENABLED(INFO)) { if(LOG_ENABLED(INFO)) {
LOG(INFO) << "Resolving backend address"; LOG(INFO) << "Resolving backend address";

View File

@ -258,36 +258,37 @@ int HttpDownstreamConnection::push_request_headers()
int HttpDownstreamConnection::push_upload_data_chunk int HttpDownstreamConnection::push_upload_data_chunk
(const uint8_t *data, size_t datalen) (const uint8_t *data, size_t datalen)
{ {
ssize_t res = 0;
int rv; int rv;
int chunked = downstream_->get_chunked_request(); int chunked = downstream_->get_chunked_request();
auto output = bufferevent_get_output(bev_); auto output = bufferevent_get_output(bev_);
if(chunked) { if(chunked) {
char chunk_size_hex[16]; auto chunk_size_hex = util::utox(datalen);
rv = snprintf(chunk_size_hex, sizeof(chunk_size_hex), "%X\r\n", chunk_size_hex += "\r\n";
static_cast<unsigned int>(datalen));
res += rv; rv = evbuffer_add(output, chunk_size_hex.c_str(), chunk_size_hex.size());
rv = evbuffer_add(output, chunk_size_hex, rv);
if(rv == -1) { if(rv == -1) {
DCLOG(FATAL, this) << "evbuffer_add() failed"; DCLOG(FATAL, this) << "evbuffer_add() failed";
return -1; return -1;
} }
} }
rv = evbuffer_add(output, data, datalen); rv = evbuffer_add(output, data, datalen);
if(rv == -1) { if(rv == -1) {
DCLOG(FATAL, this) << "evbuffer_add() failed"; DCLOG(FATAL, this) << "evbuffer_add() failed";
return -1; return -1;
} }
res += rv;
if(chunked) { if(chunked) {
rv = evbuffer_add(output, "\r\n", 2); rv = evbuffer_add(output, "\r\n", 2);
if(rv == -1) { if(rv == -1) {
DCLOG(FATAL, this) << "evbuffer_add() failed"; DCLOG(FATAL, this) << "evbuffer_add() failed";
return -1; return -1;
} }
res += 2;
} }
return res;
return 0;
} }
int HttpDownstreamConnection::end_upload_data() int HttpDownstreamConnection::end_upload_data()

View File

@ -650,11 +650,12 @@ int HttpsUpstream::on_downstream_header_complete(Downstream *downstream)
if(LOG_ENABLED(INFO)) { if(LOG_ENABLED(INFO)) {
DLOG(INFO, downstream) << "HTTP response header completed"; DLOG(INFO, downstream) << "HTTP response header completed";
} }
char temp[16];
snprintf(temp, sizeof(temp), "HTTP/%d.%d ", std::string hdrs = "HTTP/";
downstream->get_request_major(), hdrs += util::utos(downstream->get_request_major());
downstream->get_request_minor()); hdrs += ".";
std::string hdrs = temp; hdrs += util::utos(downstream->get_request_minor());
hdrs += " ";
hdrs += http2::get_status_string(downstream->get_response_http_status()); hdrs += http2::get_status_string(downstream->get_response_http_status());
hdrs += "\r\n"; hdrs += "\r\n";
downstream->normalize_response_headers(); downstream->normalize_response_headers();
@ -757,10 +758,12 @@ int HttpsUpstream::on_downstream_body(Downstream *downstream,
} }
auto output = bufferevent_get_output(handler_->get_bev()); auto output = bufferevent_get_output(handler_->get_bev());
if(downstream->get_chunked_response()) { if(downstream->get_chunked_response()) {
char chunk_size_hex[16]; auto chunk_size_hex = util::utox(len);
rv = snprintf(chunk_size_hex, sizeof(chunk_size_hex), "%X\r\n", chunk_size_hex += "\r\n";
static_cast<unsigned int>(len));
if(evbuffer_add(output, chunk_size_hex, rv) != 0) { rv = evbuffer_add(output, chunk_size_hex.c_str(), chunk_size_hex.size());
if(rv != 0) {
ULOG(FATAL, this) << "evbuffer_add() failed"; ULOG(FATAL, this) << "evbuffer_add() failed";
return -1; return -1;
} }

View File

@ -42,6 +42,8 @@ namespace util {
const char DEFAULT_STRIP_CHARSET[] = "\r\n\t "; const char DEFAULT_STRIP_CHARSET[] = "\r\n\t ";
const char UPPER_XDIGITS[] = "0123456789ABCDEF";
bool isAlpha(const char c) bool isAlpha(const char c)
{ {
return ('A' <= c && c <= 'Z') || ('a' <= c && c <= 'z'); return ('A' <= c && c <= 'Z') || ('a' <= c && c <= 'z');
@ -68,13 +70,14 @@ std::string percentEncode(const unsigned char* target, size_t len)
{ {
std::string dest; std::string dest;
for(size_t i = 0; i < len; ++i) { for(size_t i = 0; i < len; ++i) {
if(inRFC3986UnreservedChars(target[i])) { unsigned char c = target[i];
dest += target[i];
if(inRFC3986UnreservedChars(c)) {
dest += c;
} else { } else {
char temp[4]; dest += "%";
snprintf(temp, sizeof(temp), "%%%02X", target[i]); dest += UPPER_XDIGITS[c >> 4];
dest.append(temp); dest += UPPER_XDIGITS[(c & 0x0f)];
//dest.append(fmt("%%%02X", target[i]));
} }
} }
return dest; return dest;
@ -102,13 +105,14 @@ std::string percent_encode_token(const std::string& target)
std::string dest; std::string dest;
for(size_t i = 0; i < len; ++i) { for(size_t i = 0; i < len; ++i) {
char c = target[i]; unsigned char c = target[i];
if(c != '%' && in_token(c)) { if(c != '%' && in_token(c)) {
dest += c; dest += c;
} else { } else {
char temp[4]; dest += "%";
snprintf(temp, sizeof(temp), "%%%02X", c); dest += UPPER_XDIGITS[c >> 4];
dest += temp; dest += UPPER_XDIGITS[(c & 0x0f)];
} }
} }
return dest; return dest;

View File

@ -399,6 +399,27 @@ std::string utos(T n)
return res; return res;
} }
extern const char UPPER_XDIGITS[];
template<typename T>
std::string utox(T n)
{
std::string res;
if(n == 0) {
res = "0";
return res;
}
int i = 0;
T t = n;
for(; t; t /= 16, ++i);
res.resize(i);
--i;
for(; n; --i, n /= 16) {
res[i] = UPPER_XDIGITS[(n & 0x0f)];
}
return res;
}
template<typename T, typename... U> template<typename T, typename... U>
typename std::enable_if<!std::is_array<T>::value, std::unique_ptr<T>>::type typename std::enable_if<!std::is_array<T>::value, std::unique_ptr<T>>::type
make_unique(U&&... u) make_unique(U&&... u)

View File

@ -101,4 +101,14 @@ void test_util_percent_encode_token(void)
CU_ASSERT("http%202" == util::percent_encode_token("http 2")); CU_ASSERT("http%202" == util::percent_encode_token("http 2"));
} }
void test_util_utox(void)
{
CU_ASSERT("0" == util::utox(0));
CU_ASSERT("1" == util::utox(1));
CU_ASSERT("F" == util::utox(15));
CU_ASSERT("10" == util::utox(16));
CU_ASSERT("3B9ACA07" == util::utox(1000000007));
CU_ASSERT("100000000" == util::utox(1LL << 32));
}
} // namespace shrpx } // namespace shrpx

View File

@ -32,6 +32,7 @@ void test_util_strieq(void);
void test_util_inp_strlower(void); void test_util_inp_strlower(void);
void test_util_to_base64(void); void test_util_to_base64(void);
void test_util_percent_encode_token(void); void test_util_percent_encode_token(void);
void test_util_utox(void);
} // namespace shrpx } // namespace shrpx