mirror of
https://github.com/pgbackrest/pgbackrest.git
synced 2025-01-18 04:58:51 +02:00
Abstract IO layer out of the storage layer.
This allows the routines to be used for IO objects that do not have a storage representation. Implement buffer read and write IO objects.
This commit is contained in:
parent
5dc8a2ec08
commit
0ac176b722
@ -37,6 +37,10 @@
|
||||
<p>Allow <code>Buffer</code> object <quote>used size</quote> to be different than <quote>allocated size</quote>. Add functions to manage used size and remaining size and update automatically when possible.</p>
|
||||
</release-item>
|
||||
|
||||
<release-item>
|
||||
<p>Abstract IO layer out of the storage layer. This allows the routines to be used for IO objects that do not have a storage representation. Implement buffer read and write IO objects.</p>
|
||||
</release-item>
|
||||
|
||||
<release-item>
|
||||
<p><code>storageFileRead()</code> accepts a buffer for output rather than creating one. This is more efficient overall and allows the caller to specify how many bytes will be read on each call. Reads are appended if the buffer already contains data but the buffer size will never increase.</p>
|
||||
</release-item>
|
||||
|
@ -48,7 +48,11 @@ my @stryCFile =
|
||||
'common/encode/base64.c',
|
||||
'common/error.c',
|
||||
'common/ini.c',
|
||||
'common/io/bufferRead.c',
|
||||
'common/io/handle.c',
|
||||
'common/io/io.c',
|
||||
'common/io/read.c',
|
||||
'common/io/write.c',
|
||||
'common/lock.c',
|
||||
'common/log.c',
|
||||
'common/memContext.c',
|
||||
|
47
src/Makefile
47
src/Makefile
@ -65,7 +65,11 @@ SRCS = \
|
||||
common/error.c \
|
||||
common/exit.c \
|
||||
common/fork.c \
|
||||
common/io/bufferRead.c \
|
||||
common/io/handle.c \
|
||||
common/io/io.c \
|
||||
common/io/read.c \
|
||||
common/io/write.c \
|
||||
common/ini.c \
|
||||
common/lock.c \
|
||||
common/log.c \
|
||||
@ -123,13 +127,13 @@ install: pgbackrest
|
||||
####################################################################################################################################
|
||||
# Compile rules
|
||||
####################################################################################################################################
|
||||
command/archive/common.o: command/archive/common.c command/archive/common.h common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h postgres/version.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
command/archive/common.o: command/archive/common.c command/archive/common.h common/assert.h common/debug.h common/error.auto.h common/error.h common/io/read.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h postgres/version.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c command/archive/common.c -o command/archive/common.o
|
||||
|
||||
command/archive/get/get.o: command/archive/get/get.c command/archive/common.h command/command.h common/assert.h common/debug.h common/error.auto.h common/error.h common/fork.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/regExp.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h perl/exec.h postgres/info.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
command/archive/get/get.o: command/archive/get/get.c command/archive/common.h command/command.h common/assert.h common/debug.h common/error.auto.h common/error.h common/fork.h common/io/read.h common/io/write.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/regExp.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h perl/exec.h postgres/info.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c command/archive/get/get.c -o command/archive/get/get.o
|
||||
|
||||
command/archive/push/push.o: command/archive/push/push.c command/archive/common.h command/command.h common/debug.h common/error.auto.h common/error.h common/fork.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h perl/exec.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
command/archive/push/push.o: command/archive/push/push.c command/archive/common.h command/command.h common/debug.h common/error.auto.h common/error.h common/fork.h common/io/read.h common/io/write.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h perl/exec.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c command/archive/push/push.c -o command/archive/push/push.o
|
||||
|
||||
command/command.o: command/command.c common/assert.h common/debug.h common/error.auto.h common/error.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/time.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h version.h
|
||||
@ -156,13 +160,28 @@ common/exit.o: common/exit.c command/command.h common/debug.h common/error.auto.
|
||||
common/fork.o: common/fork.c common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/stackTrace.h common/type/convert.h
|
||||
$(CC) $(CFLAGS) -c common/fork.c -o common/fork.o
|
||||
|
||||
common/ini.o: common/ini.c common/debug.h common/error.auto.h common/error.h common/ini.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
common/ini.o: common/ini.c common/debug.h common/error.auto.h common/error.h common/ini.h common/io/read.h common/io/write.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c common/ini.c -o common/ini.o
|
||||
|
||||
common/io/bufferRead.o: common/io/bufferRead.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/bufferRead.h common/io/read.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h
|
||||
$(CC) $(CFLAGS) -c common/io/bufferRead.c -o common/io/bufferRead.o
|
||||
|
||||
common/io/bufferWrite.o: common/io/bufferWrite.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/bufferWrite.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h
|
||||
$(CC) $(CFLAGS) -c common/io/bufferWrite.c -o common/io/bufferWrite.o
|
||||
|
||||
common/io/handle.o: common/io/handle.c common/debug.h common/error.auto.h common/error.h common/io/handle.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h
|
||||
$(CC) $(CFLAGS) -c common/io/handle.c -o common/io/handle.o
|
||||
|
||||
common/lock.o: common/lock.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/handle.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
common/io/io.o: common/io/io.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/io.h common/log.h common/logLevel.h common/stackTrace.h common/type/convert.h
|
||||
$(CC) $(CFLAGS) -c common/io/io.c -o common/io/io.o
|
||||
|
||||
common/io/read.o: common/io/read.c common/debug.h common/error.auto.h common/error.h common/io/read.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h
|
||||
$(CC) $(CFLAGS) -c common/io/read.c -o common/io/read.o
|
||||
|
||||
common/io/write.o: common/io/write.c common/debug.h common/error.auto.h common/error.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h
|
||||
$(CC) $(CFLAGS) -c common/io/write.c -o common/io/write.o
|
||||
|
||||
common/lock.o: common/lock.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/handle.h common/io/read.h common/io/write.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c common/lock.c -o common/lock.o
|
||||
|
||||
common/log.o: common/log.c common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/stackTrace.h common/time.h common/type/convert.h
|
||||
@ -213,10 +232,10 @@ config/config.o: config/config.c common/assert.h common/debug.h common/error.aut
|
||||
config/define.o: config/define.c common/assert.h common/debug.h common/error.auto.h common/error.h common/logLevel.h common/stackTrace.h common/type/convert.h config/define.auto.c config/define.auto.h config/define.h
|
||||
$(CC) $(CFLAGS) -c config/define.c -o config/define.o
|
||||
|
||||
config/load.o: config/load.c command/command.h common/debug.h common/error.auto.h common/error.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h config/parse.h
|
||||
config/load.o: config/load.c command/command.h common/debug.h common/error.auto.h common/error.h common/io/io.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h config/parse.h
|
||||
$(CC) $(CFLAGS) -c config/load.c -o config/load.o
|
||||
|
||||
config/parse.o: config/parse.c common/assert.h common/debug.h common/error.auto.h common/error.h common/ini.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/regExp.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/parse.auto.c config/parse.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
config/parse.o: config/parse.c common/assert.h common/debug.h common/error.auto.h common/error.h common/ini.h common/io/read.h common/io/write.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/regExp.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/parse.auto.c config/parse.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c config/parse.c -o config/parse.o
|
||||
|
||||
crypto/cipherBlock.o: crypto/cipherBlock.c common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/convert.h crypto/cipher.h crypto/cipherBlock.h crypto/crypto.h crypto/random.h
|
||||
@ -240,13 +259,13 @@ perl/config.o: perl/config.c common/debug.h common/error.auto.h common/error.h c
|
||||
perl/exec.o: perl/exec.c ../libc/LibC.h common/debug.h common/encode.h common/error.auto.h common/error.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h config/load.h config/parse.h crypto/cipher.h crypto/cipherBlock.h crypto/hash.h crypto/random.h perl/config.h perl/embed.auto.c perl/exec.h perl/libc.auto.c postgres/pageChecksum.h storage/driver/posix/driver.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/info.h version.h ../libc/xs/common/encode.xsh ../libc/xs/crypto/cipherBlock.xsh ../libc/xs/crypto/hash.xsh
|
||||
$(CC) $(CFLAGS) -c perl/exec.c -o perl/exec.o
|
||||
|
||||
postgres/info.o: postgres/info.c common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h postgres/info.h postgres/type.h postgres/version.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
postgres/info.o: postgres/info.c common/debug.h common/error.auto.h common/error.h common/io/read.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h postgres/info.h postgres/type.h postgres/version.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c postgres/info.c -o postgres/info.o
|
||||
|
||||
postgres/pageChecksum.o: postgres/pageChecksum.c common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/stackTrace.h common/type/convert.h postgres/pageChecksum.h postgres/type.h
|
||||
$(CC) $(CFLAGS) -funroll-loops -ftree-vectorize -c postgres/pageChecksum.c -o postgres/pageChecksum.o
|
||||
|
||||
storage/driver/posix/driver.o: storage/driver/posix/driver.c common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/regExp.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h storage/driver/posix/driver.h storage/driver/posix/driverFile.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/info.h storage/storage.h version.h
|
||||
storage/driver/posix/driver.o: storage/driver/posix/driver.c common/debug.h common/error.auto.h common/error.h common/io/read.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/regExp.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h storage/driver/posix/driver.h storage/driver/posix/driverFile.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c storage/driver/posix/driver.c -o storage/driver/posix/driver.o
|
||||
|
||||
storage/driver/posix/driverFile.o: storage/driver/posix/driverFile.c common/assert.h common/debug.h common/error.auto.h common/error.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h storage/driver/posix/driverFile.h
|
||||
@ -255,17 +274,17 @@ storage/driver/posix/driverFile.o: storage/driver/posix/driverFile.c common/asse
|
||||
storage/driver/posix/driverRead.o: storage/driver/posix/driverRead.c common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h storage/driver/posix/driverFile.h storage/driver/posix/driverRead.h
|
||||
$(CC) $(CFLAGS) -c storage/driver/posix/driverRead.c -o storage/driver/posix/driverRead.o
|
||||
|
||||
storage/driver/posix/driverWrite.o: storage/driver/posix/driverWrite.c common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h storage/driver/posix/driver.h storage/driver/posix/driverFile.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileWrite.h storage/info.h version.h
|
||||
storage/driver/posix/driverWrite.o: storage/driver/posix/driverWrite.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h storage/driver/posix/driver.h storage/driver/posix/driverFile.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileWrite.h storage/info.h version.h
|
||||
$(CC) $(CFLAGS) -c storage/driver/posix/driverWrite.c -o storage/driver/posix/driverWrite.o
|
||||
|
||||
storage/fileRead.o: storage/fileRead.c common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h storage/driver/posix/driverRead.h storage/fileRead.h
|
||||
storage/fileRead.o: storage/fileRead.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/read.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h storage/driver/posix/driverRead.h storage/fileRead.h
|
||||
$(CC) $(CFLAGS) -c storage/fileRead.c -o storage/fileRead.o
|
||||
|
||||
storage/fileWrite.o: storage/fileWrite.c common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h storage/driver/posix/driverWrite.h storage/fileWrite.h version.h
|
||||
storage/fileWrite.o: storage/fileWrite.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/string.h storage/driver/posix/driverWrite.h storage/fileWrite.h version.h
|
||||
$(CC) $(CFLAGS) -c storage/fileWrite.c -o storage/fileWrite.o
|
||||
|
||||
storage/helper.o: storage/helper.c common/debug.h common/error.auto.h common/error.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
storage/helper.o: storage/helper.c common/debug.h common/error.auto.h common/error.h common/io/read.h common/io/write.h common/lock.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h config/config.auto.h config/config.h config/define.auto.h config/define.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/helper.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c storage/helper.c -o storage/helper.o
|
||||
|
||||
storage/storage.o: storage/storage.c common/assert.h common/debug.h common/error.auto.h common/error.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h storage/driver/posix/driver.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/info.h storage/storage.h version.h
|
||||
storage/storage.o: storage/storage.c common/assert.h common/debug.h common/error.auto.h common/error.h common/io/io.h common/io/read.h common/io/write.h common/log.h common/logLevel.h common/memContext.h common/stackTrace.h common/type/buffer.h common/type/convert.h common/type/keyValue.h common/type/string.h common/type/stringList.h common/type/variant.h common/type/variantList.h common/wait.h storage/driver/posix/driver.h storage/driver/posix/driverRead.h storage/driver/posix/driverWrite.h storage/fileRead.h storage/fileWrite.h storage/info.h storage/storage.h version.h
|
||||
$(CC) $(CFLAGS) -c storage/storage.c -o storage/storage.o
|
||||
|
146
src/common/io/bufferRead.c
Normal file
146
src/common/io/bufferRead.c
Normal file
@ -0,0 +1,146 @@
|
||||
/***********************************************************************************************************************************
|
||||
Buffer IO Read
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/assert.h"
|
||||
#include "common/debug.h"
|
||||
#include "common/io/bufferRead.h"
|
||||
#include "common/log.h"
|
||||
#include "common/memContext.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Buffer read object
|
||||
***********************************************************************************************************************************/
|
||||
struct IoBufferRead
|
||||
{
|
||||
MemContext *memContext;
|
||||
IoRead *io;
|
||||
const Buffer *read;
|
||||
size_t readPos;
|
||||
bool eof;
|
||||
};
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Read from the buffer
|
||||
***********************************************************************************************************************************/
|
||||
static size_t
|
||||
ioBufferRead(IoBufferRead *this, Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_BUFFER_READ, this);
|
||||
FUNCTION_DEBUG_PARAM(BUFFER, buffer);
|
||||
|
||||
FUNCTION_DEBUG_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_ASSERT(buffer != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
size_t actualBytes = 0;
|
||||
|
||||
if (!this->eof)
|
||||
{
|
||||
// Determine how many bytes can actually be read from the buffer (if all bytes will be read then EOF)
|
||||
actualBytes = bufUsed(this->read) - this->readPos;
|
||||
|
||||
if (actualBytes > bufRemains(buffer))
|
||||
actualBytes = bufRemains(buffer);
|
||||
else
|
||||
this->eof = true;
|
||||
|
||||
// Copy bytes to buffer
|
||||
bufCatSub(buffer, this->read, this->readPos, actualBytes);
|
||||
this->readPos += actualBytes;
|
||||
}
|
||||
|
||||
FUNCTION_DEBUG_RESULT(SIZE, actualBytes);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Have all bytes been read from the buffer?
|
||||
***********************************************************************************************************************************/
|
||||
static bool
|
||||
ioBufferReadEof(IoBufferRead *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_BUFFER_READ, this);
|
||||
|
||||
FUNCTION_DEBUG_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(BOOL, this->eof);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Create object
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferRead *
|
||||
ioBufferReadNew(const Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(BUFFER, buffer);
|
||||
|
||||
FUNCTION_TEST_ASSERT(buffer != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
IoBufferRead *this = NULL;
|
||||
|
||||
MEM_CONTEXT_NEW_BEGIN("IoBufferRead")
|
||||
{
|
||||
this = memNew(sizeof(IoBufferRead));
|
||||
this->memContext = memContextCurrent();
|
||||
|
||||
this->read = buffer;
|
||||
this->io = ioReadNew(this, NULL, (IoReadProcess)ioBufferRead, NULL, (IoReadEof)ioBufferReadEof);
|
||||
}
|
||||
MEM_CONTEXT_NEW_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(IO_BUFFER_READ, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Move the object to a new context
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferRead *
|
||||
ioBufferReadMove(IoBufferRead *this, MemContext *parentNew)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(IO_BUFFER_READ, this);
|
||||
FUNCTION_TEST_PARAM(MEM_CONTEXT, parentNew);
|
||||
|
||||
FUNCTION_TEST_ASSERT(parentNew != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
if (this != NULL)
|
||||
memContextMove(this->memContext, parentNew);
|
||||
|
||||
FUNCTION_TEST_RESULT(IO_BUFFER_READ, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get io interface
|
||||
***********************************************************************************************************************************/
|
||||
IoRead *
|
||||
ioBufferReadIo(const IoBufferRead *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(IO_BUFFER_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(IO_READ, this->io);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Free the object
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
ioBufferReadFree(IoBufferRead *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_BUFFER_READ, this);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
if (this != NULL)
|
||||
memContextFree(this->memContext);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
42
src/common/io/bufferRead.h
Normal file
42
src/common/io/bufferRead.h
Normal file
@ -0,0 +1,42 @@
|
||||
/***********************************************************************************************************************************
|
||||
Buffer IO Read
|
||||
***********************************************************************************************************************************/
|
||||
#ifndef COMMON_IO_BUFFERREAD_H
|
||||
#define COMMON_IO_BUFFERREAD_H
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Buffer read object
|
||||
***********************************************************************************************************************************/
|
||||
typedef struct IoBufferRead IoBufferRead;
|
||||
|
||||
#include "common/io/read.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Constructor
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferRead *ioBufferReadNew(const Buffer *buffer);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Functions
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferRead *ioBufferReadMove(IoBufferRead *this, MemContext *parentNew);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Getters
|
||||
***********************************************************************************************************************************/
|
||||
IoRead *ioBufferReadIo(const IoBufferRead *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Destructor
|
||||
***********************************************************************************************************************************/
|
||||
void ioBufferReadFree(IoBufferRead *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Macros for function logging
|
||||
***********************************************************************************************************************************/
|
||||
#define FUNCTION_DEBUG_IO_BUFFER_READ_TYPE \
|
||||
IoBufferRead *
|
||||
#define FUNCTION_DEBUG_IO_BUFFER_READ_FORMAT(value, buffer, bufferSize) \
|
||||
objToLog(value, "IoBufferRead", buffer, bufferSize)
|
||||
|
||||
#endif
|
114
src/common/io/bufferWrite.c
Normal file
114
src/common/io/bufferWrite.c
Normal file
@ -0,0 +1,114 @@
|
||||
/***********************************************************************************************************************************
|
||||
Buffer IO Write
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/assert.h"
|
||||
#include "common/debug.h"
|
||||
#include "common/io/bufferWrite.h"
|
||||
#include "common/log.h"
|
||||
#include "common/memContext.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Buffer write object
|
||||
***********************************************************************************************************************************/
|
||||
struct IoBufferWrite
|
||||
{
|
||||
MemContext *memContext;
|
||||
IoWrite *io;
|
||||
Buffer *write;
|
||||
};
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Write to the buffer
|
||||
***********************************************************************************************************************************/
|
||||
static void
|
||||
ioBufferWrite(IoBufferWrite *this, Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_BUFFER_WRITE, this);
|
||||
FUNCTION_DEBUG_PARAM(BUFFER, buffer);
|
||||
|
||||
FUNCTION_DEBUG_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_ASSERT(buffer != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
bufCat(this->write, buffer);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Create object
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferWrite *
|
||||
ioBufferWriteNew(Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(BUFFER, buffer);
|
||||
|
||||
FUNCTION_TEST_ASSERT(buffer != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
IoBufferWrite *this = NULL;
|
||||
|
||||
MEM_CONTEXT_NEW_BEGIN("IoBufferWrite")
|
||||
{
|
||||
this = memNew(sizeof(IoBufferWrite));
|
||||
this->memContext = memContextCurrent();
|
||||
|
||||
this->write = buffer;
|
||||
this->io = ioWriteNew(this, NULL, (IoWriteProcess)ioBufferWrite, NULL);
|
||||
}
|
||||
MEM_CONTEXT_NEW_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(IO_BUFFER_WRITE, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Move the object to a new context
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferWrite *
|
||||
ioBufferWriteMove(IoBufferWrite *this, MemContext *parentNew)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(IO_BUFFER_WRITE, this);
|
||||
FUNCTION_TEST_PARAM(MEM_CONTEXT, parentNew);
|
||||
|
||||
FUNCTION_TEST_ASSERT(parentNew != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
if (this != NULL)
|
||||
memContextMove(this->memContext, parentNew);
|
||||
|
||||
FUNCTION_TEST_RESULT(IO_BUFFER_WRITE, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get io interface
|
||||
***********************************************************************************************************************************/
|
||||
IoWrite *
|
||||
ioBufferWriteIo(const IoBufferWrite *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(IO_BUFFER_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(IO_WRITE, this->io);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Free the object
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
ioBufferWriteFree(IoBufferWrite *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_BUFFER_WRITE, this);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
if (this != NULL)
|
||||
memContextFree(this->memContext);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
42
src/common/io/bufferWrite.h
Normal file
42
src/common/io/bufferWrite.h
Normal file
@ -0,0 +1,42 @@
|
||||
/***********************************************************************************************************************************
|
||||
Buffer IO Write
|
||||
***********************************************************************************************************************************/
|
||||
#ifndef COMMON_IO_BUFFERWRITE_H
|
||||
#define COMMON_IO_BUFFERWRITE_H
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Buffer write object
|
||||
***********************************************************************************************************************************/
|
||||
typedef struct IoBufferWrite IoBufferWrite;
|
||||
|
||||
#include "common/io/write.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Constructor
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferWrite *ioBufferWriteNew(Buffer *buffer);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Functions
|
||||
***********************************************************************************************************************************/
|
||||
IoBufferWrite *ioBufferWriteMove(IoBufferWrite *this, MemContext *parentNew);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Getters
|
||||
***********************************************************************************************************************************/
|
||||
IoWrite *ioBufferWriteIo(const IoBufferWrite *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Destructor
|
||||
***********************************************************************************************************************************/
|
||||
void ioBufferWriteFree(IoBufferWrite *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Macros for function logging
|
||||
***********************************************************************************************************************************/
|
||||
#define FUNCTION_DEBUG_IO_BUFFER_WRITE_TYPE \
|
||||
IoBufferWrite *
|
||||
#define FUNCTION_DEBUG_IO_BUFFER_WRITE_FORMAT(value, buffer, bufferSize) \
|
||||
objToLog(value, "IoBufferWrite", buffer, bufferSize)
|
||||
|
||||
#endif
|
40
src/common/io/io.c
Normal file
40
src/common/io/io.c
Normal file
@ -0,0 +1,40 @@
|
||||
/***********************************************************************************************************************************
|
||||
IO Functions
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/assert.h"
|
||||
#include "common/debug.h"
|
||||
#include "common/io/io.h"
|
||||
#include "common/log.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Buffer size
|
||||
|
||||
This buffer size will be used for all IO operations that require buffers not passed by the caller. Initially it is set to a
|
||||
conservative default with the expectation that it will be changed to a new value after options have been loaded. In general callers
|
||||
should set their buffer size using ioBufferSize() but there may be cases where an alternative buffer size makes sense.
|
||||
***********************************************************************************************************************************/
|
||||
#define IO_BUFFER_BLOCK_SIZE (8 * 1024)
|
||||
|
||||
static size_t bufferSize = (8 * IO_BUFFER_BLOCK_SIZE);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get/set buffer size
|
||||
***********************************************************************************************************************************/
|
||||
size_t
|
||||
ioBufferSize()
|
||||
{
|
||||
FUNCTION_TEST_VOID();
|
||||
FUNCTION_TEST_RESULT(SIZE, bufferSize);
|
||||
}
|
||||
|
||||
void
|
||||
ioBufferSizeSet(size_t bufferSizeParam)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(SIZE, bufferSizeParam);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
bufferSize = bufferSizeParam;
|
||||
|
||||
FUNCTION_TEST_RESULT_VOID();
|
||||
}
|
15
src/common/io/io.h
Normal file
15
src/common/io/io.h
Normal file
@ -0,0 +1,15 @@
|
||||
/***********************************************************************************************************************************
|
||||
IO Functions
|
||||
***********************************************************************************************************************************/
|
||||
#ifndef COMMON_IO_IO_H
|
||||
#define COMMON_IO_IO_H
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Getters/Setters
|
||||
***********************************************************************************************************************************/
|
||||
size_t ioBufferSize();
|
||||
void ioBufferSizeSet(size_t bufferSize);
|
||||
|
||||
#endif
|
133
src/common/io/read.c
Normal file
133
src/common/io/read.c
Normal file
@ -0,0 +1,133 @@
|
||||
/***********************************************************************************************************************************
|
||||
IO Read
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/debug.h"
|
||||
#include "common/io/read.h"
|
||||
#include "common/log.h"
|
||||
#include "common/memContext.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
IO read object
|
||||
***********************************************************************************************************************************/
|
||||
struct IoRead
|
||||
{
|
||||
MemContext *memContext; // Mem context of driver
|
||||
void *driver; // Driver object
|
||||
IoReadOpen open; // Driver open
|
||||
IoReadProcess process; // Driver read
|
||||
IoReadClose close; // Driver close
|
||||
IoReadEof eof; // Driver eof
|
||||
size_t size; // Total bytes read
|
||||
};
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Create a new read IO
|
||||
|
||||
Allocations will be in the memory context of the caller.
|
||||
***********************************************************************************************************************************/
|
||||
IoRead *
|
||||
ioReadNew(void *driver, IoReadOpen open, IoReadProcess process, IoReadClose close, IoReadEof eof)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(VOIDP, driver);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, open);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, process);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, close);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, eof);
|
||||
|
||||
FUNCTION_TEST_ASSERT(driver != NULL);
|
||||
FUNCTION_TEST_ASSERT(process != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
IoRead *this = memNew(sizeof(IoRead));
|
||||
this->memContext = memContextCurrent();
|
||||
this->driver = driver;
|
||||
this->open = open;
|
||||
this->process = process;
|
||||
this->close = close;
|
||||
this->eof = eof;
|
||||
|
||||
FUNCTION_DEBUG_RESULT(IO_READ, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Open the IO
|
||||
***********************************************************************************************************************************/
|
||||
bool
|
||||
ioReadOpen(IoRead *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(BOOL, this->open != NULL ? this->open(this->driver) : true);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Read data from IO
|
||||
***********************************************************************************************************************************/
|
||||
size_t
|
||||
ioRead(IoRead *this, Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_ASSERT(buffer != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
size_t result = this->process(this->driver, buffer);
|
||||
this->size += result;
|
||||
|
||||
FUNCTION_DEBUG_RESULT(SIZE, result);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Close the IO
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
ioReadClose(IoRead *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
if (this->close != NULL)
|
||||
this->close(this->driver);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Is IO at EOF?
|
||||
***********************************************************************************************************************************/
|
||||
bool
|
||||
ioReadEof(const IoRead *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(BOOL, this->eof != NULL ? this->eof(this->driver) : false);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Total bytes read
|
||||
***********************************************************************************************************************************/
|
||||
size_t
|
||||
ioReadSize(const IoRead *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(IO_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(SIZE, this->size);
|
||||
}
|
48
src/common/io/read.h
Normal file
48
src/common/io/read.h
Normal file
@ -0,0 +1,48 @@
|
||||
/***********************************************************************************************************************************
|
||||
IO Read
|
||||
***********************************************************************************************************************************/
|
||||
#ifndef COMMON_IO_READ_H
|
||||
#define COMMON_IO_READ_H
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
IO read object
|
||||
***********************************************************************************************************************************/
|
||||
typedef struct IoRead IoRead;
|
||||
|
||||
#include "common/type/buffer.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Function pointer types
|
||||
***********************************************************************************************************************************/
|
||||
typedef bool (*IoReadOpen)(void *driver);
|
||||
typedef size_t (*IoReadProcess)(void *driver, Buffer *buffer);
|
||||
typedef void (*IoReadClose)(void *driver);
|
||||
typedef bool (*IoReadEof)(void *driver);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Constructor
|
||||
***********************************************************************************************************************************/
|
||||
IoRead *ioReadNew(void *driver, IoReadOpen open, IoReadProcess process, IoReadClose close, IoReadEof eof);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Functions
|
||||
***********************************************************************************************************************************/
|
||||
bool ioReadOpen(IoRead *this);
|
||||
size_t ioRead(IoRead *this, Buffer *buffer);
|
||||
void ioReadClose(IoRead *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Getters
|
||||
***********************************************************************************************************************************/
|
||||
bool ioReadEof(const IoRead *this);
|
||||
size_t ioReadSize(const IoRead *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Macros for function logging
|
||||
***********************************************************************************************************************************/
|
||||
#define FUNCTION_DEBUG_IO_READ_TYPE \
|
||||
IoRead *
|
||||
#define FUNCTION_DEBUG_IO_READ_FORMAT(value, buffer, bufferSize) \
|
||||
objToLog(value, "IoRead", buffer, bufferSize)
|
||||
|
||||
#endif
|
121
src/common/io/write.c
Normal file
121
src/common/io/write.c
Normal file
@ -0,0 +1,121 @@
|
||||
/***********************************************************************************************************************************
|
||||
IO Write
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/debug.h"
|
||||
#include "common/io/write.h"
|
||||
#include "common/log.h"
|
||||
#include "common/memContext.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
IO write object
|
||||
***********************************************************************************************************************************/
|
||||
struct IoWrite
|
||||
{
|
||||
MemContext *memContext; // Mem context of driver
|
||||
void *driver; // Driver object
|
||||
IoWriteOpen open; // Driver open
|
||||
IoWriteProcess process; // Driver write
|
||||
IoWriteClose close; // Driver close
|
||||
size_t size; // Total bytes written
|
||||
};
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Create a new write IO
|
||||
|
||||
Allocations will be in the memory context of the caller.
|
||||
***********************************************************************************************************************************/
|
||||
IoWrite *
|
||||
ioWriteNew(void *driver, IoWriteOpen open, IoWriteProcess process, IoWriteClose close)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(VOIDP, driver);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, open);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, process);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, close);
|
||||
|
||||
FUNCTION_TEST_ASSERT(driver != NULL);
|
||||
FUNCTION_TEST_ASSERT(process != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
IoWrite *this = memNew(sizeof(IoWrite));
|
||||
this->memContext = memContextCurrent();
|
||||
this->driver = driver;
|
||||
this->open = open;
|
||||
this->process = process;
|
||||
this->close = close;
|
||||
|
||||
FUNCTION_DEBUG_RESULT(IO_WRITE, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Open the IO
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
ioWriteOpen(IoWrite *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
if (this->open != NULL)
|
||||
this->open(this->driver);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Write data to IO
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
ioWrite(IoWrite *this, const Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
// Only write if there is data to write
|
||||
if (buffer != NULL && bufSize(buffer) > 0)
|
||||
{
|
||||
this->process(this->driver, buffer);
|
||||
this->size += bufUsed(buffer);
|
||||
}
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Close the IO
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
ioWriteClose(IoWrite *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(IO_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
if (this->close != NULL)
|
||||
this->close(this->driver);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Total bytes written
|
||||
***********************************************************************************************************************************/
|
||||
size_t
|
||||
ioWriteSize(const IoWrite *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(IO_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(SIZE, this->size);
|
||||
}
|
46
src/common/io/write.h
Normal file
46
src/common/io/write.h
Normal file
@ -0,0 +1,46 @@
|
||||
/***********************************************************************************************************************************
|
||||
IO Write
|
||||
***********************************************************************************************************************************/
|
||||
#ifndef COMMON_IO_WRITE_H
|
||||
#define COMMON_IO_WRITE_H
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
IO write object
|
||||
***********************************************************************************************************************************/
|
||||
typedef struct IoWrite IoWrite;
|
||||
|
||||
#include "common/type/buffer.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Function pointer types
|
||||
***********************************************************************************************************************************/
|
||||
typedef void (*IoWriteOpen)(void *driver);
|
||||
typedef void (*IoWriteProcess)(void *driver, const Buffer *buffer);
|
||||
typedef void (*IoWriteClose)(void *driver);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Constructor
|
||||
***********************************************************************************************************************************/
|
||||
IoWrite *ioWriteNew(void *driver, IoWriteOpen open, IoWriteProcess process, IoWriteClose close);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Functions
|
||||
***********************************************************************************************************************************/
|
||||
void ioWriteOpen(IoWrite *this);
|
||||
void ioWrite(IoWrite *this, const Buffer *buffer);
|
||||
void ioWriteClose(IoWrite *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Getters
|
||||
***********************************************************************************************************************************/
|
||||
size_t ioWriteSize(const IoWrite *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Macros for function logging
|
||||
***********************************************************************************************************************************/
|
||||
#define FUNCTION_DEBUG_IO_WRITE_TYPE \
|
||||
IoWrite *
|
||||
#define FUNCTION_DEBUG_IO_WRITE_FORMAT(value, buffer, bufferSize) \
|
||||
objToLog(value, "IoWrite", buffer, bufferSize)
|
||||
|
||||
#endif
|
@ -102,16 +102,64 @@ bufCat(Buffer *this, const Buffer *cat)
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
if (cat != NULL && cat->used > 0)
|
||||
if (cat != NULL)
|
||||
bufCatC(this, cat->buffer, 0, cat->used);
|
||||
|
||||
FUNCTION_TEST_RESULT(BUFFER, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Append a C buffer
|
||||
***********************************************************************************************************************************/
|
||||
Buffer *
|
||||
bufCatC(Buffer *this, const unsigned char *cat, size_t catOffset, size_t catSize)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(BUFFER, this);
|
||||
FUNCTION_TEST_PARAM(UCHARP, cat);
|
||||
FUNCTION_TEST_PARAM(SIZE, catOffset);
|
||||
FUNCTION_TEST_PARAM(SIZE, catSize);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_ASSERT(catSize == 0 || cat != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
if (catSize > 0)
|
||||
{
|
||||
if (this->used + cat->used > this->size)
|
||||
bufResize(this, this->used + cat->used);
|
||||
if (this->used + catSize > this->size)
|
||||
bufResize(this, this->used + catSize);
|
||||
|
||||
// Just here to silence nonnull warnings from clang static analyzer
|
||||
ASSERT_DEBUG(this->buffer != NULL);
|
||||
|
||||
memcpy(this->buffer + this->used, cat->buffer, cat->used);
|
||||
this->used = this->used + cat->used;
|
||||
memcpy(this->buffer + this->used, cat + catOffset, catSize);
|
||||
this->used += catSize;
|
||||
}
|
||||
|
||||
FUNCTION_TEST_RESULT(BUFFER, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Append a subset of another buffer
|
||||
***********************************************************************************************************************************/
|
||||
Buffer *
|
||||
bufCatSub(Buffer *this, const Buffer *cat, size_t catOffset, size_t catSize)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(BUFFER, this);
|
||||
FUNCTION_TEST_PARAM(BUFFER, cat);
|
||||
FUNCTION_TEST_PARAM(SIZE, catOffset);
|
||||
FUNCTION_TEST_PARAM(SIZE, catSize);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
if (cat != NULL)
|
||||
{
|
||||
ASSERT(catOffset <= cat->used);
|
||||
ASSERT(catSize <= cat->used - catOffset);
|
||||
|
||||
bufCatC(this, cat->buffer, catOffset, catSize);
|
||||
}
|
||||
|
||||
FUNCTION_TEST_RESULT(BUFFER, this);
|
||||
|
@ -20,6 +20,8 @@ Buffer *bufNewC(size_t size, const void *buffer);
|
||||
Buffer *bufNewStr(const String *string);
|
||||
|
||||
Buffer *bufCat(Buffer *this, const Buffer *cat);
|
||||
Buffer *bufCatC(Buffer *this, const unsigned char *cat, size_t catOffset, size_t catSize);
|
||||
Buffer *bufCatSub(Buffer *this, const Buffer *cat, size_t catOffset, size_t catSize);
|
||||
bool bufEq(const Buffer *this, const Buffer *compare);
|
||||
Buffer *bufMove(Buffer *this, MemContext *parentNew);
|
||||
Buffer *bufResize(Buffer *this, size_t size);
|
||||
|
@ -64,7 +64,7 @@ strNewBuf(const Buffer *buffer)
|
||||
// Create object
|
||||
String *this = memNew(sizeof(String));
|
||||
this->memContext = memContextCurrent();
|
||||
this->size = bufSize(buffer);
|
||||
this->size = bufUsed(buffer);
|
||||
|
||||
// Allocate and assign string
|
||||
this->buffer = memNewRaw(this->size + 1);
|
||||
|
@ -7,6 +7,7 @@ Configuration Load
|
||||
#include "command/command.h"
|
||||
#include "common/memContext.h"
|
||||
#include "common/debug.h"
|
||||
#include "common/io/io.h"
|
||||
#include "common/lock.h"
|
||||
#include "common/log.h"
|
||||
#include "config/config.h"
|
||||
@ -223,6 +224,10 @@ cfgLoad(unsigned int argListSize, const char *argList[])
|
||||
// If a command is set
|
||||
if (cfgCommand() != cfgCmdNone)
|
||||
{
|
||||
// Set IO buffer size
|
||||
if (cfgOptionValid(cfgOptBufferSize))
|
||||
ioBufferSizeSet((size_t)cfgOptionInt(cfgOptBufferSize));
|
||||
|
||||
// Open the log file if this command logs to a file
|
||||
if (cfgLogFile() && !cfgCommandHelp())
|
||||
{
|
||||
@ -234,7 +239,7 @@ cfgLoad(unsigned int argListSize, const char *argList[])
|
||||
// Begin the command
|
||||
cmdBegin(true);
|
||||
|
||||
// Open the log file if this command logs to a file
|
||||
// Acquire a lock if this command requires a lock
|
||||
if (cfgLockRequired() && !cfgCommandHelp())
|
||||
lockAcquire(cfgOptionStr(cfgOptLockPath), cfgOptionStr(cfgOptStanza), cfgLockType(), 0, true);
|
||||
|
||||
|
@ -23,7 +23,6 @@ struct StorageFileReadPosix
|
||||
|
||||
int handle;
|
||||
bool eof;
|
||||
size_t size;
|
||||
};
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
@ -87,7 +86,7 @@ storageFileReadPosixOpen(StorageFileReadPosix *this)
|
||||
/***********************************************************************************************************************************
|
||||
Read from a file
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
size_t
|
||||
storageFileReadPosix(StorageFileReadPosix *this, Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
@ -99,19 +98,20 @@ storageFileReadPosix(StorageFileReadPosix *this, Buffer *buffer)
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
// Read if EOF has not been reached
|
||||
ssize_t actualBytes = 0;
|
||||
|
||||
if (!this->eof)
|
||||
{
|
||||
// Read and handle errors
|
||||
size_t expectedBytes = bufRemains(buffer);
|
||||
ssize_t actualBytes = read(this->handle, bufRemainsPtr(buffer), expectedBytes);
|
||||
actualBytes = read(this->handle, bufRemainsPtr(buffer), expectedBytes);
|
||||
|
||||
// Error occurred during write
|
||||
if (actualBytes == -1)
|
||||
THROW_SYS_ERROR_FMT(FileReadError, "unable to read '%s'", strPtr(this->name));
|
||||
|
||||
// Update amount of buffer used and total size
|
||||
// Update amount of buffer used
|
||||
bufUsedInc(buffer, (size_t)actualBytes);
|
||||
this->size += (size_t)actualBytes;
|
||||
|
||||
// If less data than expected was read then EOF. The file may not actually be EOF but we are not concerned with files that
|
||||
// are growing. Just read up to the point where the file is being extended.
|
||||
@ -119,7 +119,7 @@ storageFileReadPosix(StorageFileReadPosix *this, Buffer *buffer)
|
||||
this->eof = true;
|
||||
}
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
FUNCTION_DEBUG_RESULT(SIZE, (size_t)actualBytes);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
@ -191,21 +191,6 @@ storageFileReadPosixName(StorageFileReadPosix *this)
|
||||
FUNCTION_TEST_RESULT(CONST_STRING, this->name);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
File size
|
||||
***********************************************************************************************************************************/
|
||||
size_t
|
||||
storageFileReadPosixSize(StorageFileReadPosix *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(STORAGE_FILE_READ_POSIX, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(SIZE, this->size);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Free the file
|
||||
***********************************************************************************************************************************/
|
||||
|
@ -21,7 +21,7 @@ StorageFileReadPosix *storageFileReadPosixNew(const String *name, bool ignoreMis
|
||||
Functions
|
||||
***********************************************************************************************************************************/
|
||||
bool storageFileReadPosixOpen(StorageFileReadPosix *this);
|
||||
void storageFileReadPosix(StorageFileReadPosix *this, Buffer *buffer);
|
||||
size_t storageFileReadPosix(StorageFileReadPosix *this, Buffer *buffer);
|
||||
void storageFileReadPosixClose(StorageFileReadPosix *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
@ -30,7 +30,6 @@ Getters
|
||||
bool storageFileReadPosixEof(StorageFileReadPosix *this);
|
||||
bool storageFileReadPosixIgnoreMissing(StorageFileReadPosix *this);
|
||||
const String *storageFileReadPosixName(StorageFileReadPosix *this);
|
||||
size_t storageFileReadPosixSize(StorageFileReadPosix *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Destructor
|
||||
|
@ -14,22 +14,20 @@ struct StorageFileRead
|
||||
{
|
||||
MemContext *memContext;
|
||||
StorageFileReadPosix *fileDriver;
|
||||
size_t bufferSize;
|
||||
IoRead *io;
|
||||
};
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Create a new storage file
|
||||
***********************************************************************************************************************************/
|
||||
StorageFileRead *
|
||||
storageFileReadNew(const String *name, bool ignoreMissing, size_t bufferSize)
|
||||
storageFileReadNew(const String *name, bool ignoreMissing)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(STRING, name);
|
||||
FUNCTION_DEBUG_PARAM(BOOL, ignoreMissing);
|
||||
FUNCTION_DEBUG_PARAM(BOOL, bufferSize);
|
||||
|
||||
FUNCTION_TEST_ASSERT(name != NULL);
|
||||
FUNCTION_TEST_ASSERT(bufferSize > 0);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
StorageFileRead *this = NULL;
|
||||
@ -40,45 +38,16 @@ storageFileReadNew(const String *name, bool ignoreMissing, size_t bufferSize)
|
||||
this->memContext = memContextCurrent();
|
||||
|
||||
this->fileDriver = storageFileReadPosixNew(name, ignoreMissing);
|
||||
this->bufferSize = bufferSize;
|
||||
|
||||
this->io = ioReadNew(
|
||||
this->fileDriver, (IoReadOpen)storageFileReadPosixOpen, (IoReadProcess)storageFileReadPosix,
|
||||
(IoReadClose)storageFileReadPosixClose, (IoReadEof)storageFileReadPosixEof);
|
||||
}
|
||||
MEM_CONTEXT_NEW_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(STORAGE_FILE_READ, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Open the file
|
||||
***********************************************************************************************************************************/
|
||||
bool
|
||||
storageFileReadOpen(StorageFileRead *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(STORAGE_FILE_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(BOOL, storageFileReadPosixOpen(this->fileDriver));
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Read data from the file
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
storageFileRead(StorageFileRead *this, Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(STORAGE_FILE_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
storageFileReadPosix(this->fileDriver, buffer);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Move the file object to a new context
|
||||
***********************************************************************************************************************************/
|
||||
@ -98,38 +67,6 @@ storageFileReadMove(StorageFileRead *this, MemContext *parentNew)
|
||||
FUNCTION_TEST_RESULT(STORAGE_FILE_READ, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Close the file
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
storageFileReadClose(StorageFileRead *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(STORAGE_FILE_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
storageFileReadPosixClose(this->fileDriver);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get buffer size
|
||||
***********************************************************************************************************************************/
|
||||
size_t
|
||||
storageFileReadBufferSize(const StorageFileRead *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(STORAGE_FILE_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(SIZE, this->bufferSize);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get file driver
|
||||
***********************************************************************************************************************************/
|
||||
@ -146,10 +83,10 @@ storageFileReadFileDriver(const StorageFileRead *this)
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Has file reached EOF?
|
||||
Get io interface
|
||||
***********************************************************************************************************************************/
|
||||
bool
|
||||
storageFileReadEof(const StorageFileRead *this)
|
||||
IoRead *
|
||||
storageFileReadIo(const StorageFileRead *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(STORAGE_FILE_READ, this);
|
||||
@ -157,7 +94,7 @@ storageFileReadEof(const StorageFileRead *this)
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(BOOL, storageFileReadPosixEof(this->fileDriver));
|
||||
FUNCTION_TEST_RESULT(IO_READ, this->io);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
@ -190,21 +127,6 @@ storageFileReadName(const StorageFileRead *this)
|
||||
FUNCTION_TEST_RESULT(CONST_STRING, storageFileReadPosixName(this->fileDriver));
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get file size
|
||||
***********************************************************************************************************************************/
|
||||
size_t
|
||||
storageFileReadSize(const StorageFileRead *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(STORAGE_FILE_READ, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(SIZE, storageFileReadPosixSize(this->fileDriver));
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Free the file
|
||||
***********************************************************************************************************************************/
|
||||
|
@ -9,6 +9,7 @@ Storage file read object
|
||||
***********************************************************************************************************************************/
|
||||
typedef struct StorageFileRead StorageFileRead;
|
||||
|
||||
#include "common/io/read.h"
|
||||
#include "common/type/buffer.h"
|
||||
#include "common/type/string.h"
|
||||
#include "storage/driver/posix/driverRead.h"
|
||||
@ -16,26 +17,20 @@ typedef struct StorageFileRead StorageFileRead;
|
||||
/***********************************************************************************************************************************
|
||||
Constructor
|
||||
***********************************************************************************************************************************/
|
||||
StorageFileRead *storageFileReadNew(const String *name, bool ignoreMissing, size_t bufferSize);
|
||||
StorageFileRead *storageFileReadNew(const String *name, bool ignoreMissing);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Functions
|
||||
***********************************************************************************************************************************/
|
||||
bool storageFileReadOpen(StorageFileRead *this);
|
||||
void storageFileRead(StorageFileRead *this, Buffer *buffer);
|
||||
void storageFileReadClose(StorageFileRead *this);
|
||||
|
||||
StorageFileRead *storageFileReadMove(StorageFileRead *this, MemContext *parentNew);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Getters
|
||||
***********************************************************************************************************************************/
|
||||
size_t storageFileReadBufferSize(const StorageFileRead *this);
|
||||
StorageFileReadPosix *storageFileReadFileDriver(const StorageFileRead *this);
|
||||
bool storageFileReadEof(const StorageFileRead *this);
|
||||
IoRead *storageFileReadIo(const StorageFileRead *this);
|
||||
bool storageFileReadIgnoreMissing(const StorageFileRead *this);
|
||||
const String *storageFileReadName(const StorageFileRead *this);
|
||||
size_t storageFileReadSize(const StorageFileRead *this);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Destructor
|
||||
|
@ -14,6 +14,7 @@ struct StorageFileWrite
|
||||
{
|
||||
MemContext *memContext;
|
||||
StorageFileWritePosix *fileDriver;
|
||||
IoWrite *io;
|
||||
};
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
@ -42,58 +43,22 @@ storageFileWriteNew(
|
||||
|
||||
ASSERT_DEBUG(name != NULL);
|
||||
|
||||
// Create the file. The file driver is not created here because we don't want to open the file for write until we know that
|
||||
// there is a source file.
|
||||
MEM_CONTEXT_NEW_BEGIN("StorageFileWrite")
|
||||
{
|
||||
this = memNew(sizeof(StorageFileWrite));
|
||||
this->memContext = MEM_CONTEXT_NEW();
|
||||
|
||||
this->fileDriver = storageFileWritePosixNew(name, modeFile, modePath, noCreatePath, noSyncFile, noSyncPath, noAtomic);
|
||||
|
||||
this->io = ioWriteNew(
|
||||
this->fileDriver, (IoWriteOpen)storageFileWritePosixOpen, (IoWriteProcess)storageFileWritePosix,
|
||||
(IoWriteClose)storageFileWritePosixClose);
|
||||
}
|
||||
MEM_CONTEXT_NEW_END();
|
||||
|
||||
FUNCTION_DEBUG_RESULT(STORAGE_FILE_WRITE, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Open the file
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
storageFileWriteOpen(StorageFileWrite *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(STORAGE_FILE_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
// Open the file
|
||||
storageFileWritePosixOpen(this->fileDriver);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Write to a file
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
storageFileWrite(StorageFileWrite *this, const Buffer *buffer)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(STORAGE_FILE_WRITE, this);
|
||||
FUNCTION_DEBUG_PARAM(BUFFER, buffer);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
// Only write if there is data to write
|
||||
if (buffer != NULL && bufSize(buffer) > 0)
|
||||
storageFileWritePosix(this->fileDriver, buffer);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Move the file object to a new context
|
||||
***********************************************************************************************************************************/
|
||||
@ -113,23 +78,6 @@ storageFileWriteMove(StorageFileWrite *this, MemContext *parentNew)
|
||||
FUNCTION_TEST_RESULT(STORAGE_FILE_WRITE, this);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Close the file
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
storageFileWriteClose(StorageFileWrite *this)
|
||||
{
|
||||
FUNCTION_DEBUG_BEGIN(logLevelTrace);
|
||||
FUNCTION_DEBUG_PARAM(STORAGE_FILE_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
storageFileWritePosixClose(this->fileDriver);
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Will the file be written atomically?
|
||||
|
||||
@ -177,6 +125,21 @@ storageFileWriteFileDriver(const StorageFileWrite *this)
|
||||
FUNCTION_TEST_RESULT(STORAGE_FILE_WRITE_POSIX, this->fileDriver);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get the IO object
|
||||
***********************************************************************************************************************************/
|
||||
IoWrite *
|
||||
storageFileWriteIo(const StorageFileWrite *this)
|
||||
{
|
||||
FUNCTION_TEST_BEGIN();
|
||||
FUNCTION_TEST_PARAM(STORAGE_FILE_WRITE, this);
|
||||
|
||||
FUNCTION_TEST_ASSERT(this != NULL);
|
||||
FUNCTION_TEST_END();
|
||||
|
||||
FUNCTION_TEST_RESULT(IO_WRITE, this->io);
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Get file mode
|
||||
***********************************************************************************************************************************/
|
||||
|
@ -11,6 +11,7 @@ Storage file read object
|
||||
***********************************************************************************************************************************/
|
||||
typedef struct StorageFileWrite StorageFileWrite;
|
||||
|
||||
#include "common/io/write.h"
|
||||
#include "common/type/buffer.h"
|
||||
#include "common/type/string.h"
|
||||
#include "storage/driver/posix/driverWrite.h"
|
||||
@ -30,10 +31,6 @@ StorageFileWrite *storageFileWriteNew(
|
||||
/***********************************************************************************************************************************
|
||||
Functions
|
||||
***********************************************************************************************************************************/
|
||||
void storageFileWriteOpen(StorageFileWrite *this);
|
||||
void storageFileWrite(StorageFileWrite *this, const Buffer *buffer);
|
||||
void storageFileWriteClose(StorageFileWrite *this);
|
||||
|
||||
StorageFileWrite *storageFileWriteMove(StorageFileWrite *this, MemContext *parentNew);
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
@ -42,6 +39,7 @@ Getters
|
||||
bool storageFileWriteAtomic(const StorageFileWrite *this);
|
||||
bool storageFileWriteCreatePath(const StorageFileWrite *this);
|
||||
StorageFileWritePosix *storageFileWriteFileDriver(const StorageFileWrite *this);
|
||||
IoWrite *storageFileWriteIo(const StorageFileWrite *this);
|
||||
mode_t storageFileWriteModeFile(const StorageFileWrite *this);
|
||||
mode_t storageFileWriteModePath(const StorageFileWrite *this);
|
||||
const String *storageFileWriteName(const StorageFileWrite *this);
|
||||
|
@ -142,8 +142,7 @@ storageSpool()
|
||||
{
|
||||
storageSpoolStanza = strDup(cfgOptionStr(cfgOptStanza));
|
||||
storageSpoolData = storageNewP(
|
||||
cfgOptionStr(cfgOptSpoolPath), .bufferSize = (size_t)cfgOptionInt(cfgOptBufferSize),
|
||||
.pathExpressionFunction = storageSpoolPathExpression, .write = true);
|
||||
cfgOptionStr(cfgOptSpoolPath), .pathExpressionFunction = storageSpoolPathExpression, .write = true);
|
||||
}
|
||||
MEM_CONTEXT_END();
|
||||
}
|
||||
|
@ -6,6 +6,7 @@ Storage Manager
|
||||
|
||||
#include "common/assert.h"
|
||||
#include "common/debug.h"
|
||||
#include "common/io/io.h"
|
||||
#include "common/log.h"
|
||||
#include "common/memContext.h"
|
||||
#include "common/wait.h"
|
||||
@ -21,7 +22,6 @@ struct Storage
|
||||
String *path;
|
||||
mode_t modeFile;
|
||||
mode_t modePath;
|
||||
size_t bufferSize;
|
||||
bool write;
|
||||
StoragePathExpressionCallback pathExpressionFunction;
|
||||
};
|
||||
@ -36,7 +36,6 @@ storageNew(const String *path, StorageNewParam param)
|
||||
FUNCTION_DEBUG_PARAM(STRING, path);
|
||||
FUNCTION_DEBUG_PARAM(MODE, param.modeFile);
|
||||
FUNCTION_DEBUG_PARAM(MODE, param.modePath);
|
||||
FUNCTION_DEBUG_PARAM(SIZE, param.bufferSize);
|
||||
FUNCTION_DEBUG_PARAM(BOOL, param.write);
|
||||
FUNCTION_DEBUG_PARAM(FUNCTIONP, param.pathExpressionFunction);
|
||||
|
||||
@ -53,7 +52,6 @@ storageNew(const String *path, StorageNewParam param)
|
||||
this->path = strDup(path);
|
||||
this->modeFile = param.modeFile == 0 ? STORAGE_FILE_MODE_DEFAULT : param.modeFile;
|
||||
this->modePath = param.modePath == 0 ? STORAGE_PATH_MODE_DEFAULT : param.modePath;
|
||||
this->bufferSize = param.bufferSize == 0 ? STORAGE_BUFFER_SIZE_DEFAULT : param.bufferSize;
|
||||
this->write = param.write;
|
||||
this->pathExpressionFunction = param.pathExpressionFunction;
|
||||
}
|
||||
@ -81,25 +79,25 @@ storageCopy(StorageFileRead *source, StorageFileWrite *destination)
|
||||
MEM_CONTEXT_TEMP_BEGIN()
|
||||
{
|
||||
// Open source file
|
||||
if (storageFileReadOpen(source))
|
||||
if (ioReadOpen(storageFileReadIo(source)))
|
||||
{
|
||||
// Open the destination file now that we know the source file exists and is readable
|
||||
storageFileWriteOpen(destination);
|
||||
ioWriteOpen(storageFileWriteIo(destination));
|
||||
|
||||
// Copy data from source to destination
|
||||
Buffer *read = bufNew(storageFileReadBufferSize(source));
|
||||
Buffer *read = bufNew(ioBufferSize(source));
|
||||
|
||||
do
|
||||
{
|
||||
storageFileRead(source, read);
|
||||
storageFileWrite(destination, read);
|
||||
ioRead(storageFileReadIo(source), read);
|
||||
ioWrite(storageFileWriteIo(destination), read);
|
||||
bufUsedZero(read);
|
||||
}
|
||||
while (!storageFileReadEof(source));
|
||||
while (!ioReadEof(storageFileReadIo(source)));
|
||||
|
||||
// Close the source and destination files
|
||||
storageFileReadClose(source);
|
||||
storageFileWriteClose(destination);
|
||||
ioReadClose(storageFileReadIo(source));
|
||||
ioWriteClose(storageFileWriteIo(destination));
|
||||
|
||||
// Set result to indicate that the file was copied
|
||||
result = true;
|
||||
@ -164,7 +162,7 @@ storageGet(StorageFileRead *file, StorageGetParam param)
|
||||
Buffer *result = NULL;
|
||||
|
||||
// If the file exists
|
||||
if (storageFileReadOpen(file))
|
||||
if (ioReadOpen(storageFileReadIo(file)))
|
||||
{
|
||||
MEM_CONTEXT_TEMP_BEGIN()
|
||||
{
|
||||
@ -172,7 +170,7 @@ storageGet(StorageFileRead *file, StorageGetParam param)
|
||||
if (param.exactSize > 0)
|
||||
{
|
||||
result = bufNew(param.exactSize);
|
||||
storageFileRead(file, result);
|
||||
ioRead(storageFileReadIo(file), result);
|
||||
|
||||
// If an exact read make sure the size is as expected
|
||||
if (bufUsed(result) != param.exactSize)
|
||||
@ -185,18 +183,18 @@ storageGet(StorageFileRead *file, StorageGetParam param)
|
||||
else
|
||||
{
|
||||
result = bufNew(0);
|
||||
Buffer *read = bufNew(storageFileReadBufferSize(file));
|
||||
Buffer *read = bufNew(ioBufferSize(file));
|
||||
|
||||
do
|
||||
{
|
||||
// Read data
|
||||
storageFileRead(file, read);
|
||||
ioRead(storageFileReadIo(file), read);
|
||||
|
||||
// Add to result and free read buffer
|
||||
bufCat(result, read);
|
||||
bufUsedZero(read);
|
||||
}
|
||||
while (!storageFileReadEof(file));
|
||||
while (!ioReadEof(storageFileReadIo(file)));
|
||||
}
|
||||
|
||||
// Move buffer to parent context on success
|
||||
@ -204,7 +202,7 @@ storageGet(StorageFileRead *file, StorageGetParam param)
|
||||
}
|
||||
MEM_CONTEXT_TEMP_END();
|
||||
|
||||
storageFileReadClose(file);
|
||||
ioReadClose(storageFileReadIo(file));
|
||||
}
|
||||
|
||||
FUNCTION_DEBUG_RESULT(BUFFER, result);
|
||||
@ -324,8 +322,7 @@ storageNewRead(const Storage *this, const String *fileExp, StorageNewReadParam p
|
||||
|
||||
MEM_CONTEXT_TEMP_BEGIN()
|
||||
{
|
||||
result = storageFileReadMove(
|
||||
storageFileReadNew(storagePathNP(this, fileExp), param.ignoreMissing, this->bufferSize), MEM_CONTEXT_OLD());
|
||||
result = storageFileReadMove(storageFileReadNew(storagePathNP(this, fileExp), param.ignoreMissing), MEM_CONTEXT_OLD());
|
||||
}
|
||||
MEM_CONTEXT_TEMP_END();
|
||||
|
||||
@ -575,9 +572,9 @@ storagePut(StorageFileWrite *file, const Buffer *buffer)
|
||||
FUNCTION_DEBUG_ASSERT(file != NULL);
|
||||
FUNCTION_DEBUG_END();
|
||||
|
||||
storageFileWriteOpen(file);
|
||||
storageFileWrite(file, buffer);
|
||||
storageFileWriteClose(file);
|
||||
ioWriteOpen(storageFileWriteIo(file));
|
||||
ioWrite(storageFileWriteIo(file), buffer);
|
||||
ioWriteClose(storageFileWriteIo(file));
|
||||
|
||||
FUNCTION_DEBUG_RESULT_VOID();
|
||||
}
|
||||
|
@ -17,14 +17,6 @@ typedef struct Storage Storage;
|
||||
#include "storage/fileWrite.h"
|
||||
#include "storage/info.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Default buffer size
|
||||
|
||||
Generally buffer size should be pulled out of options but some storage is created without access to options. In those cases we'll
|
||||
assume they are not doing any heavy lifting and have a moderate default.
|
||||
***********************************************************************************************************************************/
|
||||
#define STORAGE_BUFFER_SIZE_DEFAULT (64 * 1024)
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Default file and path modes
|
||||
***********************************************************************************************************************************/
|
||||
@ -43,7 +35,6 @@ typedef struct StorageNewParam
|
||||
{
|
||||
mode_t modeFile;
|
||||
mode_t modePath;
|
||||
size_t bufferSize;
|
||||
bool write;
|
||||
StoragePathExpressionCallback pathExpressionFunction;
|
||||
} StorageNewParam;
|
||||
|
@ -123,11 +123,16 @@ unit:
|
||||
common/lock: full
|
||||
|
||||
# ----------------------------------------------------------------------------------------------------------------------------
|
||||
- name: io-handle
|
||||
total: 1
|
||||
- name: io
|
||||
total: 4
|
||||
|
||||
coverage:
|
||||
common/io/io: full
|
||||
common/io/handle: full
|
||||
common/io/read: full
|
||||
common/io/bufferRead: full
|
||||
common/io/write: full
|
||||
common/io/bufferWrite: full
|
||||
|
||||
# ----------------------------------------------------------------------------------------------------------------------------
|
||||
- name: exit
|
||||
|
@ -254,6 +254,13 @@ Macros to ease the use of common data types
|
||||
#define TEST_RESULT_PTR_NE(statement, resultExpected, ...) \
|
||||
TEST_RESULT_PTR_PARAM(statement, resultExpected, !=, __VA_ARGS__);
|
||||
|
||||
#define TEST_RESULT_SIZE_PARAM(statement, resultExpected, typeOp, ...) \
|
||||
TEST_RESULT(statement, resultExpected, size_t, "%zu", TEST_TYPE_FORMAT, typeOp, TEST_TYPE_COMPARE, __VA_ARGS__);
|
||||
#define TEST_RESULT_SIZE(statement, resultExpected, ...) \
|
||||
TEST_RESULT_SIZE_PARAM(statement, resultExpected, ==, __VA_ARGS__);
|
||||
#define TEST_RESULT_SIZE_NE(statement, resultExpected, ...) \
|
||||
TEST_RESULT_SIZE_PARAM(statement, resultExpected, !=, __VA_ARGS__);
|
||||
|
||||
#define TEST_RESULT_STR_PARAM(statement, resultExpected, typeOp, ...) \
|
||||
TEST_RESULT(statement, resultExpected, char *, "%s", TEST_TYPE_FORMAT_PTR, typeOp, TEST_TYPE_COMPARE_STR, __VA_ARGS__);
|
||||
#define TEST_RESULT_STR(statement, resultExpected, ...) \
|
||||
|
@ -1,29 +0,0 @@
|
||||
/***********************************************************************************************************************************
|
||||
Test Handle IO
|
||||
***********************************************************************************************************************************/
|
||||
#include <fcntl.h>
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Test Run
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
testRun()
|
||||
{
|
||||
FUNCTION_HARNESS_VOID();
|
||||
|
||||
// *****************************************************************************************************************************
|
||||
if (testBegin("ioHandleWriteOneStr()"))
|
||||
{
|
||||
TEST_ERROR(
|
||||
ioHandleWriteOneStr(999999, strNew("test")), FileWriteError,
|
||||
"unable to write to 4 byte(s) to handle: [9] Bad file descriptor");
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
String *fileName = strNewFmt("%s/test.txt", testPath());
|
||||
int fileHandle = open(strPtr(fileName), O_CREAT | O_TRUNC | O_WRONLY, 0700);
|
||||
|
||||
TEST_RESULT_VOID(ioHandleWriteOneStr(fileHandle, strNew("test1\ntest2")), "write string to file");
|
||||
}
|
||||
|
||||
FUNCTION_HARNESS_RESULT_VOID();
|
||||
}
|
184
test/src/module/common/ioTest.c
Normal file
184
test/src/module/common/ioTest.c
Normal file
@ -0,0 +1,184 @@
|
||||
/***********************************************************************************************************************************
|
||||
Test IO
|
||||
***********************************************************************************************************************************/
|
||||
#include <fcntl.h>
|
||||
|
||||
#include "common/assert.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Test functions for IoRead that are not covered by testing the IoBufferRead object
|
||||
***********************************************************************************************************************************/
|
||||
static bool
|
||||
testIoReadOpen(void *driver)
|
||||
{
|
||||
ASSERT(driver == (void *)999);
|
||||
return false;
|
||||
}
|
||||
|
||||
static size_t
|
||||
testIoReadProcess(void *driver, Buffer *buffer)
|
||||
{
|
||||
ASSERT(driver == (void *)999);
|
||||
bufCat(buffer, bufNewStr(strNew("Z")));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static bool testIoReadCloseCalled = false;
|
||||
|
||||
static void
|
||||
testIoReadClose(void *driver)
|
||||
{
|
||||
ASSERT(driver == (void *)999);
|
||||
testIoReadCloseCalled = true;
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Test functions for IoWrite that are not covered by testing the IoBufferWrite object
|
||||
***********************************************************************************************************************************/
|
||||
static bool testIoWriteOpenCalled = false;
|
||||
|
||||
static void
|
||||
testIoWriteOpen(void *driver)
|
||||
{
|
||||
ASSERT(driver == (void *)999);
|
||||
testIoWriteOpenCalled = true;
|
||||
}
|
||||
|
||||
static void
|
||||
testIoWriteProcess(void *driver, const Buffer *buffer)
|
||||
{
|
||||
ASSERT(driver == (void *)999);
|
||||
ASSERT(strEq(strNewBuf(buffer), strNew("ABC")));
|
||||
}
|
||||
|
||||
static bool testIoWriteCloseCalled = false;
|
||||
|
||||
static void
|
||||
testIoWriteClose(void *driver)
|
||||
{
|
||||
ASSERT(driver == (void *)999);
|
||||
testIoWriteCloseCalled = true;
|
||||
}
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
Test Run
|
||||
***********************************************************************************************************************************/
|
||||
void
|
||||
testRun()
|
||||
{
|
||||
FUNCTION_HARNESS_VOID();
|
||||
|
||||
// *****************************************************************************************************************************
|
||||
if (testBegin("ioBufferSize() and ioBufferSizeSet()"))
|
||||
{
|
||||
TEST_RESULT_SIZE(ioBufferSize(), 65536, "check initial buffer size");
|
||||
TEST_RESULT_VOID(ioBufferSizeSet(16384), "set buffer size");
|
||||
TEST_RESULT_SIZE(ioBufferSize(), 16384, "check buffer size");
|
||||
}
|
||||
|
||||
// *****************************************************************************************************************************
|
||||
if (testBegin("IoRead and IoBufferRead"))
|
||||
{
|
||||
IoRead *read = NULL;
|
||||
Buffer *buffer = bufNew(2);
|
||||
|
||||
TEST_ASSIGN(
|
||||
read, ioReadNew((void *)999, testIoReadOpen, testIoReadProcess, testIoReadClose, NULL), "create io read object");
|
||||
|
||||
TEST_RESULT_BOOL(ioReadOpen(read), false, " open io object");
|
||||
TEST_RESULT_SIZE(ioRead(read, buffer), 1, " read 1 byte");
|
||||
TEST_RESULT_BOOL(ioReadEof(read), false, " no eof");
|
||||
TEST_RESULT_VOID(ioReadClose(read), " close io object");
|
||||
TEST_RESULT_BOOL(testIoReadCloseCalled, true, " check io object closed");
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
IoBufferRead *bufferRead = NULL;
|
||||
buffer = bufNew(2);
|
||||
Buffer *bufferOriginal = bufNewStr(strNew("123"));
|
||||
|
||||
MEM_CONTEXT_TEMP_BEGIN()
|
||||
{
|
||||
TEST_ASSIGN(bufferRead, ioBufferReadNew(bufferOriginal), "create buffer read object");
|
||||
TEST_RESULT_VOID(ioBufferReadMove(bufferRead, MEM_CONTEXT_OLD()), " move object to new context");
|
||||
TEST_RESULT_VOID(ioBufferReadMove(NULL, MEM_CONTEXT_OLD()), " move NULL object to new context");
|
||||
}
|
||||
MEM_CONTEXT_TEMP_END();
|
||||
|
||||
TEST_RESULT_BOOL(ioReadEof(ioBufferReadIo(bufferRead)), false, " not eof");
|
||||
TEST_RESULT_SIZE(ioRead(ioBufferReadIo(bufferRead), buffer), 2, " read 2 bytes");
|
||||
TEST_RESULT_BOOL(memcmp(bufPtr(buffer), "12", 2) == 0, true, " memcmp");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(buffer)), "12", " check read");
|
||||
TEST_RESULT_SIZE(ioReadSize(ioBufferReadIo(bufferRead)), 2, " read size is 2");
|
||||
TEST_RESULT_BOOL(ioReadEof(ioBufferReadIo(bufferRead)), false, " not eof");
|
||||
|
||||
TEST_RESULT_VOID(bufUsedZero(buffer), " zero buffer");
|
||||
TEST_RESULT_SIZE(ioRead(ioBufferReadIo(bufferRead), buffer), 1, " read 1 byte");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(buffer)), "3", " check read");
|
||||
TEST_RESULT_BOOL(ioReadEof(ioBufferReadIo(bufferRead)), true, " eof");
|
||||
TEST_RESULT_SIZE(ioRead(ioBufferReadIo(bufferRead), buffer), 0, " read 0 bytes");
|
||||
TEST_RESULT_SIZE(ioReadSize(ioBufferReadIo(bufferRead)), 3, " read size is 3");
|
||||
TEST_RESULT_VOID(ioReadClose(ioBufferReadIo(bufferRead)), " close buffer read object");
|
||||
|
||||
TEST_RESULT_VOID(ioBufferReadFree(bufferRead), " free buffer read object");
|
||||
TEST_RESULT_VOID(ioBufferReadFree(NULL), " free NULL buffer read object");
|
||||
}
|
||||
|
||||
// *****************************************************************************************************************************
|
||||
if (testBegin("IoWrite and IoBufferWrite"))
|
||||
{
|
||||
IoWrite *write = NULL;
|
||||
|
||||
TEST_ASSIGN(
|
||||
write, ioWriteNew((void *)999, testIoWriteOpen, testIoWriteProcess, testIoWriteClose), "create io write object");
|
||||
|
||||
TEST_RESULT_VOID(ioWriteOpen(write), " open io object");
|
||||
TEST_RESULT_BOOL(testIoWriteOpenCalled, true, " check io object open");
|
||||
TEST_RESULT_VOID(ioWrite(write, bufNewStr(strNew("ABC"))), " write 3 bytes");
|
||||
TEST_RESULT_VOID(ioWriteClose(write), " close io object");
|
||||
TEST_RESULT_BOOL(testIoWriteCloseCalled, true, " check io object closed");
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
IoBufferWrite *bufferWrite = NULL;
|
||||
Buffer *buffer = bufNew(0);
|
||||
|
||||
MEM_CONTEXT_TEMP_BEGIN()
|
||||
{
|
||||
TEST_ASSIGN(bufferWrite, ioBufferWriteNew(buffer), "create buffer write object");
|
||||
TEST_RESULT_VOID(ioBufferWriteMove(bufferWrite, MEM_CONTEXT_OLD()), " move object to new context");
|
||||
TEST_RESULT_VOID(ioBufferWriteMove(NULL, MEM_CONTEXT_OLD()), " move NULL object to new context");
|
||||
}
|
||||
MEM_CONTEXT_TEMP_END();
|
||||
|
||||
TEST_RESULT_VOID(ioWriteOpen(ioBufferWriteIo(bufferWrite)), " open buffer write object");
|
||||
TEST_RESULT_VOID(ioWrite(ioBufferWriteIo(bufferWrite), bufNewStr(strNew("ABC"))), " write 3 bytes");
|
||||
TEST_RESULT_VOID(ioWrite(ioBufferWriteIo(bufferWrite), bufNewStr(strNew(""))), " write 0 bytes");
|
||||
TEST_RESULT_VOID(ioWrite(ioBufferWriteIo(bufferWrite), NULL), " write 0 bytes");
|
||||
TEST_RESULT_SIZE(ioWriteSize(ioBufferWriteIo(bufferWrite)), 3, " write size is 3");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(buffer)), "ABC", " check write");
|
||||
|
||||
TEST_RESULT_VOID(ioWrite(ioBufferWriteIo(bufferWrite), bufNewStr(strNew("1234"))), " write 4 bytes");
|
||||
TEST_RESULT_SIZE(ioWriteSize(ioBufferWriteIo(bufferWrite)), 7, " write size is 7");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(buffer)), "ABC1234", " check write");
|
||||
|
||||
TEST_RESULT_VOID(ioWriteClose(ioBufferWriteIo(bufferWrite)), " close buffer write object");
|
||||
|
||||
TEST_RESULT_VOID(ioBufferWriteFree(bufferWrite), " free buffer write object");
|
||||
TEST_RESULT_VOID(ioBufferWriteFree(NULL), " free NULL buffer write object");
|
||||
}
|
||||
|
||||
// *****************************************************************************************************************************
|
||||
if (testBegin("ioHandleWriteOneStr()"))
|
||||
{
|
||||
TEST_ERROR(
|
||||
ioHandleWriteOneStr(999999, strNew("test")), FileWriteError,
|
||||
"unable to write to 4 byte(s) to handle: [9] Bad file descriptor");
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
String *fileName = strNewFmt("%s/test.txt", testPath());
|
||||
int fileHandle = open(strPtr(fileName), O_CREAT | O_TRUNC | O_WRONLY, 0700);
|
||||
|
||||
TEST_RESULT_VOID(ioHandleWriteOneStr(fileHandle, strNew("test1\ntest2")), "write string to file");
|
||||
}
|
||||
|
||||
FUNCTION_HARNESS_RESULT_VOID();
|
||||
}
|
@ -110,12 +110,17 @@ testRun()
|
||||
}
|
||||
|
||||
// *****************************************************************************************************************************
|
||||
if (testBegin("bufCat()"))
|
||||
if (testBegin("bufCat*()"))
|
||||
{
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(bufCat(bufNewStr(strNew("123")), NULL))), "123", "cat null buffer");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(bufCat(bufNewStr(strNew("123")), bufNew(0)))), "123", "cat empty buffer");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(bufCat(bufNewStr(strNew("123")), bufNewStr(strNew("ABC"))))), "123ABC", "cat buffer");
|
||||
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(bufCatSub(bufNewStr(strNew("123")), NULL, 0, 0))), "123", "cat sub null buffer");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(bufCatSub(bufNewStr(strNew("123")), bufNew(0), 0, 0))), "123", "cat sub empty buffer");
|
||||
TEST_RESULT_STR(
|
||||
strPtr(strNewBuf(bufCatSub(bufNewStr(strNew("123")), bufNewStr(strNew("ABC")), 1, 2))), "123BC", "cat sub buffer");
|
||||
|
||||
Buffer *buffer = NULL;
|
||||
TEST_ASSIGN(buffer, bufNew(2), "new buffer with space");
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(bufCat(buffer, bufNewStr(strNew("AB"))))), "AB", "cat buffer with space");
|
||||
|
@ -28,6 +28,7 @@ testRun()
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
Buffer *buffer = bufNew(8);
|
||||
memcpy(bufPtr(buffer), "12345678", 8);
|
||||
bufUsedSet(buffer, 8);
|
||||
|
||||
TEST_RESULT_STR(strPtr(strNewBuf(buffer)), "12345678", "new string from buffer");
|
||||
|
||||
|
@ -1,6 +1,7 @@
|
||||
/***********************************************************************************************************************************
|
||||
Test Configuration Load
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/io/io.h"
|
||||
#include "common/log.h"
|
||||
#include "version.h"
|
||||
|
||||
@ -268,7 +269,17 @@ testRun()
|
||||
|
||||
TEST_RESULT_VOID(cfgLoad(strLstSize(argList), strLstPtr(argList)), "no command");
|
||||
|
||||
// Help command
|
||||
// Help command only
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
argList = strLstNew();
|
||||
strLstAdd(argList, strNew("pgbackrest"));
|
||||
strLstAdd(argList, strNew("help"));
|
||||
|
||||
ioBufferSizeSet(333);
|
||||
TEST_RESULT_VOID(cfgLoad(strLstSize(argList), strLstPtr(argList)), "help command");
|
||||
TEST_RESULT_SIZE(ioBufferSize(), 333, "buffer size not updated by help command");
|
||||
|
||||
// Help command for backup
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
argList = strLstNew();
|
||||
strLstAdd(argList, strNew("pgbackrest"));
|
||||
@ -276,7 +287,8 @@ testRun()
|
||||
strLstAdd(argList, strNew("backup"));
|
||||
strLstAdd(argList, strNew("--repo1-retention-full=2"));
|
||||
|
||||
TEST_RESULT_VOID(cfgLoad(strLstSize(argList), strLstPtr(argList)), "help command");
|
||||
TEST_RESULT_VOID(cfgLoad(strLstSize(argList), strLstPtr(argList)), "help command for backup");
|
||||
TEST_RESULT_SIZE(ioBufferSize(), 4 * 1024 * 1024, "buffer size set to option default");
|
||||
|
||||
// Command takes lock and opens log file
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
|
@ -1,6 +1,7 @@
|
||||
/***********************************************************************************************************************************
|
||||
Test Storage File
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/io/io.h"
|
||||
#include "storage/storage.h"
|
||||
|
||||
/***********************************************************************************************************************************
|
||||
@ -12,7 +13,8 @@ testRun()
|
||||
FUNCTION_HARNESS_VOID();
|
||||
|
||||
// Create default storage object for testing
|
||||
Storage *storageTest = storageNewP(strNew(testPath()), .write = true, .bufferSize = 2);
|
||||
Storage *storageTest = storageNewP(strNew(testPath()), .write = true);
|
||||
ioBufferSizeSet(2);
|
||||
|
||||
// Create a directory and file that cannot be accessed to test permissions errors
|
||||
String *fileNoPerm = strNewFmt("%s/noperm/noperm", testPath());
|
||||
@ -79,7 +81,7 @@ testRun()
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
TEST_ASSIGN(file, storageNewReadNP(storageTest, fileNoPerm), "new no perm read file");
|
||||
TEST_ERROR_FMT(
|
||||
storageFileReadOpen(file), FileOpenError,
|
||||
ioReadOpen(storageFileReadIo(file)), FileOpenError,
|
||||
"unable to open '%s' for read: [13] Permission denied", strPtr(fileNoPerm));
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
@ -87,12 +89,12 @@ testRun()
|
||||
|
||||
TEST_ASSIGN(file, storageNewReadNP(storageTest, fileName), "new missing read file");
|
||||
TEST_ERROR_FMT(
|
||||
storageFileReadOpen(file), FileOpenError,
|
||||
ioReadOpen(storageFileReadIo(file)), FileOpenError,
|
||||
"unable to open '%s' for read: [2] No such file or directory", strPtr(fileName));
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
TEST_ASSIGN(file, storageNewReadP(storageTest, fileName, .ignoreMissing = true), "new missing read file");
|
||||
TEST_RESULT_BOOL(storageFileReadOpen(file), false, " missing file ignored");
|
||||
TEST_RESULT_BOOL(ioReadOpen(storageFileReadIo(file)), false, " missing file ignored");
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
Buffer *outBuffer = bufNew(2);
|
||||
@ -100,16 +102,16 @@ testRun()
|
||||
TEST_RESULT_VOID(storagePutNP(storageNewWriteNP(storageTest, fileName), expectedBuffer), "write test file");
|
||||
|
||||
TEST_ASSIGN(file, storageNewReadNP(storageTest, fileName), "new read file");
|
||||
TEST_RESULT_BOOL(storageFileReadOpen(file), true, " open file");
|
||||
TEST_RESULT_BOOL(ioReadOpen(storageFileReadIo(file)), true, " open file");
|
||||
|
||||
// Close the file handle so operations will fail
|
||||
close(file->fileDriver->handle);
|
||||
|
||||
TEST_ERROR_FMT(
|
||||
storageFileRead(file, outBuffer), FileReadError,
|
||||
ioRead(storageFileReadIo(file), outBuffer), FileReadError,
|
||||
"unable to read '%s': [9] Bad file descriptor", strPtr(fileName));
|
||||
TEST_ERROR_FMT(
|
||||
storageFileReadClose(file), FileCloseError,
|
||||
ioReadClose(storageFileReadIo(file)), FileCloseError,
|
||||
"unable to close '%s': [9] Bad file descriptor", strPtr(fileName));
|
||||
|
||||
// Set file handle to -1 so the close on free with not fail
|
||||
@ -124,41 +126,41 @@ testRun()
|
||||
}
|
||||
MEM_CONTEXT_TEMP_END();
|
||||
|
||||
TEST_RESULT_BOOL(storageFileReadOpen(file), true, " open file");
|
||||
TEST_RESULT_BOOL(ioReadOpen(storageFileReadIo(file)), true, " open file");
|
||||
TEST_RESULT_STR(strPtr(storageFileReadName(file)), strPtr(fileName), " check file name");
|
||||
TEST_RESULT_INT(storageFileReadSize(file), 0, " check size");
|
||||
TEST_RESULT_INT(ioReadSize(storageFileReadIo(file)), 0, " check size");
|
||||
|
||||
TEST_RESULT_VOID(storageFileRead(file, outBuffer), " load data");
|
||||
TEST_RESULT_VOID(ioRead(storageFileReadIo(file), outBuffer), " load data");
|
||||
bufCat(buffer, outBuffer);
|
||||
bufUsedZero(outBuffer);
|
||||
TEST_RESULT_VOID(storageFileRead(file, outBuffer), " load data");
|
||||
TEST_RESULT_VOID(ioRead(storageFileReadIo(file), outBuffer), " load data");
|
||||
bufCat(buffer, outBuffer);
|
||||
bufUsedZero(outBuffer);
|
||||
TEST_RESULT_VOID(storageFileRead(file, outBuffer), " load data");
|
||||
TEST_RESULT_VOID(ioRead(storageFileReadIo(file), outBuffer), " load data");
|
||||
bufCat(buffer, outBuffer);
|
||||
bufUsedZero(outBuffer);
|
||||
TEST_RESULT_VOID(storageFileRead(file, outBuffer), " load data");
|
||||
TEST_RESULT_VOID(ioRead(storageFileReadIo(file), outBuffer), " load data");
|
||||
bufCat(buffer, outBuffer);
|
||||
bufUsedZero(outBuffer);
|
||||
TEST_RESULT_BOOL(bufEq(buffer, expectedBuffer), false, " check file contents (not all loaded yet)");
|
||||
TEST_RESULT_INT(storageFileReadSize(file), 8, " check size");
|
||||
TEST_RESULT_INT(ioReadSize(storageFileReadIo(file)), 8, " check size");
|
||||
|
||||
TEST_RESULT_VOID(storageFileRead(file, outBuffer), " load data");
|
||||
TEST_RESULT_VOID(ioRead(storageFileReadIo(file), outBuffer), " load data");
|
||||
bufCat(buffer, outBuffer);
|
||||
bufUsedZero(outBuffer);
|
||||
|
||||
TEST_RESULT_VOID(storageFileRead(file, outBuffer), " no data to load");
|
||||
TEST_RESULT_VOID(ioRead(storageFileReadIo(file), outBuffer), " no data to load");
|
||||
TEST_RESULT_INT(bufUsed(outBuffer), 0, " buffer is empty");
|
||||
|
||||
TEST_RESULT_BOOL(bufEq(buffer, expectedBuffer), true, " check file contents (all loaded)");
|
||||
TEST_RESULT_INT(storageFileReadSize(file), 9, " check size");
|
||||
TEST_RESULT_INT(ioReadSize(storageFileReadIo(file)), 9, " check size");
|
||||
|
||||
TEST_RESULT_BOOL(storageFileReadEof(file), true, " eof");
|
||||
TEST_RESULT_BOOL(storageFileReadEof(file), true, " still eof");
|
||||
TEST_RESULT_BOOL(ioReadEof(storageFileReadIo(file)), true, " eof");
|
||||
TEST_RESULT_BOOL(ioReadEof(storageFileReadIo(file)), true, " still eof");
|
||||
|
||||
TEST_RESULT_VOID(storageFileReadClose(file), " close file");
|
||||
TEST_RESULT_VOID(storageFileReadClose(file), " close again");
|
||||
TEST_RESULT_INT(storageFileReadSize(file), 9, " check size");
|
||||
TEST_RESULT_VOID(ioReadClose(storageFileReadIo(file)), " close file");
|
||||
TEST_RESULT_VOID(ioReadClose(storageFileReadIo(file)), " close again");
|
||||
TEST_RESULT_INT(ioReadSize(storageFileReadIo(file)), 9, " check size");
|
||||
|
||||
TEST_RESULT_VOID(storageFileReadFree(file), " free file");
|
||||
TEST_RESULT_VOID(storageFileReadFree(NULL), " free null file");
|
||||
@ -192,7 +194,7 @@ testRun()
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
TEST_ASSIGN(file, storageNewWriteP(storageTest, fileNoPerm, .noAtomic = true), "new write file");
|
||||
TEST_ERROR_FMT(
|
||||
storageFileWriteOpen(file), FileOpenError,
|
||||
ioWriteOpen(storageFileWriteIo(file)), FileOpenError,
|
||||
"unable to open '%s' for write: [13] Permission denied", strPtr(fileNoPerm));
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
@ -200,7 +202,7 @@ testRun()
|
||||
|
||||
TEST_ASSIGN(file, storageNewWriteP(storageTest, fileName, .noCreatePath = true, .noAtomic = true), "new write file");
|
||||
TEST_ERROR_FMT(
|
||||
storageFileWriteOpen(file), FileOpenError,
|
||||
ioWriteOpen(storageFileWriteIo(file)), FileOpenError,
|
||||
"unable to open '%s' for write: [2] No such file or directory", strPtr(fileName));
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
@ -209,24 +211,24 @@ testRun()
|
||||
|
||||
TEST_ASSIGN(file, storageNewWriteNP(storageTest, fileName), "new write file");
|
||||
TEST_RESULT_STR(strPtr(storageFileWriteName(file)), strPtr(fileName), " check file name");
|
||||
TEST_RESULT_VOID(storageFileWriteOpen(file), " open file");
|
||||
TEST_RESULT_VOID(ioWriteOpen(storageFileWriteIo(file)), " open file");
|
||||
|
||||
// Close the file handle so operations will fail
|
||||
close(file->fileDriver->handle);
|
||||
storageRemoveP(storageTest, fileTmp, .errorOnMissing = true);
|
||||
|
||||
TEST_ERROR_FMT(
|
||||
storageFileWrite(file, buffer), FileWriteError,
|
||||
ioWrite(storageFileWriteIo(file), buffer), FileWriteError,
|
||||
"unable to write '%s': [9] Bad file descriptor", strPtr(fileName));
|
||||
TEST_ERROR_FMT(
|
||||
storageFileWriteClose(file), FileSyncError,
|
||||
ioWriteClose(storageFileWriteIo(file)), FileSyncError,
|
||||
"unable to sync '%s': [9] Bad file descriptor", strPtr(fileName));
|
||||
|
||||
// Disable file sync so the close can be reached
|
||||
file->fileDriver->noSyncFile = true;
|
||||
|
||||
TEST_ERROR_FMT(
|
||||
storageFileWriteClose(file), FileCloseError,
|
||||
ioWriteClose(storageFileWriteIo(file)), FileCloseError,
|
||||
"unable to close '%s': [9] Bad file descriptor", strPtr(fileName));
|
||||
|
||||
// Set file handle to -1 so the close on free with not fail
|
||||
@ -235,12 +237,12 @@ testRun()
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
TEST_ASSIGN(file, storageNewWriteNP(storageTest, fileName), "new write file");
|
||||
TEST_RESULT_STR(strPtr(storageFileWriteName(file)), strPtr(fileName), " check file name");
|
||||
TEST_RESULT_VOID(storageFileWriteOpen(file), " open file");
|
||||
TEST_RESULT_VOID(ioWriteOpen(storageFileWriteIo(file)), " open file");
|
||||
|
||||
// Rename the file back to original name from tmp -- this will cause the rename in close to fail
|
||||
TEST_RESULT_INT(rename(strPtr(fileTmp), strPtr(fileName)), 0, " rename tmp file");
|
||||
TEST_ERROR_FMT(
|
||||
storageFileWriteClose(file), FileMoveError,
|
||||
ioWriteClose(storageFileWriteIo(file)), FileMoveError,
|
||||
"unable to move '%s' to '%s': [2] No such file or directory", strPtr(fileTmp), strPtr(fileName));
|
||||
|
||||
// Set file handle to -1 so the close on free with not fail
|
||||
@ -255,11 +257,12 @@ testRun()
|
||||
}
|
||||
MEM_CONTEXT_TEMP_END();
|
||||
|
||||
TEST_RESULT_VOID(storageFileWriteOpen(file), " open file");
|
||||
TEST_RESULT_VOID(storageFileWrite(file, NULL), " write null buffer to file");
|
||||
TEST_RESULT_VOID(storageFileWrite(file, bufNew(0)), " write zero buffer to file");
|
||||
TEST_RESULT_VOID(storageFileWrite(file, buffer), " write to file");
|
||||
TEST_RESULT_VOID(storageFileWriteClose(file), " close file");
|
||||
TEST_RESULT_VOID(ioWriteOpen(storageFileWriteIo(file)), " open file");
|
||||
TEST_RESULT_VOID(ioWrite(storageFileWriteIo(file), NULL), " write null buffer to file");
|
||||
TEST_RESULT_VOID(ioWrite(storageFileWriteIo(file), bufNew(0)), " write zero buffer to file");
|
||||
TEST_RESULT_VOID(ioWrite(storageFileWriteIo(file), buffer), " write to file");
|
||||
TEST_RESULT_VOID(ioWriteClose(storageFileWriteIo(file)), " close file");
|
||||
TEST_RESULT_SIZE(ioWriteSize(storageFileWriteIo(file)), 9, " check size");
|
||||
TEST_RESULT_VOID(storageFileWriteFree(file), " free file");
|
||||
TEST_RESULT_VOID(storageFileWriteFree(NULL), " free null file");
|
||||
TEST_RESULT_VOID(storageFileWritePosixFree(NULL), " free null posix file");
|
||||
@ -281,9 +284,9 @@ testRun()
|
||||
storageTest, fileName, .modePath = 0700, .modeFile = 0600, .noSyncPath = true, .noSyncFile = true,
|
||||
.noAtomic = true),
|
||||
"new write file");
|
||||
TEST_RESULT_VOID(storageFileWriteOpen(file), " open file");
|
||||
TEST_RESULT_VOID(storageFileWrite(file, buffer), " write to file");
|
||||
TEST_RESULT_VOID(storageFileWriteClose(file), " close file");
|
||||
TEST_RESULT_VOID(ioWriteOpen(storageFileWriteIo(file)), " open file");
|
||||
TEST_RESULT_VOID(ioWrite(storageFileWriteIo(file), buffer), " write to file");
|
||||
TEST_RESULT_VOID(ioWriteClose(storageFileWriteIo(file)), " close file");
|
||||
|
||||
expectedBuffer = storageGetNP(storageNewReadNP(storageTest, fileName));
|
||||
TEST_RESULT_BOOL(bufEq(buffer, expectedBuffer), true, " check file contents");
|
||||
|
@ -1,6 +1,7 @@
|
||||
/***********************************************************************************************************************************
|
||||
Test Storage Manager
|
||||
***********************************************************************************************************************************/
|
||||
#include "common/io/io.h"
|
||||
#include "common/time.h"
|
||||
#include "storage/fileRead.h"
|
||||
#include "storage/fileWrite.h"
|
||||
@ -32,8 +33,9 @@ testRun()
|
||||
FUNCTION_HARNESS_VOID();
|
||||
|
||||
// Create default storage object for testing
|
||||
Storage *storageTest = storageNewP(strNew(testPath()), .write = true, .bufferSize = 3);
|
||||
Storage *storageTest = storageNewP(strNew(testPath()), .write = true);
|
||||
Storage *storageTmp = storageNewP(strNew("/tmp"), .write = true);
|
||||
ioBufferSizeSet(2);
|
||||
|
||||
// Create a directory and file that cannot be accessed to test permissions errors
|
||||
String *fileNoPerm = strNewFmt("%s/noperm/noperm", testPath());
|
||||
@ -56,20 +58,18 @@ testRun()
|
||||
TEST_RESULT_STR(strPtr(storageTest->path), "/", " check path");
|
||||
TEST_RESULT_INT(storageTest->modeFile, 0640, " check file mode");
|
||||
TEST_RESULT_INT(storageTest->modePath, 0750, " check path mode");
|
||||
TEST_RESULT_INT(storageTest->bufferSize, 65536, " check buffer size");
|
||||
TEST_RESULT_BOOL(storageTest->write, false, " check write");
|
||||
TEST_RESULT_BOOL(storageTest->pathExpressionFunction == NULL, true, " check expression function is not set");
|
||||
|
||||
TEST_ASSIGN(
|
||||
storageTest,
|
||||
storageNewP(
|
||||
strNew("/path/to"), .modeFile = 0600, .modePath = 0700, .bufferSize = 8192, .write = true,
|
||||
strNew("/path/to"), .modeFile = 0600, .modePath = 0700, .write = true,
|
||||
.pathExpressionFunction = storageTestPathExpression),
|
||||
"new storage (non-default)");
|
||||
TEST_RESULT_STR(strPtr(storageTest->path), "/path/to", " check path");
|
||||
TEST_RESULT_INT(storageTest->modeFile, 0600, " check file mode");
|
||||
TEST_RESULT_INT(storageTest->modePath, 0700, " check path mode");
|
||||
TEST_RESULT_INT(storageTest->bufferSize, 8192, " check buffer size");
|
||||
TEST_RESULT_BOOL(storageTest->write, true, " check write");
|
||||
TEST_RESULT_BOOL(storageTest->pathExpressionFunction != NULL, true, " check expression function is set");
|
||||
|
||||
@ -475,14 +475,14 @@ testRun()
|
||||
|
||||
TEST_ASSIGN(file, storageNewReadNP(storageTest, fileName), "new read file (defaults)");
|
||||
TEST_ERROR_FMT(
|
||||
storageFileReadOpen(file), FileOpenError,
|
||||
ioReadOpen(storageFileReadIo(file)), FileOpenError,
|
||||
"unable to open '%s' for read: [2] No such file or directory", strPtr(fileName));
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
TEST_RESULT_INT(system(strPtr(strNewFmt("touch %s", strPtr(fileName)))), 0, "create read file");
|
||||
|
||||
TEST_RESULT_BOOL(storageFileReadOpen(file), true, " open file");
|
||||
TEST_RESULT_VOID(storageFileReadClose(file), " close file");
|
||||
TEST_RESULT_BOOL(ioReadOpen(storageFileReadIo(file)), true, " open file");
|
||||
TEST_RESULT_VOID(ioReadClose(storageFileReadIo(file)), " close file");
|
||||
}
|
||||
|
||||
// *****************************************************************************************************************************
|
||||
@ -492,15 +492,15 @@ testRun()
|
||||
|
||||
TEST_ASSIGN(file, storageNewWriteP(storageTest, fileNoPerm, .noAtomic = true), "new write file (defaults)");
|
||||
TEST_ERROR_FMT(
|
||||
storageFileWriteOpen(file), FileOpenError,
|
||||
ioWriteOpen(storageFileWriteIo(file)), FileOpenError,
|
||||
"unable to open '%s' for write: [13] Permission denied", strPtr(fileNoPerm));
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
String *fileName = strNewFmt("%s/sub1/testfile", testPath());
|
||||
|
||||
TEST_ASSIGN(file, storageNewWriteNP(storageTest, fileName), "new write file (defaults)");
|
||||
TEST_RESULT_VOID(storageFileWriteOpen(file), " open file");
|
||||
TEST_RESULT_VOID(storageFileWriteClose(file), " close file");
|
||||
TEST_RESULT_VOID(ioWriteOpen(storageFileWriteIo(file)), " open file");
|
||||
TEST_RESULT_VOID(ioWriteClose(storageFileWriteIo(file)), " close file");
|
||||
TEST_RESULT_INT(storageInfoNP(storageTest, strPath(fileName)).mode, 0750, " check path mode");
|
||||
TEST_RESULT_INT(storageInfoNP(storageTest, fileName).mode, 0640, " check file mode");
|
||||
|
||||
@ -509,8 +509,8 @@ testRun()
|
||||
|
||||
TEST_ASSIGN(
|
||||
file, storageNewWriteP(storageTest, fileName, .modePath = 0700, .modeFile = 0600), "new write file (set mode)");
|
||||
TEST_RESULT_VOID(storageFileWriteOpen(file), " open file");
|
||||
TEST_RESULT_VOID(storageFileWriteClose(file), " close file");
|
||||
TEST_RESULT_VOID(ioWriteOpen(storageFileWriteIo(file)), " open file");
|
||||
TEST_RESULT_VOID(ioWriteClose(storageFileWriteIo(file)), " close file");
|
||||
TEST_RESULT_INT(storageInfoNP(storageTest, strPath(fileName)).mode, 0700, " check path mode");
|
||||
TEST_RESULT_INT(storageInfoNP(storageTest, fileName).mode, 0600, " check file mode");
|
||||
}
|
||||
@ -560,8 +560,7 @@ testRun()
|
||||
"unable to read 64 byte(s) from '%s/test.txt'", testPath());
|
||||
|
||||
// -------------------------------------------------------------------------------------------------------------------------
|
||||
const Storage *storage = storageTest;
|
||||
((Storage *)storage)->bufferSize = 2;
|
||||
ioBufferSizeSet(2);
|
||||
|
||||
TEST_ASSIGN(buffer, storageGetNP(storageNewReadNP(storageTest, strNewFmt("%s/test.txt", testPath()))), "get text");
|
||||
TEST_RESULT_INT(bufSize(buffer), 9, "check size");
|
||||
|
Loading…
x
Reference in New Issue
Block a user