ffserver: fix unsafe snprintf() return usage.
authorMichael Niedermayer <michaelni@gmx.at>
Sun, 9 Sep 2012 12:10:11 +0000 (14:10 +0200)
committerMichael Niedermayer <michaelni@gmx.at>
Sun, 9 Sep 2012 12:10:11 +0000 (14:10 +0200)
Found-by: "Ronald S. Bultje" <rsbultje@gmail.com>
Signed-off-by: Michael Niedermayer <michaelni@gmx.at>
ffserver.c

index 2bd92a1..bd8d95e 100644 (file)
@@ -1566,7 +1566,7 @@ static int http_parse_request(HTTPContext *c)
     if (stream->stream_type == STREAM_TYPE_REDIRECT) {
         c->http_error = 301;
         q = c->buffer;
-        q += snprintf(q, c->buffer_size,
+        snprintf(q, c->buffer_size,
                       "HTTP/1.0 301 Moved\r\n"
                       "Location: %s\r\n"
                       "Content-type: text/html\r\n"
@@ -1574,6 +1574,7 @@ static int http_parse_request(HTTPContext *c)
                       "<html><head><title>Moved</title></head><body>\r\n"
                       "You should be <a href=\"%s\">redirected</a>.\r\n"
                       "</body></html>\r\n", stream->feed_filename, stream->feed_filename);
+        q += strlen(q);
         /* prepare output buffer */
         c->buffer_ptr = c->buffer;
         c->buffer_end = q;
@@ -1604,7 +1605,7 @@ static int http_parse_request(HTTPContext *c)
     if (c->post == 0 && max_bandwidth < current_bandwidth) {
         c->http_error = 503;
         q = c->buffer;
-        q += snprintf(q, c->buffer_size,
+        snprintf(q, c->buffer_size,
                       "HTTP/1.0 503 Server too busy\r\n"
                       "Content-type: text/html\r\n"
                       "\r\n"
@@ -1613,6 +1614,7 @@ static int http_parse_request(HTTPContext *c)
                       "<p>The bandwidth being served (including your stream) is %"PRIu64"kbit/sec, "
                       "and this exceeds the limit of %"PRIu64"kbit/sec.</p>\r\n"
                       "</body></html>\r\n", current_bandwidth, max_bandwidth);
+        q += strlen(q);
         /* prepare output buffer */
         c->buffer_ptr = c->buffer;
         c->buffer_end = q;
@@ -1655,7 +1657,7 @@ static int http_parse_request(HTTPContext *c)
                     q = c->buffer;
                     switch(redir_type) {
                     case REDIR_ASX:
-                        q += snprintf(q, c->buffer_size,
+                        snprintf(q, c->buffer_size,
                                       "HTTP/1.0 200 ASX Follows\r\n"
                                       "Content-type: video/x-ms-asf\r\n"
                                       "\r\n"
@@ -1663,22 +1665,25 @@ static int http_parse_request(HTTPContext *c)
                                       //"<!-- Autogenerated by ffserver -->\r\n"
                                       "<ENTRY><REF HREF=\"http://%s/%s%s\"/></ENTRY>\r\n"
                                       "</ASX>\r\n", hostbuf, filename, info);
+                        q += strlen(q);
                         break;
                     case REDIR_RAM:
-                        q += snprintf(q, c->buffer_size,
+                        snprintf(q, c->buffer_size,
                                       "HTTP/1.0 200 RAM Follows\r\n"
                                       "Content-type: audio/x-pn-realaudio\r\n"
                                       "\r\n"
                                       "# Autogenerated by ffserver\r\n"
                                       "http://%s/%s%s\r\n", hostbuf, filename, info);
+                        q += strlen(q);
                         break;
                     case REDIR_ASF:
-                        q += snprintf(q, c->buffer_size,
+                        snprintf(q, c->buffer_size,
                                       "HTTP/1.0 200 ASF Redirect follows\r\n"
                                       "Content-type: video/x-ms-asf\r\n"
                                       "\r\n"
                                       "[Reference]\r\n"
                                       "Ref1=http://%s/%s%s\r\n", hostbuf, filename, info);
+                        q += strlen(q);
                         break;
                     case REDIR_RTSP:
                         {
@@ -1688,12 +1693,13 @@ static int http_parse_request(HTTPContext *c)
                             p = strrchr(hostname, ':');
                             if (p)
                                 *p = '\0';
-                            q += snprintf(q, c->buffer_size,
+                            snprintf(q, c->buffer_size,
                                           "HTTP/1.0 200 RTSP Redirect follows\r\n"
                                           /* XXX: incorrect mime type ? */
                                           "Content-type: application/x-rtsp\r\n"
                                           "\r\n"
                                           "rtsp://%s:%d/%s\r\n", hostname, ntohs(my_rtsp_addr.sin_port), filename);
+                            q += strlen(q);
                         }
                         break;
                     case REDIR_SDP:
@@ -1702,10 +1708,11 @@ static int http_parse_request(HTTPContext *c)
                             int sdp_data_size, len;
                             struct sockaddr_in my_addr;
 
-                            q += snprintf(q, c->buffer_size,
+                            snprintf(q, c->buffer_size,
                                           "HTTP/1.0 200 OK\r\n"
                                           "Content-type: application/sdp\r\n"
                                           "\r\n");
+                            q += strlen(q);
 
                             len = sizeof(my_addr);
                             getsockname(c->fd, (struct sockaddr *)&my_addr, &len);
@@ -1824,12 +1831,12 @@ static int http_parse_request(HTTPContext *c)
     }
 
     /* prepare http header */
-    q = c->buffer;
-    q += snprintf(q, q - (char *) c->buffer + c->buffer_size, "HTTP/1.0 200 OK\r\n");
+    c->buffer[0] = 0;
+    av_strlcatf(c->buffer, c->buffer_size, "HTTP/1.0 200 OK\r\n");
     mime_type = c->stream->fmt->mime_type;
     if (!mime_type)
         mime_type = "application/x-octet-stream";
-    q += snprintf(q, q - (char *) c->buffer + c->buffer_size, "Pragma: no-cache\r\n");
+    av_strlcatf(c->buffer, c->buffer_size, "Pragma: no-cache\r\n");
 
     /* for asf, we need extra headers */
     if (!strcmp(c->stream->fmt->name,"asf_stream")) {
@@ -1837,10 +1844,11 @@ static int http_parse_request(HTTPContext *c)
 
         c->wmp_client_id = av_lfg_get(&random_state);
 
-        q += snprintf(q, q - (char *) c->buffer + c->buffer_size, "Server: Cougar 4.1.0.3923\r\nCache-Control: no-cache\r\nPragma: client-id=%d\r\nPragma: features=\"broadcast\"\r\n", c->wmp_client_id);
+        av_strlcatf(c->buffer, c->buffer_size, "Server: Cougar 4.1.0.3923\r\nCache-Control: no-cache\r\nPragma: client-id=%d\r\nPragma: features=\"broadcast\"\r\n", c->wmp_client_id);
     }
-    q += snprintf(q, q - (char *) c->buffer + c->buffer_size, "Content-Type: %s\r\n", mime_type);
-    q += snprintf(q, q - (char *) c->buffer + c->buffer_size, "\r\n");
+    av_strlcatf(c->buffer, c->buffer_size, "Content-Type: %s\r\n", mime_type);
+    av_strlcatf(c->buffer, c->buffer_size, "\r\n");
+    q = c->buffer + strlen(c->buffer);
 
     /* prepare output buffer */
     c->http_error = 0;
@@ -1851,7 +1859,7 @@ static int http_parse_request(HTTPContext *c)
  send_error:
     c->http_error = 404;
     q = c->buffer;
-    q += snprintf(q, c->buffer_size,
+    snprintf(q, c->buffer_size,
                   "HTTP/1.0 404 Not Found\r\n"
                   "Content-type: text/html\r\n"
                   "\r\n"
@@ -1859,6 +1867,7 @@ static int http_parse_request(HTTPContext *c)
                   "<head><title>404 Not Found</title></head>\n"
                   "<body>%s</body>\n"
                   "</html>\n", msg);
+    q += strlen(q);
     /* prepare output buffer */
     c->buffer_ptr = c->buffer;
     c->buffer_end = q;