Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-30 Thread Micah Galizia
Hi,

This version fixes the cstr leak and explicitly frees tmp when allocating 
cookies fails. Freeing tmp also means we don't need to free *cookies when ret 
is less than zero.

I've also formatted the name properly, so it'll show up as a new thread.

Thanks in advance.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-28 Thread Michael Niedermayer
On Wed, Apr 26, 2017 at 09:48:09PM -0400, Micah Galizia wrote:
> Signed-off-by: Micah Galizia 
> ---
>  libavformat/http.c | 212 
> +++--
>  1 file changed, 155 insertions(+), 57 deletions(-)

forgot to mention
the commit message "Ignore expired cookies"
needs lib & file/ module prefix

no major issue, i add these on pushing unless i forget

[...]
-- 
Michael GnuPG fingerprint: 9FF2128B147EF6730BADF133611EC787040B0FAB

I have often repented speaking, but never of holding my tongue.
-- Xenocrates


signature.asc
Description: Digital signature
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-28 Thread Michael Niedermayer
On Wed, Apr 26, 2017 at 09:48:09PM -0400, Micah Galizia wrote:
> Signed-off-by: Micah Galizia 
> ---
>  libavformat/http.c | 212 
> +++--
>  1 file changed, 155 insertions(+), 57 deletions(-)
> 
> diff --git a/libavformat/http.c b/libavformat/http.c
> index 293a8a7204..58fc3902ab 100644
> --- a/libavformat/http.c
> +++ b/libavformat/http.c
> @@ -29,6 +29,7 @@
>  #include "libavutil/avstring.h"
>  #include "libavutil/opt.h"
>  #include "libavutil/time.h"
> +#include "libavutil/parseutils.h"
>  
>  #include "avformat.h"
>  #include "http.h"
> @@ -48,6 +49,8 @@
>  #define MAX_REDIRECTS 8
>  #define HTTP_SINGLE   1
>  #define HTTP_MUTLI2
> +#define MAX_EXPIRY19
> +#define WHITESPACES " \n\t\r"
>  typedef enum {
>  LOWER_PROTO,
>  READ_HEADERS,
> @@ -680,10 +683,110 @@ static int parse_icy(HTTPContext *s, const char *tag, 
> const char *p)
>  return 0;
>  }
>  
> +static int parse_set_cookie_expiry_time(const char *exp_str, struct tm *buf)
> +{
> +char exp_buf[MAX_EXPIRY];
> +int i, j, exp_buf_len = MAX_EXPIRY-1;
> +char *expiry;
> +
> +// strip off any punctuation or whitespace
> +for (i = 0, j = 0; exp_str[i] != '\0' && j < exp_buf_len; i++) {
> +if ((exp_str[i] >= '0' && exp_str[i] <= '9') ||
> +(exp_str[i] >= 'A' && exp_str[i] <= 'Z') ||
> +(exp_str[i] >= 'a' && exp_str[i] <= 'z')) {
> +exp_buf[j] = exp_str[i];
> +j++;
> +}
> +}
> +exp_buf[j] = '\0';
> +expiry = exp_buf;
> +
> +// move the string beyond the day of week
> +while ((*expiry < '0' || *expiry > '9') && *expiry != '\0')
> +expiry++;
> +
> +return av_small_strptime(expiry, "%d%b%Y%H%M%S", buf) ? 0 : 
> AVERROR(EINVAL);
> +}
> +

> +static int parse_set_cookie(const char *set_cookie, AVDictionary **dict)
> +{
> +char *param, *next_param, *cstr, *back;
> +
> +if (!(cstr = av_strdup(set_cookie)))
> +return AVERROR(EINVAL);
> +
> +// strip any trailing whitespace
> +back = [strlen(cstr)-1];
> +while (strchr(WHITESPACES, *back)) {
> +*back='\0';
> +back--;
> +}
> +
> +next_param = cstr;
> +while ((param = av_strtok(next_param, ";", _param))) {
> +char *name, *value;
> +param += strspn(param, WHITESPACES);
> +if ((name = av_strtok(param, "=", ))) {
> +if (av_dict_set(dict, name, value, 0) < 0)
> +return -1;

this leaks cstr


[...]
> @@ -876,87 +979,82 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> const char *path,
>  av_dict_free(>cookie_dict);
>  
>  *cookies = NULL;
> -while ((cookie = av_strtok(set_cookies, "\n", ))) {
> -int domain_offset = 0;
> -char *param, *next_param, *cdomain = NULL, *cpath = NULL, *cvalue = 
> NULL;
> -set_cookies = NULL;
> +while ((cookie = av_strtok(next, "\n", ))) {
> +AVDictionary *cookie_params = NULL;
> +AVDictionaryEntry *cookie_entry, *e;
>  
>  // store the cookie in a dict in case it is updated in the response
>  if (parse_cookie(s, cookie, >cookie_dict))
>  av_log(s, AV_LOG_WARNING, "Unable to parse '%s'\n", cookie);
>  
> -while ((param = av_strtok(cookie, "; ", _param))) {
> -if (cookie) {
> -// first key-value pair is the actual cookie value
> -cvalue = av_strdup(param);
> -cookie = NULL;
> -} else if (!av_strncasecmp("path=",   param, 5)) {
> -av_free(cpath);
> -cpath = av_strdup([5]);
> -} else if (!av_strncasecmp("domain=", param, 7)) {
> -// if the cookie specifies a sub-domain, skip the leading 
> dot thereby
> -// supporting URLs that point to sub-domains and the master 
> domain
> -int leading_dot = (param[7] == '.');
> -av_free(cdomain);
> -cdomain = av_strdup([7+leading_dot]);
> -} else {
> -// ignore unknown attributes
> -}
> +// continue on to the next cookie if this one cannot be parsed
> +if (parse_set_cookie(cookie, _params))
> +continue;
> +
> +// if the cookie has no value, skip it
> +cookie_entry = av_dict_get(cookie_params, "", NULL, 
> AV_DICT_IGNORE_SUFFIX);
> +if (!cookie_entry || !cookie_entry->value) {
> +av_dict_free(_params);
> +continue;
>  }
> -if (!cdomain)
> -cdomain = av_strdup(domain);
> -
> -// ensure all of the necessary values are valid
> -if (!cdomain || !cpath || !cvalue) {
> -av_log(s, AV_LOG_WARNING,
> -   "Invalid cookie found, no value, path or domain 
> specified\n");
> -goto done_cookie;
> +
> +// if the cookie has expired, don't add it
> +if ((e = 

Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-26 Thread Micah Galizia
Thanks for the review, new fix checks av_dict_set return.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-26 Thread Micah Galizia
Signed-off-by: Micah Galizia 
---
 libavformat/http.c | 212 +++--
 1 file changed, 155 insertions(+), 57 deletions(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 293a8a7204..58fc3902ab 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -29,6 +29,7 @@
 #include "libavutil/avstring.h"
 #include "libavutil/opt.h"
 #include "libavutil/time.h"
+#include "libavutil/parseutils.h"
 
 #include "avformat.h"
 #include "http.h"
@@ -48,6 +49,8 @@
 #define MAX_REDIRECTS 8
 #define HTTP_SINGLE   1
 #define HTTP_MUTLI2
+#define MAX_EXPIRY19
+#define WHITESPACES " \n\t\r"
 typedef enum {
 LOWER_PROTO,
 READ_HEADERS,
@@ -680,10 +683,110 @@ static int parse_icy(HTTPContext *s, const char *tag, 
const char *p)
 return 0;
 }
 
+static int parse_set_cookie_expiry_time(const char *exp_str, struct tm *buf)
+{
+char exp_buf[MAX_EXPIRY];
+int i, j, exp_buf_len = MAX_EXPIRY-1;
+char *expiry;
+
+// strip off any punctuation or whitespace
+for (i = 0, j = 0; exp_str[i] != '\0' && j < exp_buf_len; i++) {
+if ((exp_str[i] >= '0' && exp_str[i] <= '9') ||
+(exp_str[i] >= 'A' && exp_str[i] <= 'Z') ||
+(exp_str[i] >= 'a' && exp_str[i] <= 'z')) {
+exp_buf[j] = exp_str[i];
+j++;
+}
+}
+exp_buf[j] = '\0';
+expiry = exp_buf;
+
+// move the string beyond the day of week
+while ((*expiry < '0' || *expiry > '9') && *expiry != '\0')
+expiry++;
+
+return av_small_strptime(expiry, "%d%b%Y%H%M%S", buf) ? 0 : 
AVERROR(EINVAL);
+}
+
+static int parse_set_cookie(const char *set_cookie, AVDictionary **dict)
+{
+char *param, *next_param, *cstr, *back;
+
+if (!(cstr = av_strdup(set_cookie)))
+return AVERROR(EINVAL);
+
+// strip any trailing whitespace
+back = [strlen(cstr)-1];
+while (strchr(WHITESPACES, *back)) {
+*back='\0';
+back--;
+}
+
+next_param = cstr;
+while ((param = av_strtok(next_param, ";", _param))) {
+char *name, *value;
+param += strspn(param, WHITESPACES);
+if ((name = av_strtok(param, "=", ))) {
+if (av_dict_set(dict, name, value, 0) < 0)
+return -1;
+}
+}
+
+av_free(cstr);
+return 0;
+}
+
 static int parse_cookie(HTTPContext *s, const char *p, AVDictionary **cookies)
 {
+AVDictionary *new_params = NULL;
+AVDictionaryEntry *e, *cookie_entry;
 char *eql, *name;
 
+// ensure the cookie is parsable
+if (parse_set_cookie(p, _params))
+return -1;
+
+// if there is no cookie value there is nothing to parse
+cookie_entry = av_dict_get(new_params, "", NULL, AV_DICT_IGNORE_SUFFIX);
+if (!cookie_entry || !cookie_entry->value) {
+av_dict_free(_params);
+return -1;
+}
+
+// ensure the cookie is not expired or older than an existing value
+if ((e = av_dict_get(new_params, "expires", NULL, 0)) && e->value) {
+struct tm new_tm = {0};
+if (!parse_set_cookie_expiry_time(e->value, _tm)) {
+AVDictionaryEntry *e2;
+
+// if the cookie has already expired ignore it
+if (av_timegm(_tm) < av_gettime() / 100) {
+av_dict_free(_params);
+return -1;
+}
+
+// only replace an older cookie with the same name
+e2 = av_dict_get(*cookies, cookie_entry->key, NULL, 0);
+if (e2 && e2->value) {
+AVDictionary *old_params = NULL;
+if (!parse_set_cookie(p, _params)) {
+e2 = av_dict_get(old_params, "expires", NULL, 0);
+if (e2 && e2->value) {
+struct tm old_tm = {0};
+if (!parse_set_cookie_expiry_time(e->value, _tm)) {
+if (av_timegm(_tm) < av_timegm(_tm)) {
+av_dict_free(_params);
+av_dict_free(_params);
+return -1;
+}
+}
+}
+}
+av_dict_free(_params);
+}
+}
+}
+
 // duplicate the cookie name (dict will dupe the value)
 if (!(eql = strchr(p, '='))) return AVERROR(EINVAL);
 if (!(name = av_strndup(p, eql - p))) return AVERROR(ENOMEM);
@@ -868,7 +971,7 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 // cookie strings will look like Set-Cookie header field values.  Multiple
 // Set-Cookie fields will result in multiple values delimited by a newline
 int ret = 0;
-char *next, *cookie, *set_cookies = av_strdup(s->cookies), *cset_cookies = 
set_cookies;
+char *cookie, *set_cookies = av_strdup(s->cookies), *next = set_cookies;
 
 if (!set_cookies) return AVERROR(EINVAL);
 
@@ -876,87 +979,82 @@ static 

Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-25 Thread Michael Niedermayer
On Sat, Apr 08, 2017 at 09:05:46PM -0400, Micah Galizia wrote:
> Signed-off-by: Micah Galizia 
> ---
>  libavformat/http.c | 211 
> ++---
>  1 file changed, 154 insertions(+), 57 deletions(-)
> 
> diff --git a/libavformat/http.c b/libavformat/http.c
> index 293a8a7204..425711aab5 100644
> --- a/libavformat/http.c
> +++ b/libavformat/http.c
> @@ -29,6 +29,7 @@
>  #include "libavutil/avstring.h"
>  #include "libavutil/opt.h"
>  #include "libavutil/time.h"
> +#include "libavutil/parseutils.h"
>  
>  #include "avformat.h"
>  #include "http.h"
> @@ -48,6 +49,8 @@
>  #define MAX_REDIRECTS 8
>  #define HTTP_SINGLE   1
>  #define HTTP_MUTLI2
> +#define MAX_EXPIRY19
> +#define WHITESPACES " \n\t\r"
>  typedef enum {
>  LOWER_PROTO,
>  READ_HEADERS,
> @@ -680,10 +683,109 @@ static int parse_icy(HTTPContext *s, const char *tag, 
> const char *p)
>  return 0;
>  }
>  
> +static int parse_set_cookie_expiry_time(const char *exp_str, struct tm *buf)
> +{
> +char exp_buf[MAX_EXPIRY];
> +int i, j, exp_buf_len = MAX_EXPIRY-1;
> +char *expiry;
> +
> +// strip off any punctuation or whitespace
> +for (i = 0, j = 0; exp_str[i] != '\0' && j < exp_buf_len; i++) {
> +if ((exp_str[i] >= '0' && exp_str[i] <= '9') ||
> +(exp_str[i] >= 'A' && exp_str[i] <= 'Z') ||
> +(exp_str[i] >= 'a' && exp_str[i] <= 'z')) {
> +exp_buf[j] = exp_str[i];
> +j++;
> +}
> +}
> +exp_buf[j] = '\0';
> +expiry = exp_buf;
> +
> +// move the string beyond the day of week
> +while ((*expiry < '0' || *expiry > '9') && *expiry != '\0')
> +expiry++;
> +
> +return av_small_strptime(expiry, "%d%b%Y%H%M%S", buf) ? 0 : 
> AVERROR(EINVAL);
> +}
> +
> +static int parse_set_cookie(const char *set_cookie, AVDictionary **dict)
> +{
> +char *param, *next_param, *cstr, *back;
> +
> +if (!(cstr = av_strdup(set_cookie)))
> +return AVERROR(EINVAL);
> +
> +// strip any trailing whitespace
> +back = [strlen(cstr)-1];
> +while (strchr(WHITESPACES, *back)) {
> +*back='\0';
> +back--;
> +}
> +
> +next_param = cstr;
> +while ((param = av_strtok(next_param, ";", _param))) {
> +char *name, *value;
> +param += strspn(param, WHITESPACES);
> +if ((name = av_strtok(param, "=", ))) {

> +av_dict_set(dict, name, value, 0);

missing failure check

also if you get no reviewes of patches and are interrested in
the code, try to suggest to help with maintaining it, if noone objects
send a patch that adds you to MAINTAINERs

thx

[...]
-- 
Michael GnuPG fingerprint: 9FF2128B147EF6730BADF133611EC787040B0FAB

It is what and why we do it that matters, not just one of them.


signature.asc
Description: Digital signature
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-24 Thread Micah Galizia

On 2017-04-08 09:05 PM, Micah Galizia wrote:



Is there something I can do to get this reviewed?

Thanks in advance.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-14 Thread Micah Galizia

On 2017-04-08 09:05 PM, Micah Galizia wrote:

Signed-off-by: Micah Galizia 




Hello,

Has anyone had a chance to review this? I was hoping to get the rework 
(if needed) done this weekend.


Thanks,
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-04-08 Thread Micah Galizia
Signed-off-by: Micah Galizia 
---
 libavformat/http.c | 211 ++---
 1 file changed, 154 insertions(+), 57 deletions(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 293a8a7204..425711aab5 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -29,6 +29,7 @@
 #include "libavutil/avstring.h"
 #include "libavutil/opt.h"
 #include "libavutil/time.h"
+#include "libavutil/parseutils.h"
 
 #include "avformat.h"
 #include "http.h"
@@ -48,6 +49,8 @@
 #define MAX_REDIRECTS 8
 #define HTTP_SINGLE   1
 #define HTTP_MUTLI2
+#define MAX_EXPIRY19
+#define WHITESPACES " \n\t\r"
 typedef enum {
 LOWER_PROTO,
 READ_HEADERS,
@@ -680,10 +683,109 @@ static int parse_icy(HTTPContext *s, const char *tag, 
const char *p)
 return 0;
 }
 
+static int parse_set_cookie_expiry_time(const char *exp_str, struct tm *buf)
+{
+char exp_buf[MAX_EXPIRY];
+int i, j, exp_buf_len = MAX_EXPIRY-1;
+char *expiry;
+
+// strip off any punctuation or whitespace
+for (i = 0, j = 0; exp_str[i] != '\0' && j < exp_buf_len; i++) {
+if ((exp_str[i] >= '0' && exp_str[i] <= '9') ||
+(exp_str[i] >= 'A' && exp_str[i] <= 'Z') ||
+(exp_str[i] >= 'a' && exp_str[i] <= 'z')) {
+exp_buf[j] = exp_str[i];
+j++;
+}
+}
+exp_buf[j] = '\0';
+expiry = exp_buf;
+
+// move the string beyond the day of week
+while ((*expiry < '0' || *expiry > '9') && *expiry != '\0')
+expiry++;
+
+return av_small_strptime(expiry, "%d%b%Y%H%M%S", buf) ? 0 : 
AVERROR(EINVAL);
+}
+
+static int parse_set_cookie(const char *set_cookie, AVDictionary **dict)
+{
+char *param, *next_param, *cstr, *back;
+
+if (!(cstr = av_strdup(set_cookie)))
+return AVERROR(EINVAL);
+
+// strip any trailing whitespace
+back = [strlen(cstr)-1];
+while (strchr(WHITESPACES, *back)) {
+*back='\0';
+back--;
+}
+
+next_param = cstr;
+while ((param = av_strtok(next_param, ";", _param))) {
+char *name, *value;
+param += strspn(param, WHITESPACES);
+if ((name = av_strtok(param, "=", ))) {
+av_dict_set(dict, name, value, 0);
+}
+}
+
+av_free(cstr);
+return 0;
+}
+
 static int parse_cookie(HTTPContext *s, const char *p, AVDictionary **cookies)
 {
+AVDictionary *new_params = NULL;
+AVDictionaryEntry *e, *cookie_entry;
 char *eql, *name;
 
+// ensure the cookie is parsable
+if (parse_set_cookie(p, _params))
+return -1;
+
+// if there is no cookie value there is nothing to parse
+cookie_entry = av_dict_get(new_params, "", NULL, AV_DICT_IGNORE_SUFFIX);
+if (!cookie_entry || !cookie_entry->value) {
+av_dict_free(_params);
+return -1;
+}
+
+// ensure the cookie is not expired or older than an existing value
+if ((e = av_dict_get(new_params, "expires", NULL, 0)) && e->value) {
+struct tm new_tm = {0};
+if (!parse_set_cookie_expiry_time(e->value, _tm)) {
+AVDictionaryEntry *e2;
+
+// if the cookie has already expired ignore it
+if (av_timegm(_tm) < av_gettime() / 100) {
+av_dict_free(_params);
+return -1;
+}
+
+// only replace an older cookie with the same name
+e2 = av_dict_get(*cookies, cookie_entry->key, NULL, 0);
+if (e2 && e2->value) {
+AVDictionary *old_params = NULL;
+if (!parse_set_cookie(p, _params)) {
+e2 = av_dict_get(old_params, "expires", NULL, 0);
+if (e2 && e2->value) {
+struct tm old_tm = {0};
+if (!parse_set_cookie_expiry_time(e->value, _tm)) {
+if (av_timegm(_tm) < av_timegm(_tm)) {
+av_dict_free(_params);
+av_dict_free(_params);
+return -1;
+}
+}
+}
+}
+av_dict_free(_params);
+}
+}
+}
+
 // duplicate the cookie name (dict will dupe the value)
 if (!(eql = strchr(p, '='))) return AVERROR(EINVAL);
 if (!(name = av_strndup(p, eql - p))) return AVERROR(ENOMEM);
@@ -868,7 +970,7 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 // cookie strings will look like Set-Cookie header field values.  Multiple
 // Set-Cookie fields will result in multiple values delimited by a newline
 int ret = 0;
-char *next, *cookie, *set_cookies = av_strdup(s->cookies), *cset_cookies = 
set_cookies;
+char *cookie, *set_cookies = av_strdup(s->cookies), *next = set_cookies;
 
 if (!set_cookies) return AVERROR(EINVAL);
 
@@ -876,87 +978,82 @@ static int get_cookies(HTTPContext *s, char 

Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-31 Thread Alexander Strasser
Hi Nicolas!

On 2017-03-30 22:12 +0200, Nicolas George wrote:
> Le decadi 10 germinal, an CCXXV, Alexander Strasser a écrit :
> > If expiry is zero terminated and you are going through it one byte at a 
> > time,
> > you could omit the strlen call and just check if expiry[i] is non zero.
> > 
> > It's maybe the more common idiom too.
> 
> On the other hand, code that does not need a 0-terminated string is more
> generic.

  This code depends already on a 0-terminated string. Otherwise the call of
strlen before would be wrong. Also the later loop is also written against
a 0-terminated string. IMHO for this patch it's not really important
to avoid relying on 0-terminated string.


> I am thinking of the ideas I posted a few months ago about reworking the
> options system to avoid escaping hell. Parsers for various types must be
> able to work in the middle of strings with foreign delimiters. Code that
> is already capable of working in the middle of a string would be easier
> to integrate.
> 
> Of course, all this is in the far future. I will not insist on all new
> code to be able to work like that, but I would like it nonetheless. And
> if it is already written that way, let us keep it.

  I am not in general against getting rid of 0-terminated string in
some places. I often thought of this too.


> All in all, 0-terminated strings were a terrible terrible idea.

Yes, they probably still are a bad idea.


  Alexander
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-30 Thread Micah Galizia
Thanks for those comments -- I'll get rid of the strlen in the
upcoming patch but, Nicolas, you lost me there.

Anyway, this patch only does half the job -- I have a new one that is
unfortunately larger, but has taken prior advice to break cookies into
dicts.

On Thu, Mar 30, 2017 at 4:12 PM, Nicolas George  wrote:
> Le decadi 10 germinal, an CCXXV, Alexander Strasser a écrit :
>> If expiry is zero terminated and you are going through it one byte at a time,
>> you could omit the strlen call and just check if expiry[i] is non zero.
>>
>> It's maybe the more common idiom too.
>
> On the other hand, code that does not need a 0-terminated string is more
> generic.
>
> I am thinking of the ideas I posted a few months ago about reworking the
> options system to avoid escaping hell. Parsers for various types must be
> able to work in the middle of strings with foreign delimiters. Code that
> is already capable of working in the middle of a string would be easier
> to integrate.
>
> Of course, all this is in the far future. I will not insist on all new
> code to be able to work like that, but I would like it nonetheless. And
> if it is already written that way, let us keep it.
>
> All in all, 0-terminated strings were a terrible terrible idea.
>
> Regards,
>
> --
>   Nicolas George
>
> ___
> ffmpeg-devel mailing list
> ffmpeg-devel@ffmpeg.org
> http://ffmpeg.org/mailman/listinfo/ffmpeg-devel
>



-- 
"The mark of an immature man is that he wants to die nobly for a
cause, while the mark of the mature man is that he wants to live
humbly for one."   --W. Stekel
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-30 Thread Nicolas George
Le decadi 10 germinal, an CCXXV, Alexander Strasser a écrit :
> If expiry is zero terminated and you are going through it one byte at a time,
> you could omit the strlen call and just check if expiry[i] is non zero.
> 
> It's maybe the more common idiom too.

On the other hand, code that does not need a 0-terminated string is more
generic.

I am thinking of the ideas I posted a few months ago about reworking the
options system to avoid escaping hell. Parsers for various types must be
able to work in the middle of strings with foreign delimiters. Code that
is already capable of working in the middle of a string would be easier
to integrate.

Of course, all this is in the far future. I will not insist on all new
code to be able to work like that, but I would like it nonetheless. And
if it is already written that way, let us keep it.

All in all, 0-terminated strings were a terrible terrible idea.

Regards,

-- 
  Nicolas George


signature.asc
Description: Digital signature
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-30 Thread Alexander Strasser
Hi!

On 2017-03-29 19:42 -0400, Micah Galizia wrote:
> I'm going to have to submit a v2 for this patch (hopefully soon) --
> this version only accomplishes half the job: not sending expired
> cookies. The change should also prevent storing them in the first
> place.
> 
> Regardless, thanks for your help on this one.

I noticed one or two things while reading the patch. See below.

> On Sat, Mar 25, 2017 at 7:27 PM, Micah Galizia  wrote:
> > Signed-off-by: Micah Galizia 
> > ---
> >  libavformat/http.c | 43 +++
> >  1 file changed, 39 insertions(+), 4 deletions(-)
> >
> > diff --git a/libavformat/http.c b/libavformat/http.c
> > index 293a8a7..53fae2a 100644
> > --- a/libavformat/http.c
> > +++ b/libavformat/http.c
> > @@ -29,6 +29,7 @@
> >  #include "libavutil/avstring.h"
> >  #include "libavutil/opt.h"
> >  #include "libavutil/time.h"
> > +#include "libavutil/parseutils.h"
> >
> >  #include "avformat.h"
> >  #include "http.h"
> > @@ -48,6 +49,8 @@
> >  #define MAX_REDIRECTS 8
> >  #define HTTP_SINGLE   1
> >  #define HTTP_MUTLI2
> > +#define MAX_EXPIRY19
> > +#define WHITESPACES " \n\t\r"
> >  typedef enum {
> >  LOWER_PROTO,
> >  READ_HEADERS,
> > @@ -877,15 +880,20 @@ static int get_cookies(HTTPContext *s, char 
> > **cookies, const char *path,
> >
> >  *cookies = NULL;
> >  while ((cookie = av_strtok(set_cookies, "\n", ))) {
> > -int domain_offset = 0;
> > +int domain_offset = 0, expired = 0;
> >  char *param, *next_param, *cdomain = NULL, *cpath = NULL, *cvalue 
> > = NULL;
> > +char exp_buf[MAX_EXPIRY];
> >  set_cookies = NULL;
> >
> >  // store the cookie in a dict in case it is updated in the response
> >  if (parse_cookie(s, cookie, >cookie_dict))
> >  av_log(s, AV_LOG_WARNING, "Unable to parse '%s'\n", cookie);
> >
> > -while ((param = av_strtok(cookie, "; ", _param))) {
> > +while ((param = av_strtok(cookie, ";", _param))) {
> > +
> > +// move past any leading whitespace
> > +param += strspn(param, WHITESPACES);
> > +
> >  if (cookie) {
> >  // first key-value pair is the actual cookie value
> >  cvalue = av_strdup(param);
> > @@ -899,6 +907,33 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> > const char *path,
> >  int leading_dot = (param[7] == '.');
> >  av_free(cdomain);
> >  cdomain = av_strdup([7+leading_dot]);
> > +} else if (!av_strncasecmp("expires=", param, 8)) {
> > +int i, j, exp_len, exp_buf_len = MAX_EXPIRY-1;
> > +struct tm tm_buf = {0};
> > +char *expiry = [8];
> > +
> > +// strip off any punctuation or whitespace
> > +exp_len = strlen(expiry);
> > +for (i = 0, j = 0; i < exp_len && j < exp_buf_len; i++) {
> > +if ((expiry[i] >= '0' && expiry[i] <= '9') ||
> > +(expiry[i] >= 'A' && expiry[i] <= 'Z') ||
> > +(expiry[i] >= 'a' && expiry[i] <= 'z')) {
> > +exp_buf[j] = expiry[i];
> > +j++;
> > +}
> > +}

If expiry is zero terminated and you are going through it one byte at a time,
you could omit the strlen call and just check if expiry[i] is non zero.

It's maybe the more common idiom too.

> > +exp_buf[j] = '\0';
> > +expiry = exp_buf;
> > +
> > +// move the string beyond the day of week
> > +while ((*expiry < '0' || *expiry > '9') && *expiry != '\0')
> > +expiry++;
> > +
> > +if (av_small_strptime(expiry, "%d%b%Y%H%M%S", _buf)) {
> > +time_t now = av_gettime() / 100;
> > +if (av_timegm(_buf) < now)
> > +expired = 1;
> > +}

The patch seems a bit long for what it achieves. I don't really have any
better idea for now. One thing that came to mind: you might be able to
merge the skipping-day-of-week loop into the first loop that writes the
stripped down date string into the buffer.


  Alexander

> >  } else {
> >  // ignore unknown attributes
> >  }
> > @@ -907,9 +942,9 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> > const char *path,
> >  cdomain = av_strdup(domain);
> >
> >  // ensure all of the necessary values are valid
> > -if (!cdomain || !cpath || !cvalue) {
> > +if (expired || !cdomain || !cpath || !cvalue ) {
> >  av_log(s, AV_LOG_WARNING,
> > -   "Invalid cookie found, no value, path or domain 
> > specified\n");
> > +   "Invalid cookie found, expired or no value, path or 
> > domain 

Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-29 Thread Micah Galizia
Hi,

I'm going to have to submit a v2 for this patch (hopefully soon) --
this version only accomplishes half the job: not sending expired
cookies. The change should also prevent storing them in the first
place.

Regardless, thanks for your help on this one.

On Sat, Mar 25, 2017 at 7:27 PM, Micah Galizia  wrote:
> Signed-off-by: Micah Galizia 
> ---
>  libavformat/http.c | 43 +++
>  1 file changed, 39 insertions(+), 4 deletions(-)
>
> diff --git a/libavformat/http.c b/libavformat/http.c
> index 293a8a7..53fae2a 100644
> --- a/libavformat/http.c
> +++ b/libavformat/http.c
> @@ -29,6 +29,7 @@
>  #include "libavutil/avstring.h"
>  #include "libavutil/opt.h"
>  #include "libavutil/time.h"
> +#include "libavutil/parseutils.h"
>
>  #include "avformat.h"
>  #include "http.h"
> @@ -48,6 +49,8 @@
>  #define MAX_REDIRECTS 8
>  #define HTTP_SINGLE   1
>  #define HTTP_MUTLI2
> +#define MAX_EXPIRY19
> +#define WHITESPACES " \n\t\r"
>  typedef enum {
>  LOWER_PROTO,
>  READ_HEADERS,
> @@ -877,15 +880,20 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> const char *path,
>
>  *cookies = NULL;
>  while ((cookie = av_strtok(set_cookies, "\n", ))) {
> -int domain_offset = 0;
> +int domain_offset = 0, expired = 0;
>  char *param, *next_param, *cdomain = NULL, *cpath = NULL, *cvalue = 
> NULL;
> +char exp_buf[MAX_EXPIRY];
>  set_cookies = NULL;
>
>  // store the cookie in a dict in case it is updated in the response
>  if (parse_cookie(s, cookie, >cookie_dict))
>  av_log(s, AV_LOG_WARNING, "Unable to parse '%s'\n", cookie);
>
> -while ((param = av_strtok(cookie, "; ", _param))) {
> +while ((param = av_strtok(cookie, ";", _param))) {
> +
> +// move past any leading whitespace
> +param += strspn(param, WHITESPACES);
> +
>  if (cookie) {
>  // first key-value pair is the actual cookie value
>  cvalue = av_strdup(param);
> @@ -899,6 +907,33 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> const char *path,
>  int leading_dot = (param[7] == '.');
>  av_free(cdomain);
>  cdomain = av_strdup([7+leading_dot]);
> +} else if (!av_strncasecmp("expires=", param, 8)) {
> +int i, j, exp_len, exp_buf_len = MAX_EXPIRY-1;
> +struct tm tm_buf = {0};
> +char *expiry = [8];
> +
> +// strip off any punctuation or whitespace
> +exp_len = strlen(expiry);
> +for (i = 0, j = 0; i < exp_len && j < exp_buf_len; i++) {
> +if ((expiry[i] >= '0' && expiry[i] <= '9') ||
> +(expiry[i] >= 'A' && expiry[i] <= 'Z') ||
> +(expiry[i] >= 'a' && expiry[i] <= 'z')) {
> +exp_buf[j] = expiry[i];
> +j++;
> +}
> +}
> +exp_buf[j] = '\0';
> +expiry = exp_buf;
> +
> +// move the string beyond the day of week
> +while ((*expiry < '0' || *expiry > '9') && *expiry != '\0')
> +expiry++;
> +
> +if (av_small_strptime(expiry, "%d%b%Y%H%M%S", _buf)) {
> +time_t now = av_gettime() / 100;
> +if (av_timegm(_buf) < now)
> +expired = 1;
> +}
>  } else {
>  // ignore unknown attributes
>  }
> @@ -907,9 +942,9 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> const char *path,
>  cdomain = av_strdup(domain);
>
>  // ensure all of the necessary values are valid
> -if (!cdomain || !cpath || !cvalue) {
> +if (expired || !cdomain || !cpath || !cvalue ) {
>  av_log(s, AV_LOG_WARNING,
> -   "Invalid cookie found, no value, path or domain 
> specified\n");
> +   "Invalid cookie found, expired or no value, path or 
> domain specified\n");
>  goto done_cookie;
>  }
>
> --
> 2.9.3
>



-- 
"The mark of an immature man is that he wants to die nobly for a
cause, while the mark of the mature man is that he wants to live
humbly for one."   --W. Stekel
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-25 Thread Micah Galizia
On Sat, Mar 25, 2017 at 10:51 AM, wm4  wrote:



> This can overflow sizeof(exp_buf).

Sorry, new patch cleans that up.

>> +
>> +// move the string beyond the day of week
>> +i = 0;
>> +while ((exp_buf[i] < '0' || exp_buf[i] > '9') && (i < j))
>> +i++;
>> +
>> +if (av_small_strptime(_buf[i], "%d%b%Y%H%M%SGMT", 
>> _buf)) {
>> +time_t now = av_gettime() / 100;
>
> I don't know if av_gettime() has the same time base...

I had to double-check but I think it's correct as it is. The av_gettime() is 
based on the time since the epoch, which is already in GMT/UTC. The cookies 
timestamp is also expressed in GMT/UTC per the HTTP spec (and per av_timegm), 
so I believe these are comparable.

If you were not talking about the timezones when you said "same base", I'm not 
entirely sure what you're getting at. I tested on my system and 
av_gettime()/100 returns the same value as time(NULL).

Thanks again.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-25 Thread Micah Galizia
Signed-off-by: Micah Galizia 
---
 libavformat/http.c | 43 +++
 1 file changed, 39 insertions(+), 4 deletions(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 293a8a7..53fae2a 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -29,6 +29,7 @@
 #include "libavutil/avstring.h"
 #include "libavutil/opt.h"
 #include "libavutil/time.h"
+#include "libavutil/parseutils.h"
 
 #include "avformat.h"
 #include "http.h"
@@ -48,6 +49,8 @@
 #define MAX_REDIRECTS 8
 #define HTTP_SINGLE   1
 #define HTTP_MUTLI2
+#define MAX_EXPIRY19
+#define WHITESPACES " \n\t\r"
 typedef enum {
 LOWER_PROTO,
 READ_HEADERS,
@@ -877,15 +880,20 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 
 *cookies = NULL;
 while ((cookie = av_strtok(set_cookies, "\n", ))) {
-int domain_offset = 0;
+int domain_offset = 0, expired = 0;
 char *param, *next_param, *cdomain = NULL, *cpath = NULL, *cvalue = 
NULL;
+char exp_buf[MAX_EXPIRY];
 set_cookies = NULL;
 
 // store the cookie in a dict in case it is updated in the response
 if (parse_cookie(s, cookie, >cookie_dict))
 av_log(s, AV_LOG_WARNING, "Unable to parse '%s'\n", cookie);
 
-while ((param = av_strtok(cookie, "; ", _param))) {
+while ((param = av_strtok(cookie, ";", _param))) {
+
+// move past any leading whitespace
+param += strspn(param, WHITESPACES);
+
 if (cookie) {
 // first key-value pair is the actual cookie value
 cvalue = av_strdup(param);
@@ -899,6 +907,33 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 int leading_dot = (param[7] == '.');
 av_free(cdomain);
 cdomain = av_strdup([7+leading_dot]);
+} else if (!av_strncasecmp("expires=", param, 8)) {
+int i, j, exp_len, exp_buf_len = MAX_EXPIRY-1;
+struct tm tm_buf = {0};
+char *expiry = [8];
+
+// strip off any punctuation or whitespace
+exp_len = strlen(expiry);
+for (i = 0, j = 0; i < exp_len && j < exp_buf_len; i++) {
+if ((expiry[i] >= '0' && expiry[i] <= '9') ||
+(expiry[i] >= 'A' && expiry[i] <= 'Z') ||
+(expiry[i] >= 'a' && expiry[i] <= 'z')) {
+exp_buf[j] = expiry[i];
+j++;
+}
+}
+exp_buf[j] = '\0';
+expiry = exp_buf;
+
+// move the string beyond the day of week
+while ((*expiry < '0' || *expiry > '9') && *expiry != '\0')
+expiry++;
+
+if (av_small_strptime(expiry, "%d%b%Y%H%M%S", _buf)) {
+time_t now = av_gettime() / 100;
+if (av_timegm(_buf) < now)
+expired = 1;
+}
 } else {
 // ignore unknown attributes
 }
@@ -907,9 +942,9 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 cdomain = av_strdup(domain);
 
 // ensure all of the necessary values are valid
-if (!cdomain || !cpath || !cvalue) {
+if (expired || !cdomain || !cpath || !cvalue ) {
 av_log(s, AV_LOG_WARNING,
-   "Invalid cookie found, no value, path or domain 
specified\n");
+   "Invalid cookie found, expired or no value, path or domain 
specified\n");
 goto done_cookie;
 }
 
-- 
2.9.3

___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-25 Thread wm4
On Sat, 25 Mar 2017 10:31:00 -0400
Micah Galizia  wrote:

> Signed-off-by: Micah Galizia 
> ---
>  libavformat/http.c | 43 +++
>  1 file changed, 39 insertions(+), 4 deletions(-)
> 
> diff --git a/libavformat/http.c b/libavformat/http.c
> index 293a8a7..f7d1925 100644
> --- a/libavformat/http.c
> +++ b/libavformat/http.c
> @@ -29,6 +29,7 @@
>  #include "libavutil/avstring.h"
>  #include "libavutil/opt.h"
>  #include "libavutil/time.h"
> +#include "libavutil/parseutils.h"
>  
>  #include "avformat.h"
>  #include "http.h"
> @@ -48,6 +49,8 @@
>  #define MAX_REDIRECTS 8
>  #define HTTP_SINGLE   1
>  #define HTTP_MUTLI2
> +#define MAX_EXPIRY30
> +#define WHITESPACES " \n\t\r"
>  typedef enum {
>  LOWER_PROTO,
>  READ_HEADERS,
> @@ -877,15 +880,20 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> const char *path,
>  
>  *cookies = NULL;
>  while ((cookie = av_strtok(set_cookies, "\n", ))) {
> -int domain_offset = 0;
> +int domain_offset = 0, expired = 0;
>  char *param, *next_param, *cdomain = NULL, *cpath = NULL, *cvalue = 
> NULL;
> +char exp_buf[MAX_EXPIRY];
>  set_cookies = NULL;
>  
>  // store the cookie in a dict in case it is updated in the response
>  if (parse_cookie(s, cookie, >cookie_dict))
>  av_log(s, AV_LOG_WARNING, "Unable to parse '%s'\n", cookie);
>  
> -while ((param = av_strtok(cookie, "; ", _param))) {
> +while ((param = av_strtok(cookie, ";", _param))) {
> +
> +// move past any leading whitespace
> +param += strspn(param, WHITESPACES);
> +
>  if (cookie) {
>  // first key-value pair is the actual cookie value
>  cvalue = av_strdup(param);
> @@ -899,6 +907,33 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> const char *path,
>  int leading_dot = (param[7] == '.');
>  av_free(cdomain);
>  cdomain = av_strdup([7+leading_dot]);
> +} else if (!av_strncasecmp("expires=", param, 8)) {
> +int i, j, exp_len;
> +struct tm tm_buf = {0};
> +char *expiry = [8];
> +
> +// strip off any punctuation or whitespace
> +exp_len = strlen(expiry);
> +for (i = 0, j = 0; i < exp_len; i++) {
> +if ((expiry[i] >= '0' && expiry[i] <= '9') ||
> +(expiry[i] >= 'A' && expiry[i] <= 'Z') ||
> +(expiry[i] >= 'a' && expiry[i] <= 'z')) {
> +exp_buf[j] = expiry[i];
> +j++;
> +}
> +}
> +exp_buf[j] = '\0';

This can overflow sizeof(exp_buf).

> +
> +// move the string beyond the day of week
> +i = 0;
> +while ((exp_buf[i] < '0' || exp_buf[i] > '9') && (i < j))
> +i++;
> +
> +if (av_small_strptime(_buf[i], "%d%b%Y%H%M%SGMT", 
> _buf)) {
> +time_t now = av_gettime() / 100;

I don't know if av_gettime() has the same time base...

> +if (av_timegm(_buf) < now)
> +expired = 1;
> +}
>  } else {
>  // ignore unknown attributes
>  }
> @@ -907,9 +942,9 @@ static int get_cookies(HTTPContext *s, char **cookies, 
> const char *path,
>  cdomain = av_strdup(domain);
>  
>  // ensure all of the necessary values are valid
> -if (!cdomain || !cpath || !cvalue) {
> +if (expired || !cdomain || !cpath || !cvalue ) {
>  av_log(s, AV_LOG_WARNING,
> -   "Invalid cookie found, no value, path or domain 
> specified\n");
> +   "Invalid cookie found, expired or no value, path or 
> domain specified\n");
>  goto done_cookie;
>  }
>  

___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-25 Thread Micah Galizia
Signed-off-by: Micah Galizia 
---
 libavformat/http.c | 43 +++
 1 file changed, 39 insertions(+), 4 deletions(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 293a8a7..f7d1925 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -29,6 +29,7 @@
 #include "libavutil/avstring.h"
 #include "libavutil/opt.h"
 #include "libavutil/time.h"
+#include "libavutil/parseutils.h"
 
 #include "avformat.h"
 #include "http.h"
@@ -48,6 +49,8 @@
 #define MAX_REDIRECTS 8
 #define HTTP_SINGLE   1
 #define HTTP_MUTLI2
+#define MAX_EXPIRY30
+#define WHITESPACES " \n\t\r"
 typedef enum {
 LOWER_PROTO,
 READ_HEADERS,
@@ -877,15 +880,20 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 
 *cookies = NULL;
 while ((cookie = av_strtok(set_cookies, "\n", ))) {
-int domain_offset = 0;
+int domain_offset = 0, expired = 0;
 char *param, *next_param, *cdomain = NULL, *cpath = NULL, *cvalue = 
NULL;
+char exp_buf[MAX_EXPIRY];
 set_cookies = NULL;
 
 // store the cookie in a dict in case it is updated in the response
 if (parse_cookie(s, cookie, >cookie_dict))
 av_log(s, AV_LOG_WARNING, "Unable to parse '%s'\n", cookie);
 
-while ((param = av_strtok(cookie, "; ", _param))) {
+while ((param = av_strtok(cookie, ";", _param))) {
+
+// move past any leading whitespace
+param += strspn(param, WHITESPACES);
+
 if (cookie) {
 // first key-value pair is the actual cookie value
 cvalue = av_strdup(param);
@@ -899,6 +907,33 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 int leading_dot = (param[7] == '.');
 av_free(cdomain);
 cdomain = av_strdup([7+leading_dot]);
+} else if (!av_strncasecmp("expires=", param, 8)) {
+int i, j, exp_len;
+struct tm tm_buf = {0};
+char *expiry = [8];
+
+// strip off any punctuation or whitespace
+exp_len = strlen(expiry);
+for (i = 0, j = 0; i < exp_len; i++) {
+if ((expiry[i] >= '0' && expiry[i] <= '9') ||
+(expiry[i] >= 'A' && expiry[i] <= 'Z') ||
+(expiry[i] >= 'a' && expiry[i] <= 'z')) {
+exp_buf[j] = expiry[i];
+j++;
+}
+}
+exp_buf[j] = '\0';
+
+// move the string beyond the day of week
+i = 0;
+while ((exp_buf[i] < '0' || exp_buf[i] > '9') && (i < j))
+i++;
+
+if (av_small_strptime(_buf[i], "%d%b%Y%H%M%SGMT", 
_buf)) {
+time_t now = av_gettime() / 100;
+if (av_timegm(_buf) < now)
+expired = 1;
+}
 } else {
 // ignore unknown attributes
 }
@@ -907,9 +942,9 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 cdomain = av_strdup(domain);
 
 // ensure all of the necessary values are valid
-if (!cdomain || !cpath || !cvalue) {
+if (expired || !cdomain || !cpath || !cvalue ) {
 av_log(s, AV_LOG_WARNING,
-   "Invalid cookie found, no value, path or domain 
specified\n");
+   "Invalid cookie found, expired or no value, path or domain 
specified\n");
 goto done_cookie;
 }
 
-- 
2.9.3

___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-25 Thread Micah Galizia
On 2017-03-25 07:11 AM, wm4 wrote:



>> -while ((param = av_strtok(cookie, "; ", _param))) {
>> +while ((param = av_strtok(cookie, ";", _param))) {
>> +
>> +// move past any leading whitespace
>> +param += strspn(param, WHITESPACES);
>> +
> Not quite sure why this change is even needed, but seems ok.

Its just a little more flexible than expecting a single space and only a space 
between each delimited field of a cookie.

>>   if (cookie) {
>>   // first key-value pair is the actual cookie value
>>   cvalue = av_strdup(param);
>> @@ -899,6 +905,33 @@ static int get_cookies(HTTPContext *s, char **cookies, 
>> const char *path,
>>   int leading_dot = (param[7] == '.');
>>   av_free(cdomain);
>>   cdomain = av_strdup([7+leading_dot]);
>> +} else if (!av_strncasecmp("expires=", param, 8)) {
>> +int i = 0, j = 0;
>> +struct tm tm_buf = {0};
>> +char *expiry = av_strdup([8]);
> Unchecked memory allocation that could fail.

Thanks, resolved using the on-stack buffer described below.

>> +
>> +// strip off any punctuation or whitespace
>> +for (; i < strlen(expiry); i++) {
> A bit ugly stylistically: the i=0 initialization should be in here, and
> the strlen should be cached in a variable, instead of recomputing it on
> every loop.

Fixed.

>> +if ((expiry[i] >= '0' && expiry[i] <= '9') ||
>> +(expiry[i] >= 'A' && expiry[i] <= 'Z') ||
>> +(expiry[i] >= 'a' && expiry[i] <= 'z')) {
>> +expiry[j] = expiry[i];
>> +j++;
>> +}
>> +}
>> +expiry[j] = '\0';
> (To be honest I don't understand why the string is even strduped - you
> could just make it with a fixed-sized on-stack buffer. Just discard the
> remainder of the string if the buffer is unexpectedly too small - time
> strings probably have an upper size bound anyway.)

Changed.

>> +
>> +// move the string beyond the day of week
>> +i = 0;
>> +while ((expiry[i] < '0' || expiry[i] > '9') && (i < j))
>> +i++;
>> +
>> +if (av_small_strptime([i], "%d%b%Y%H%M%SGMT", 
>> _buf)) {
>> +if (av_timegm(_buf) < time(NULL))
>> +expired = 1;
> A bit unsure about this time() call. Also nervous about having this in
> library code.

I borrowed some code from parseutils to resolve this.

Thanks for the prompt review.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-24 Thread Micah Galizia
Signed-off-by: Micah Galizia 
---
 libavformat/http.c | 41 +
 1 file changed, 37 insertions(+), 4 deletions(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 293a8a7..37bdacf 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -29,6 +29,7 @@
 #include "libavutil/avstring.h"
 #include "libavutil/opt.h"
 #include "libavutil/time.h"
+#include "libavutil/parseutils.h"
 
 #include "avformat.h"
 #include "http.h"
@@ -48,6 +49,7 @@
 #define MAX_REDIRECTS 8
 #define HTTP_SINGLE   1
 #define HTTP_MUTLI2
+#define WHITESPACES " \n\t\r"
 typedef enum {
 LOWER_PROTO,
 READ_HEADERS,
@@ -877,7 +879,7 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 
 *cookies = NULL;
 while ((cookie = av_strtok(set_cookies, "\n", ))) {
-int domain_offset = 0;
+int domain_offset = 0, expired = 0;
 char *param, *next_param, *cdomain = NULL, *cpath = NULL, *cvalue = 
NULL;
 set_cookies = NULL;
 
@@ -885,7 +887,11 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 if (parse_cookie(s, cookie, >cookie_dict))
 av_log(s, AV_LOG_WARNING, "Unable to parse '%s'\n", cookie);
 
-while ((param = av_strtok(cookie, "; ", _param))) {
+while ((param = av_strtok(cookie, ";", _param))) {
+
+// move past any leading whitespace
+param += strspn(param, WHITESPACES);
+
 if (cookie) {
 // first key-value pair is the actual cookie value
 cvalue = av_strdup(param);
@@ -899,6 +905,33 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 int leading_dot = (param[7] == '.');
 av_free(cdomain);
 cdomain = av_strdup([7+leading_dot]);
+} else if (!av_strncasecmp("expires=", param, 8)) {
+int i = 0, j = 0;
+struct tm tm_buf = {0};
+char *expiry = av_strdup([8]);
+
+// strip off any punctuation or whitespace
+for (; i < strlen(expiry); i++) {
+if ((expiry[i] >= '0' && expiry[i] <= '9') ||
+(expiry[i] >= 'A' && expiry[i] <= 'Z') ||
+(expiry[i] >= 'a' && expiry[i] <= 'z')) {
+expiry[j] = expiry[i];
+j++;
+}
+}
+expiry[j] = '\0';
+
+// move the string beyond the day of week
+i = 0;
+while ((expiry[i] < '0' || expiry[i] > '9') && (i < j))
+i++;
+
+if (av_small_strptime([i], "%d%b%Y%H%M%SGMT", _buf)) 
{
+if (av_timegm(_buf) < time(NULL))
+expired = 1;
+}
+
+av_free(expiry);
 } else {
 // ignore unknown attributes
 }
@@ -907,9 +940,9 @@ static int get_cookies(HTTPContext *s, char **cookies, 
const char *path,
 cdomain = av_strdup(domain);
 
 // ensure all of the necessary values are valid
-if (!cdomain || !cpath || !cvalue) {
+if (expired || !cdomain || !cpath || !cvalue ) {
 av_log(s, AV_LOG_WARNING,
-   "Invalid cookie found, no value, path or domain 
specified\n");
+   "Invalid cookie found, expired or no value, path or domain 
specified\n");
 goto done_cookie;
 }
 
-- 
2.9.3

___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-03-24 Thread Micah Galizia
Hi,

This is my second attempt at fixing how we are handling expired cookies. As a 
reminder, on some authenticated Neulion streams, they send a cookie from the 
past, like so:

Set-Cookie: nlqptid=""; Domain=.neulion.com; Expires=Thu, 01-Jan-1970 00:00:10 
GMT; Path=/

These expired cookies are ignored by other systems (eg: android).

Please let me know if you want changes.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-02-12 Thread Micah Galizia
On Sun, Feb 12, 2017 at 6:28 AM, Nicolas George  wrote:
> Thanks for the patch. See remarks below.
>
> Le tridi 23 pluviôse, an CCXXV, Micah Galizia a écrit :
>> On some authenticated Neulion streams, they send a cookie from the past,
>> like so:
>>
>> Set-Cookie: nlqptid=""; Domain=.neulion.com; Expires=Thu, 01-Jan-1970
>> 00:00:10 GMT; Path=/
>>
>> As a result, the good cookie value is overwritten and authentication breaks
>> immediately. I realise disqualifying a cookie over the date might open a
>> can of worms when it comes to date formatting used by different systems,
>
> In principle, I would be in favour of correctly heeding all elements of
> the protocol, and only on top of that provide users the option of
> ignoring certain elements. Parsing the expires field certainly enters
> this frame.
>
>> but I added Neulions wrong format and the http standard format.
>
> In that case, maybe ignoring the whole cookie because the date is
> invalid would be a better idea.

Maybe a more permissive approach would be better. Iff we _can_ parse
the date format _AND_ it's expired then and only then ignore that
cookie. This would maintain compatibility with how it works now, but
correct the specific bug I'm observing.

> Did you test to see how real browsers handle it?

Browsers, no, but the Android video player, yes. They ignore the new
cookie value if it shows up with an expiry in the past (well, at least
an expiry date in 1970) and use the value it had already. Here is a
charles dump if you want to see:
https://dl.dropboxusercontent.com/u/83154919/snnow_full2.chls

>> Please let me know if this is acceptable. I've run it against fate and
>> there were no problems.
>
> That is good practice. Unfortunately, FATE tests almost nothing about
> network protocols. If you did not, you need to check with a few web
> servers that currently work.

I tested it against the neulion stream I have access to. I don't have
a whole lot else but hopefully if I minimize the situations in which
cookies are ignored it wont matter. I'll also try to find a few other
stream sources.

> Now reviewing details of the latest version of the patch:
>
>> diff --git a/libavformat/http.c b/libavformat/http.c
>> index 944a6cf..24368aa 100644
>> --- a/libavformat/http.c
>> +++ b/libavformat/http.c
>> @@ -682,12 +682,46 @@ static int parse_icy(HTTPContext *s, const char *tag, 
>> const char *p)
>>
>>  static int parse_cookie(HTTPContext *s, const char *p, AVDictionary 
>> **cookies)
>>  {
>> -char *eql, *name;
>> +char *eql, *name, *expiry;
>>
>>  // duplicate the cookie name (dict will dupe the value)
>>  if (!(eql = strchr(p, '='))) return AVERROR(EINVAL);
>>  if (!(name = av_strndup(p, eql - p))) return AVERROR(ENOMEM);
>>
>> +// ensure the expiry is sane
>
>> +if ((expiry = strstr(eql, "Expires="))) {
>
> I believe this is not correct. First, AFAIK, all the structure elements
> in HTTP are case insensitive. Second, the string "Expires=" could
> legitimately be part of the cookie value itself.
>
> I suggest to parse the subfields of the set-cookie field correctly: it
> is a sequence of "key=value" pairs (with the "=value" part optional, but
> can be quoted) separated by semicolons and optional spaces. Furthermore,
> it would be useful for other fields too, such as content-type.
>
> I realize it is a little bit more work, but I think it is reasonable.

I think this was proposed last time I was adding cookies into the HLS
demuxer (years ago) but the problem is that you can't really pass
around complex data structures between demuxers (http, hls, etc).
AVOption was also quite restrictive last time I looked into doing
something more advanced like that.

One of the things Michael N. suggested back then was using a proper
cookie jar -- is there any reason I can't keep parsed cookies in an
in-memory global static variable scoped in http.c? Then we wouldn't
even need to pass the cookies as options around between demuxers
anymore since they'd have a perminant home in http.c, which should be
the only place they're used.

>> +struct tm tm_buf = {0};
>> +char *end;
>> +
>> +// get the start & the end of the expiry ('11 Feb 2017 09:41:35 
>> GMT')
>> +// this skips past the day of the week by finding the space 
>> following it
>
>> +expiry += 8 * sizeof(char);
>
> sizeof(char) = 1 by definition, thus writing it is always unnecessary,
> and rarely useful for readability.
>
>> +while (*expiry != ' ') expiry++;
>
> I suspect tabs and other whitespace-style characters could be present
> here.
>
> More importantly, this code will happily skip the end-of-string marker
> if there are no spaces at all, and that is a big no.
>
> Also, style nit for here and other places: the code base does not
> usually use single-line loops or conditions.
>
>> +expiry++;
>> +end = expiry+1;
>
>> +while (*end != ';') end++;
>
> Same problem here.
>
>> +
>> +// 

Re: [FFmpeg-devel] [PATCH] Ignore expired cookies

2017-02-12 Thread Nicolas George
Thanks for the patch. See remarks below.

Le tridi 23 pluviôse, an CCXXV, Micah Galizia a écrit :
> On some authenticated Neulion streams, they send a cookie from the past,
> like so:
> 
> Set-Cookie: nlqptid=""; Domain=.neulion.com; Expires=Thu, 01-Jan-1970
> 00:00:10 GMT; Path=/
> 
> As a result, the good cookie value is overwritten and authentication breaks
> immediately. I realise disqualifying a cookie over the date might open a
> can of worms when it comes to date formatting used by different systems,

In principle, I would be in favour of correctly heeding all elements of
the protocol, and only on top of that provide users the option of
ignoring certain elements. Parsing the expires field certainly enters
this frame.

> but I added Neulions wrong format and the http standard format.

In that case, maybe ignoring the whole cookie because the date is
invalid would be a better idea.

Did you test to see how real browsers handle it?

> Please let me know if this is acceptable. I've run it against fate and
> there were no problems.

That is good practice. Unfortunately, FATE tests almost nothing about
network protocols. If you did not, you need to check with a few web
servers that currently work.


Now reviewing details of the latest version of the patch:

> diff --git a/libavformat/http.c b/libavformat/http.c
> index 944a6cf..24368aa 100644
> --- a/libavformat/http.c
> +++ b/libavformat/http.c
> @@ -682,12 +682,46 @@ static int parse_icy(HTTPContext *s, const char *tag, 
> const char *p)
>  
>  static int parse_cookie(HTTPContext *s, const char *p, AVDictionary 
> **cookies)
>  {
> -char *eql, *name;
> +char *eql, *name, *expiry;
>  
>  // duplicate the cookie name (dict will dupe the value)
>  if (!(eql = strchr(p, '='))) return AVERROR(EINVAL);
>  if (!(name = av_strndup(p, eql - p))) return AVERROR(ENOMEM);
>  
> +// ensure the expiry is sane

> +if ((expiry = strstr(eql, "Expires="))) {

I believe this is not correct. First, AFAIK, all the structure elements
in HTTP are case insensitive. Second, the string "Expires=" could
legitimately be part of the cookie value itself.

I suggest to parse the subfields of the set-cookie field correctly: it
is a sequence of "key=value" pairs (with the "=value" part optional, but
can be quoted) separated by semicolons and optional spaces. Furthermore,
it would be useful for other fields too, such as content-type.

I realize it is a little bit more work, but I think it is reasonable.

> +struct tm tm_buf = {0};
> +char *end;
> +
> +// get the start & the end of the expiry ('11 Feb 2017 09:41:35 GMT')
> +// this skips past the day of the week by finding the space 
> following it

> +expiry += 8 * sizeof(char);

sizeof(char) = 1 by definition, thus writing it is always unnecessary,
and rarely useful for readability.

> +while (*expiry != ' ') expiry++;

I suspect tabs and other whitespace-style characters could be present
here.

More importantly, this code will happily skip the end-of-string marker
if there are no spaces at all, and that is a big no.

Also, style nit for here and other places: the code base does not
usually use single-line loops or conditions.

> +expiry++;
> +end = expiry+1;

> +while (*end != ';') end++;

Same problem here.

> +
> +// ensure the time is parsable
> +end = strptime(expiry, "%d %b %Y %H:%M:%S %Z", _buf);

strptime() is an XSI extension, and as such not portable enough for the
FFmpeg code base. You can look if av_small_strptime() can do the trick.

According to
https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Date
(which is more readable than
https://tools.ietf.org/html/rfc6265#section-5.1.1)
the correct date syntax starts with the abbreviated day name and a
comma, i.e. "%a,". I suspect the code that skips until a space above is
there to skip that component, but it should be part of the date parsing
itself.

Also, %Z is a non-standard GNU and BSD extension, not supported by
av_small_strptime(). Fortunately, still according to MDN, only "GMT" is
supported here.

> +
> +// ensure neulion's different format is parsable
> +if (!end) end = strptime(expiry, "%d-%b-%Y %H:%M:%S %Z", _buf);
> +
> +// if the expire is specified but unparsable, this cookie is invalid
> +if (!end) {
> +av_log(s, AV_LOG_ERROR, "Unable to parse expiry for cookie 
> '%s'\n", p);
> +av_free(name);
> +return AVERROR(EINVAL);
> +}
> +
> +// no cookies from the past (neulion)

> +if (mktime(_buf) < time(NULL)) {

Since only GMT is supported, I think you need to use av_timegm().

> +av_log(s, AV_LOG_ERROR, "Ignoring cookie from the past '%s'\n", 
> p);
> +av_free(name);
> +return AVERROR(EINVAL);

I think it does not need to be an error, but that depends on the general
policy to deal with this kind of cases.

> +}
> 

[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-02-11 Thread Micah Galizia
---
 libavformat/http.c | 36 +++-
 1 file changed, 35 insertions(+), 1 deletion(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 944a6cf..24368aa 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -682,12 +682,46 @@ static int parse_icy(HTTPContext *s, const char *tag, 
const char *p)
 
 static int parse_cookie(HTTPContext *s, const char *p, AVDictionary **cookies)
 {
-char *eql, *name;
+char *eql, *name, *expiry;
 
 // duplicate the cookie name (dict will dupe the value)
 if (!(eql = strchr(p, '='))) return AVERROR(EINVAL);
 if (!(name = av_strndup(p, eql - p))) return AVERROR(ENOMEM);
 
+// ensure the expiry is sane
+if ((expiry = strstr(eql, "Expires="))) {
+struct tm tm_buf = {0};
+char *end;
+
+// get the start & the end of the expiry ('11 Feb 2017 09:41:35 GMT')
+// this skips past the day of the week by finding the space following 
it
+expiry += 8 * sizeof(char);
+while (*expiry != ' ') expiry++;
+expiry++;
+end = expiry+1;
+while (*end != ';') end++;
+
+// ensure the time is parsable
+end = strptime(expiry, "%d %b %Y %H:%M:%S %Z", _buf);
+
+// ensure neulion's different format is parsable
+if (!end) end = strptime(expiry, "%d-%b-%Y %H:%M:%S %Z", _buf);
+
+// if the expire is specified but unparsable, this cookie is invalid
+if (!end) {
+av_log(s, AV_LOG_ERROR, "Unable to parse expiry for cookie 
'%s'\n", p);
+av_free(name);
+return AVERROR(EINVAL);
+}
+
+// no cookies from the past (neulion)
+if (mktime(_buf) < time(NULL)) {
+av_log(s, AV_LOG_ERROR, "Ignoring cookie from the past '%s'\n", p);
+av_free(name);
+return AVERROR(EINVAL);
+}
+}
+
 // add the cookie to the dictionary
 av_dict_set(cookies, name, eql, AV_DICT_DONT_STRDUP_KEY);
 
-- 
2.9.3

___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-02-11 Thread Micah Galizia
This one fixes the memory leak -- sorry for all the spam.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-02-11 Thread Micah Galizia
Signed-off-by: Micah Galizia 
---
 libavformat/http.c | 34 +-
 1 file changed, 33 insertions(+), 1 deletion(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 944a6cf..e7b8ac3 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -682,12 +682,44 @@ static int parse_icy(HTTPContext *s, const char *tag, 
const char *p)
 
 static int parse_cookie(HTTPContext *s, const char *p, AVDictionary **cookies)
 {
-char *eql, *name;
+char *eql, *name, *expiry;
 
 // duplicate the cookie name (dict will dupe the value)
 if (!(eql = strchr(p, '='))) return AVERROR(EINVAL);
 if (!(name = av_strndup(p, eql - p))) return AVERROR(ENOMEM);
 
+// ensure the expiry is sane
+if ((expiry = strstr(eql, "Expires="))) {
+struct tm tm_buf = {0};
+char *end;
+
+// get the start & the end of the expiry ('11 Feb 2017 09:41:35 GMT')
+// this skips past the day of the week by finding the space following 
it
+expiry += 8 * sizeof(char);
+while (*expiry != ' ') expiry++;
+expiry++;
+end = expiry+1;
+while (*end != ';') end++;
+
+// ensure the time is parsable
+end = strptime(expiry, "%d %b %Y %H:%M:%S %Z", _buf);
+
+// ensure neulion's different format is parsable
+if (!end) end = strptime(expiry, "%d-%b-%Y %H:%M:%S %Z", _buf);
+
+// if the expire is specified but unparsable, this cookie is invalid
+if (!end) {
+av_log(s, AV_LOG_ERROR, "Unable to parse expiry for cookie 
'%s'\n", p);
+return AVERROR(EINVAL);
+}
+
+// no cookies from the past (neulion)
+if (mktime(_buf) < time(NULL)) {
+av_log(s, AV_LOG_ERROR, "Ignoring cookie from the past '%s'\n", p);
+return AVERROR(EINVAL);
+}
+}
+
 // add the cookie to the dictionary
 av_dict_set(cookies, name, eql, AV_DICT_DONT_STRDUP_KEY);
 
-- 
2.9.3

___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-02-11 Thread Micah Galizia
Appologies, gmail screwed up the patch.
___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel


[FFmpeg-devel] [PATCH] Ignore expired cookies

2017-02-11 Thread Micah Galizia
Hello,

On some authenticated Neulion streams, they send a cookie from the past,
like so:

Set-Cookie: nlqptid=""; Domain=.neulion.com; Expires=Thu, 01-Jan-1970
00:00:10 GMT; Path=/

As a result, the good cookie value is overwritten and authentication breaks
immediately. I realise disqualifying a cookie over the date might open a
can of worms when it comes to date formatting used by different systems,
but I added Neulions wrong format and the http standard format.

Please let me know if this is acceptable. I've run it against fate and
there were no problems.
-- 
"The mark of an immature man is that he wants to die nobly for a cause,
while the mark of the mature man is that he wants to live humbly for
one."   --W. Stekel
From 1fecda5a7a36b530208a9428b86eebda66b0 Mon Sep 17 00:00:00 2001
From: Micah Galizia 
Date: Sat, 11 Feb 2017 21:18:41 -0500
Subject: [PATCH] Ignore expired cookies

Signed-off-by: Micah Galizia 
---
 libavformat/http.c | 34 +-
 1 file changed, 33 insertions(+), 1 deletion(-)

diff --git a/libavformat/http.c b/libavformat/http.c
index 944a6cf..e7b8ac3 100644
--- a/libavformat/http.c
+++ b/libavformat/http.c
@@ -682,12 +682,44 @@ static int parse_icy(HTTPContext *s, const char *tag, const char *p)
 
 static int parse_cookie(HTTPContext *s, const char *p, AVDictionary **cookies)
 {
-char *eql, *name;
+char *eql, *name, *expiry;
 
 // duplicate the cookie name (dict will dupe the value)
 if (!(eql = strchr(p, '='))) return AVERROR(EINVAL);
 if (!(name = av_strndup(p, eql - p))) return AVERROR(ENOMEM);
 
+// ensure the expiry is sane
+if ((expiry = strstr(eql, "Expires="))) {
+struct tm tm_buf = {0};
+char *end;
+
+// get the start & the end of the expiry ('11 Feb 2017 09:41:35 GMT')
+// this skips past the day of the week by finding the space following it
+expiry += 8 * sizeof(char);
+while (*expiry != ' ') expiry++;
+expiry++;
+end = expiry+1;
+while (*end != ';') end++;
+
+// ensure the time is parsable
+end = strptime(expiry, "%d %b %Y %H:%M:%S %Z", _buf);
+
+// ensure neulion's different format is parsable
+if (!end) end = strptime(expiry, "%d-%b-%Y %H:%M:%S %Z", _buf);
+
+// if the expire is specified but unparsable, this cookie is invalid
+if (!end) {
+av_log(s, AV_LOG_ERROR, "Unable to parse expiry for cookie '%s'\n", p);
+return AVERROR(EINVAL);
+}
+
+// no cookies from the past (neulion)
+if (mktime(_buf) < time(NULL)) {
+av_log(s, AV_LOG_ERROR, "Ignoring cookie from the past '%s'\n", p);
+return AVERROR(EINVAL);
+}
+}
+
 // add the cookie to the dictionary
 av_dict_set(cookies, name, eql, AV_DICT_DONT_STRDUP_KEY);
 
-- 
2.9.3

___
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
http://ffmpeg.org/mailman/listinfo/ffmpeg-devel