[Tarantool-patches] [PATCH v3 1/2] sql: add missing diag_set on failure when working inside os_unix.c
Leonid Vasiliev
lvasiliev at tarantool.org
Thu Dec 17 02:09:06 MSK 2020
SQL module didn't set an error in the diagnostics area on failure
inside unix.c. This could lead to a crash like in #5537.
Co-authored-by: Mergen Imeev<imeevma at gmail.com>
Follow-up #5537
---
src/box/sql/os_unix.c | 63 +++++++++++++++++++++++++++++++++++++++++++++++----
1 file changed, 58 insertions(+), 5 deletions(-)
diff --git a/src/box/sql/os_unix.c b/src/box/sql/os_unix.c
index d64f1bd..4f59767 100644
--- a/src/box/sql/os_unix.c
+++ b/src/box/sql/os_unix.c
@@ -159,14 +159,17 @@ robust_open(const char *z, int f, mode_t m)
if (fd < 0) {
if (errno == EINTR)
continue;
+ diag_set(SystemError, "failed to open file '%s'", z);
break;
}
if (fd >= SQL_MINIMUM_FILE_DESCRIPTOR)
break;
close(fd);
fd = -1;
- if (open("/dev/null", f, m) < 0)
+ if (open("/dev/null", f, m) < 0) {
+ diag_set(SystemError, "failed to open '/dev/null'");
break;
+ }
}
if (fd >= 0) {
if (m != 0) {
@@ -193,6 +196,10 @@ robust_ftruncate(int h, sql_int64 sz)
do {
rc = ftruncate(h, sz);
} while (rc < 0 && errno == EINTR);
+
+ if (rc < 0)
+ diag_set(SystemError, "failed to truncate file");
+
return rc;
}
@@ -395,6 +402,9 @@ findInodeInfo(unixFile * pFile, /* Unix file with file desc used in the key */
fd = pFile->h;
rc = fstat(fd, &statbuf);
if (rc != 0) {
+ diag_set(SystemError,
+ "failed to retrive information about the file '%s'",
+ pFile->zPath);
storeLastErrno(pFile, errno);
return -1;
}
@@ -433,7 +443,13 @@ static int
fileHasMoved(unixFile * pFile)
{
struct stat buf;
- return pFile->pInode != NULL && (stat(pFile->zPath, &buf) != 0 ||
+ int rc = stat(pFile->zPath, &buf);
+ if (rc < 0) {
+ diag_set(SystemError,
+ "failed to retrive information about the file '%s'",
+ pFile->zPath);
+ }
+ return pFile->pInode != NULL && (rc != 0 ||
(u64) buf.st_ino !=
pFile->pInode->fileId.ino);
}
@@ -473,8 +489,12 @@ unixFileLock(unixFile * pFile, struct flock *pLock)
lock.l_len = SHARED_SIZE;
lock.l_type = F_WRLCK;
rc = fcntl(pFile->h, F_SETLK, &lock);
- if (rc < 0)
+ if (rc < 0) {
+ diag_set(SystemError,
+ "failed to acquire a lock on the"
+ " file '%s'", pFile->zPath);
return rc;
+ }
pInode->bProcessLock = 1;
pInode->nLock++;
} else {
@@ -482,6 +502,11 @@ unixFileLock(unixFile * pFile, struct flock *pLock)
}
} else {
rc = fcntl(pFile->h, F_SETLK, pLock);
+ if (rc < 0) {
+ diag_set(SystemError,
+ "failed to acquire a lock on the file '%s'",
+ pFile->zPath);
+ }
}
return rc;
}
@@ -729,6 +754,9 @@ seekAndRead(unixFile * id, sql_int64 offset, void *pBuf, int cnt)
do {
newOffset = lseek(id->h, offset, SEEK_SET);
if (newOffset < 0) {
+ diag_set(SystemError,
+ "failed to reposition the offset of '%s' file",
+ id->zPath);
storeLastErrno((unixFile *) id, errno);
return -1;
}
@@ -740,6 +768,8 @@ seekAndRead(unixFile * id, sql_int64 offset, void *pBuf, int cnt)
got = 1;
continue;
}
+ diag_set(SystemError, "failed to read from file '%s'",
+ id->zPath);
prior = 0;
storeLastErrno((unixFile *) id, errno);
break;
@@ -825,10 +855,16 @@ seekAndWriteFd(int fd, /* File descriptor to write to */
do {
i64 iSeek = lseek(fd, iOff, SEEK_SET);
if (iSeek < 0) {
+ diag_set(SystemError,
+ "failed to reposition file offset");
rc = -1;
break;
}
rc = write(fd, pBuf, nBuf);
+ if (rc < 0) {
+ diag_set(SystemError,
+ "failed to write %i bytes to file", nBuf);
+ }
} while (rc < 0 && errno == EINTR);
if (rc < 0)
@@ -940,8 +976,12 @@ fcntlSizeHint(unixFile * pFile, i64 nByte)
i64 nSize; /* Required file size */
struct stat buf; /* Used to hold return values of fstat() */
- if (fstat(pFile->h, &buf))
+ if (fstat(pFile->h, &buf)) {
+ diag_set(SystemError,
+ "failed to retrive information about the"
+ " file '%s'", pFile->zPath);
return -1;
+ }
nSize =
((nByte + pFile->szChunk -
@@ -1165,8 +1205,12 @@ unixMapfile(unixFile * pFd, i64 nMap)
if (nMap < 0) {
struct stat statbuf; /* Low-level file information */
- if (fstat(pFd->h, &statbuf))
+ if (fstat(pFd->h, &statbuf)) {
+ diag_set(SystemError,
+ "failed to retrive information about the"
+ " file '%s'", pFd->zPath);
return -1;
+ }
nMap = statbuf.st_size;
}
if (nMap > pFd->mmapSizeMax) {
@@ -1449,6 +1493,8 @@ unixTempFileDir(void)
break;
zDir = azDirs[i++];
}
+ diag_set(ClientError, ER_SYSTEM,
+ "No access to any temporary directory");
return 0;
}
@@ -1558,6 +1604,9 @@ getFileMode(const char *zFile, /* File name */
*pUid = sStat.st_uid;
*pGid = sStat.st_gid;
} else {
+ diag_set(SystemError,
+ "failed to retrive information about the file '%s'",
+ zFile);
rc = -1;
}
return rc;
@@ -1813,6 +1862,7 @@ unixDelete(sql_vfs * NotUsed, /* VFS containing this as the xDelete method */
int rc = 0;
UNUSED_PARAMETER(NotUsed);
if (unlink(zPath) == (-1)) {
+ diag_set(SystemError, "failed to unlink the file '%s'", zPath);
return -1;
}
if ((dirSync & 1) != 0) {
@@ -1821,6 +1871,9 @@ unixDelete(sql_vfs * NotUsed, /* VFS containing this as the xDelete method */
if (rc == 0) {
struct stat buf;
if (fstat(fd, &buf)) {
+ diag_set(SystemError,
+ "failed to retrive information about"
+ " the file '%s'", zPath);
rc = -1;
}
close(fd);
--
2.7.4
More information about the Tarantool-patches
mailing list