shithub: libdvdcss

Download patch

ref: c126d5ac7843a809857a6dc14fbaae29a2499ff0
parent: 5bec036cfee3950d002f3c46c17bbd4e375d5bd6
author: Frank Henigman <fjhenigman@gmail.com>
date: Fri Feb 3 06:23:28 EST 2017

Fix directory existence check.

mkdir() followed by errno==EEXIST is not sufficient to determine if
a directory exists.  Do a stat() to check for existence before trying
mkdir().

Signed-off-by: Frank Henigman <fjhenigman@gmail.com>
Signed-off-by: Jean-Baptiste Kempf <jb@videolan.org>

--- a/src/libdvdcss.c
+++ b/src/libdvdcss.c
@@ -143,6 +143,16 @@
 #define MANUFACTURING_DATE_OFFSET 813
 #define MANUFACTURING_DATE_LENGTH  16
 
+static int exists_or_mkdir( const char *path, int perm )
+{
+    /* mkdir() may return an error if making the directory would fail,
+     * even if the directory exists, so use stat() to test for existence
+     * before trying to make the directory. */
+    struct stat st;
+    if( stat(path, &st) )
+        return mkdir(path, perm);
+    return 0;
+}
 
 static dvdcss_t dvdcss_open_common ( const char *psz_target, void *p_stream,
                                      dvdcss_stream_cb *p_stream_cb );
@@ -221,7 +231,7 @@
          * directory in userland */
         char *psz_home = "/sdcard/Android/data/org.videolan.dvdcss";
 
-        int i_ret = mkdir( psz_home, 0755 );
+        int i_ret = exists_or_mkdir( psz_home, 0755 );
         if( i_ret < 0 && errno != EEXIST )
         {
             print_error( dvdcss, "failed creating home directory" );
@@ -302,7 +312,7 @@
     char psz_tagfile[PATH_MAX];
     int i_fd, i_ret;
 
-    i_ret = mkdir( dvdcss->psz_cachefile, 0755 );
+    i_ret = exists_or_mkdir( dvdcss->psz_cachefile, 0755 );
     if( i_ret < 0 && errno != EEXIST )
     {
         print_error( dvdcss, "failed creating cache directory '%s'", dvdcss->psz_cachefile );
@@ -425,7 +435,7 @@
     /* We have a disc name or ID, we can create the cache subdirectory. */
     i = sprintf( dvdcss->psz_cachefile, "%s/%s-%s-%s",
                  dvdcss->psz_cachefile, psz_title, psz_serial, psz_key );
-    i_ret = mkdir( dvdcss->psz_cachefile, 0755 );
+    i_ret = exists_or_mkdir( dvdcss->psz_cachefile, 0755 );
     if( i_ret < 0 && errno != EEXIST )
     {
         print_error( dvdcss, "failed creating cache subdirectory" );