Revision 6964d510

View differences:

libavformat/http.c
25 25
#include <strings.h>
26 26
#include "internal.h"
27 27
#include "network.h"
28
#include "http.h"
28 29
#include "os_support.h"
29 30
#include "httpauth.h"
30 31

  
......
46 47
    char location[URL_SIZE];
47 48
    HTTPAuthState auth_state;
48 49
    int init;
50
    unsigned char headers[BUFFER_SIZE];
49 51
} HTTPContext;
50 52

  
51 53
static int http_connect(URLContext *h, const char *path, const char *hoststr,
52 54
                        const char *auth, int *new_location);
53 55
static int http_write(URLContext *h, const uint8_t *buf, int size);
54 56

  
57
void ff_http_set_headers(URLContext *h, const char *headers)
58
{
59
    HTTPContext *s = h->priv_data;
60
    int len = strlen(headers);
61

  
62
    if (len && strcmp("\r\n", headers + len - 2))
63
        av_log(NULL, AV_LOG_ERROR, "No trailing CRLF found in HTTP header.\n");
64

  
65
    av_strlcpy(s->headers, headers, sizeof(s->headers));
66
}
55 67

  
56 68
/* return non zero if error */
57 69
static int http_open_cnx(URLContext *h)
......
137 149
    s->chunksize = -1;
138 150
    s->off = 0;
139 151
    s->init = 0;
152
    *s->headers = '\0';
140 153
    memset(&s->auth_state, 0, sizeof(s->auth_state));
141 154
    av_strlcpy(s->location, uri, URL_SIZE);
142 155

  
......
245 258
    return 1;
246 259
}
247 260

  
261
static inline int has_header(const char *str, const char *header)
262
{
263
    /* header + 2 to skip over CRLF prefix. (make sure you have one!) */
264
    return av_stristart(str, header + 2, NULL) || av_stristr(str, header);
265
}
266

  
248 267
static int http_connect(URLContext *h, const char *path, const char *hoststr,
249 268
                        const char *auth, int *new_location)
250 269
{
251 270
    HTTPContext *s = h->priv_data;
252 271
    int post, err;
253 272
    char line[1024];
273
    char headers[1024];
254 274
    char *authstr = NULL;
255 275
    int64_t off = s->off;
276
    int len = 0;
256 277

  
257 278

  
258 279
    /* send http header */
259 280
    post = h->flags & URL_WRONLY;
260 281
    authstr = ff_http_auth_create_response(&s->auth_state, auth, path,
261 282
                                        post ? "POST" : "GET");
283

  
284
    /* set default headers if needed */
285
    if (!has_header(s->headers, "\r\nUser-Agent: "))
286
       len += av_strlcatf(headers + len, sizeof(headers) - len,
287
                          "User-Agent: %s\r\n", LIBAVFORMAT_IDENT);
288
    if (!has_header(s->headers, "\r\nAccept: "))
289
        len += av_strlcpy(headers + len, "Accept: */*\r\n",
290
                          sizeof(headers) - len);
291
    if (!has_header(s->headers, "\r\nRange: "))
292
        len += av_strlcatf(headers + len, sizeof(headers) - len,
293
                           "Range: bytes=%"PRId64"\r\n", s->off);
294
    if (!has_header(s->headers, "\r\nConnection: "))
295
        len += av_strlcpy(headers + len, "Connection: close\r\n",
296
                          sizeof(headers)-len);
297
    if (!has_header(s->headers, "\r\nHost: "))
298
        len += av_strlcatf(headers + len, sizeof(headers) - len,
299
                           "Host: %s\r\n", hoststr);
300

  
301
    /* now add in custom headers */
302
    av_strlcpy(headers+len, s->headers, sizeof(headers)-len);
303

  
262 304
    snprintf(s->buffer, sizeof(s->buffer),
263 305
             "%s %s HTTP/1.1\r\n"
264
             "User-Agent: %s\r\n"
265
             "Accept: */*\r\n"
266
             "Range: bytes=%"PRId64"-\r\n"
267
             "Host: %s\r\n"
268 306
             "%s"
269
             "Connection: close\r\n"
307
             "%s"
270 308
             "%s"
271 309
             "\r\n",
272 310
             post ? "POST" : "GET",
273 311
             path,
274
             LIBAVFORMAT_IDENT,
275
             s->off,
276
             hoststr,
277
             authstr ? authstr : "",
278
             post ? "Transfer-Encoding: chunked\r\n" : "");
312
             post ? "Transfer-Encoding: chunked\r\n" : "",
313
             headers,
314
             authstr ? authstr : "");
279 315

  
280 316
    av_freep(&authstr);
281 317
    if (http_write(h, s->buffer, strlen(s->buffer)) < 0)
libavformat/http.h
1
/*
2
 * HTTP definitions
3
 * Copyright (c) 2010 Josh Allmann
4
 *
5
 * This file is part of FFmpeg.
6
 *
7
 * FFmpeg is free software; you can redistribute it and/or
8
 * modify it under the terms of the GNU Lesser General Public
9
 * License as published by the Free Software Foundation; either
10
 * version 2.1 of the License, or (at your option) any later version.
11
 *
12
 * FFmpeg is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15
 * Lesser General Public License for more details.
16
 *
17
 * You should have received a copy of the GNU Lesser General Public
18
 * License along with FFmpeg; if not, write to the Free Software
19
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20
 */
21
#ifndef AVFORMAT_HTTP_H
22
#define AVFORMAT_HTTP_H
23

  
24
/**
25
 * Sets custom HTTP headers.
26
 * A trailing CRLF ("\r\n") is required for custom headers.
27
 * Passing in an empty header string ("\0") will reset to defaults.
28
 *
29
 * The following headers can be overriden by custom values,
30
 * otherwise they will be set to their defaults.
31
 *  -User-Agent
32
 *  -Accept
33
 *  -Range
34
 *  -Host
35
 *  -Connection
36
 *
37
 * @param h URL context for this HTTP connection
38
 * @param headers the custom headers to set
39
 */
40
void ff_http_set_headers(URLContext *h, const char *headers);
41

  
42
#endif /* AVFORMAT_HTTP_H */

Also available in: Unified diff