]> git.ipfire.org Git - thirdparty/asterisk.git/commitdiff
If the recording in the database is too large, it will fail to retrieve with
authorTilghman Lesher <tilghman@meg.abyt.es>
Tue, 5 Dec 2006 01:26:08 +0000 (01:26 +0000)
committerTilghman Lesher <tilghman@meg.abyt.es>
Tue, 5 Dec 2006 01:26:08 +0000 (01:26 +0000)
an mmap error.  Not too sure why this doesn't happen when we put it in the
database, also, but since that doesn't seem to be broken, I'm not going to fix
it (at least until someone reports it).  Solution is to ask for the file in
smaller chunks.  (Bug 8385)

git-svn-id: https://origsvn.digium.com/svn/asterisk/branches/1.2@48251 65c4cc65-6c06-0410-ace0-fbb531ad65f3

apps/app_voicemail.c

index a1b46d318851a17689c04c28a935cba803cfac83..a8477724ce93b4c2b05581ebe3e87429a29a1cce 100644 (file)
@@ -77,6 +77,7 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
 #define COMMAND_TIMEOUT 5000
 #define        VOICEMAIL_DIR_MODE      0700
 #define        VOICEMAIL_FILE_MODE     0600
+#define        CHUNKSIZE       65536
 
 #define VOICEMAIL_CONFIG "voicemail.conf"
 #define ASTERISK_USERNAME "asterisk"
@@ -925,6 +926,7 @@ static int retrieve_file(char *dir, int msgnum)
                                goto yuck;
                        }
                        if (!strcasecmp(coltitle, "recording")) {
+                               off_t offset;
                                res = SQLGetData(stmt, x + 1, SQL_BINARY, NULL, 0, &colsize);
                                fdlen = colsize;
                                if (fd > -1) {
@@ -935,22 +937,25 @@ static int retrieve_file(char *dir, int msgnum)
                                                fd = -1;
                                                continue;
                                        }
-                                       if (fd > -1) {
-                                               if ((fdm = mmap(NULL, fdlen, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0)) == -1) {
+                                       /* Read out in small chunks */
+                                       for (offset = 0; offset < colsize; offset += CHUNKSIZE) {
+                                               /* +1 because SQLGetData likes null-terminating binary data */
+                                               if ((fdm = mmap(NULL, CHUNKSIZE + 1, PROT_READ | PROT_WRITE, MAP_SHARED, fd, offset)) == -1) {
                                                        ast_log(LOG_WARNING, "Could not mmap the output file: %s (%d)\n", strerror(errno), errno);
                                                        SQLFreeHandle(SQL_HANDLE_STMT, stmt);
                                                        goto yuck;
+                                               } else {
+                                                       res = SQLGetData(stmt, x + 1, SQL_BINARY, fdm, CHUNKSIZE + 1, NULL);
+                                                       munmap(fdm, 0);
+                                                       if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
+                                                               ast_log(LOG_WARNING, "SQL Get Data error!\n[%s]\n\n", sql);
+                                                               unlink(full_fn);
+                                                               SQLFreeHandle(SQL_HANDLE_STMT, stmt);
+                                                               goto yuck;
+                                                       }
                                                }
                                        }
-                               }
-                               if (fdm) {
-                                       memset(fdm, 0, fdlen);
-                                       res = SQLGetData(stmt, x + 1, SQL_BINARY, fdm, fdlen, &colsize);
-                                       if ((res != SQL_SUCCESS) && (res != SQL_SUCCESS_WITH_INFO)) {
-                                               ast_log(LOG_WARNING, "SQL Get Data error!\n[%s]\n\n", sql);
-                                               SQLFreeHandle (SQL_HANDLE_STMT, stmt);
-                                               goto yuck;
-                                       }
+                                       truncate(full_fn, fdlen);
                                }
                        } else {
                                res = SQLGetData(stmt, x + 1, SQL_CHAR, rowdata, sizeof(rowdata), NULL);
@@ -969,8 +974,6 @@ static int retrieve_file(char *dir, int msgnum)
 yuck:  
        if (f)
                fclose(f);
-       if (fdm)
-               munmap(fdm, fdlen);
        if (fd > -1)
                close(fd);
        return x - 1;