summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorWaLyong Cho <walyong.cho@samsung.com>2016-12-14 11:12:56 (GMT)
committerWaLyong Cho <walyong.cho@samsung.com>2016-12-14 11:12:56 (GMT)
commitf2bbea8b404d188528cbfcef0b40e7b7d9017f58 (patch)
tree6414f82b8dc6ea9b3ff95cc90db7903b8358174e
parent26e7c65878e00c2c99d2bd6700780ce2a75450d8 (diff)
parent5c270d17bd9ccd98cad2f5a84c0d1932d3f067f1 (diff)
downloadlibsystem-f2bbea8b404d188528cbfcef0b40e7b7d9017f58.zip
libsystem-f2bbea8b404d188528cbfcef0b40e7b7d9017f58.tar.gz
libsystem-f2bbea8b404d188528cbfcef0b40e7b7d9017f58.tar.bz2
release: 4.1-0
[Model] Common [BinType] AP [Customer] N/A [Issue] N/A [Request] N/A [Occurrence Version] N/A [Problem] release: 4.1-0 [Cause & Measure] N/A [Checking Method] N/A [Team] SystemFW [Developer] WaLyong Cho [Solution company] Samsung [Change Type] N/A * devel/systemfw/master: release: 4.1-0 configure.ac: add needed build prog and headers libsystem: glib-utils: extend glist iterate macro function libsystem: add general numeric type read/write api. libsystem: add macro function for num read/write adjust line break and white spaces configure.ac: remove duplicate space in build flags untabify: replace tab to space libsystem: add 64 bit signed/unsigned read-write api Change-Id: Ia36e4a330b8d5cab3111f8d7500cb2be959f2882 Signed-off-by: WaLyong Cho <walyong.cho@samsung.com>
-rw-r--r--Doxyfile2
-rw-r--r--configure.ac18
-rw-r--r--packaging/libsystem.spec4
-rw-r--r--src/Makefile.am22
-rw-r--r--src/libsystem/config-parser.c10
-rw-r--r--src/libsystem/glib-util.h45
-rw-r--r--src/libsystem/libsystem.c424
-rw-r--r--src/libsystem/libsystem.h368
-rw-r--r--src/libsystem/proc.c18
-rw-r--r--src/test/test-foreach-glist.c138
-rw-r--r--src/test/test-read-write.c110
11 files changed, 1007 insertions, 152 deletions
diff --git a/Doxyfile b/Doxyfile
index 2f5e01e..42fbd54 100644
--- a/Doxyfile
+++ b/Doxyfile
@@ -38,7 +38,7 @@ PROJECT_NAME = libsystem
# could be handy for archiving the generated documentation or if some version
# control system is used.
-PROJECT_NUMBER = 4.0
+PROJECT_NUMBER = 4.1
# Using the PROJECT_BRIEF tag one can provide an optional one line description
# for a project that appears at the top of each page and should give viewer a
diff --git a/configure.ac b/configure.ac
index df18d8e..d0e5c51 100644
--- a/configure.ac
+++ b/configure.ac
@@ -2,7 +2,7 @@
# Process this file with autoconf to produce a configure script.
AC_PREREQ([2.68])
-AC_INIT([libsystem], [4.0], [walyong.cho@samsung.com])
+AC_INIT([libsystem], [4.1], [walyong.cho@samsung.com])
dnl AC_CONFIG_MACRO_DIRS([m4])
AC_CONFIG_MACRO_DIR([m4])
@@ -17,17 +17,21 @@ LT_PREREQ(2.2)
LT_INIT([disable-static])
# Checks for programs.
-AC_PROG_CC
AC_PROG_CXX
+AC_PROG_AWK
+AC_PROG_CC
+AC_PROG_CPP
AC_PROG_INSTALL
+AC_PROG_LN_S
AC_PROG_MAKE_SET
+AC_PROG_RANLIB
# Checks for libraries.
# FIXME: Replace `main' with a function in `-lrt':
AC_CHECK_LIB([rt], [main])
# Checks for header files.
-AC_CHECK_HEADERS([fcntl.h limits.h mntent.h stddef.h stdint.h stdlib.h string.h sys/time.h unistd.h])
+AC_CHECK_HEADERS([fcntl.h inttypes.h limits.h mntent.h stddef.h stdint.h stdlib.h string.h sys/time.h unistd.h])
# Checks for typedefs, structures, and compiler characteristics.
AC_CHECK_HEADER_STDBOOL
@@ -68,6 +72,9 @@ our_ldflags=" \
-Wl,-z,now \
-pie"
+our_cflags=$(echo $our_cflags |sed 's/\t/ /g' | sed 's/ / /g')
+our_ldflags=$(echo $our_ldflags | sed 's/\t/ /g' | sed 's/ / /g')
+
AC_SUBST([OUR_CFLAGS], "$our_cflags")
AC_SUBST([OUR_LDFLAGS], "$our_ldflags")
@@ -111,5 +118,8 @@ AC_MSG_RESULT([
lib dir: ${libdir}
rootlib dir: ${with_rootlibdir}
- OUR CFLAGS: ${OUR_CFLAGS} ${CFLAGS}
+ OUR CFLAGS: ${OUR_CFLAGS}
+ CFLAGS: ${CFLAGS}
+ OUR LDFLAGS: ${OUR_LDFLAGS}
+ LDFLAGS: ${LDFLAGS}
])
diff --git a/packaging/libsystem.spec b/packaging/libsystem.spec
index e2a32d4..073ebb7 100644
--- a/packaging/libsystem.spec
+++ b/packaging/libsystem.spec
@@ -1,7 +1,7 @@
Name: libsystem
Summary: System Libraries
-Version: 4.0
-Release: 4%{?release_flags}
+Version: 4.1
+Release: 0%{?release_flags}
License: Apache-2.0
Group: System/Libraries
Source: %{name}-%{version}.tar.gz
diff --git a/src/Makefile.am b/src/Makefile.am
index 48ad051..0b63ea5 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -113,6 +113,28 @@ test_cp_LDADD = \
tests += test-cp
# ------------------------------------------------------------------------------
+test_read_write_SOURCES = \
+ test/test-read-write.c
+
+test_read_write_LDADD = \
+ libsystem.la
+
+tests += test-read-write
+
+# ------------------------------------------------------------------------------
+test_foreach_glist_SOURCES = \
+ test/test-foreach-glist.c
+
+test_foreach_glist_CFLAGS = \
+ $(GIO_CFLAGS)
+
+test_foreach_glist_LDADD = \
+ $(GIO_LIBS) \
+ libsystem.la
+
+tests += test-foreach-glist
+
+# ------------------------------------------------------------------------------
pkgconfiglib_DATA += \
libsystem-sd/libsystem-sd.pc
diff --git a/src/libsystem/config-parser.c b/src/libsystem/config-parser.c
index e6ade0e..2799f0a 100644
--- a/src/libsystem/config-parser.c
+++ b/src/libsystem/config-parser.c
@@ -103,9 +103,7 @@ static int config_parse_table(
return 0;
}
-int config_parse(
- const char *filename,
- void *table) {
+int config_parse(const char *filename, void *table) {
_cleanup_fclose_ FILE *f = NULL;
char *sections[MAX_SECTION] = { 0 };
@@ -140,12 +138,12 @@ int config_parse(
if (*l == '[') {
len = strlen(l);
- if (l[len-1] != ']') {
+ if (l[len - 1] != ']') {
r = -EBADMSG;
goto finish;
}
- n = strndup(l+1, len-2);
+ n = strndup(l + 1, len - 2);
if (!n) {
r = -ENOMEM;
goto finish;
@@ -203,7 +201,7 @@ int config_parse(
r = 0;
finish:
- for (i=0; i<num_section; i++)
+ for (i = 0; i < num_section; i++)
if (sections[i])
free(sections[i]);
diff --git a/src/libsystem/glib-util.h b/src/libsystem/glib-util.h
index 7d3c7ad..560acc4 100644
--- a/src/libsystem/glib-util.h
+++ b/src/libsystem/glib-util.h
@@ -30,9 +30,6 @@
#pragma once
#include <glib.h>
-#include <gio/gio.h>
-
-#include "libsystem.h"
#ifdef __cplusplus
extern "C" {
@@ -41,11 +38,47 @@ extern "C" {
/**
* @brief Iterate for each list nodes.
*
- * @param n each list nodes
+ * @param c current node
+ * @param l list to iterate
+ */
+#define FOREACH_G_LIST(c, l) \
+ for (c = g_list_first(l); c; c = g_list_next(c))
+
+/**
+ * @brief Reverse iterate for each list nodes.
+ *
+ * @param c current node
+ * @param l list to iterate
+ */
+#define FOREACH_G_LIST_REVERSE(c, l) \
+ for (c = g_list_last(l); c; c = g_list_previous(c))
+
+/**
+ * @brief Iterate for each list nodes. #FOREACH_G_LIST_SAFE is similar
+ * with #FOREACH_G_LIST but safe for list remove. When you are
+ * iterating a list to remove some of list nodes, you have to use
+ * #FOREACH_G_LIST_SAFE for safe iteration.
+ *
+ * @param c current node
+ * @param n next node of current iteration, this is used for safe iteration
+ * @param l list to iterate
+ */
+#define FOREACH_G_LIST_SAFE(c, n, l) \
+ for (c = g_list_first(l), n = g_list_next(c); c; c = n, n = g_list_next(c))
+
+/**
+ * @brief Reverse iterate for each list
+ * nodes. #FOREACH_G_LIST_SAFE_REVERSE is similar with
+ * #FOREACH_G_LIST_REVERSE but safe for list remove. When you are
+ * iterating a list to remove some of list nodes, you have to use
+ * #FOREACH_G_LIST_SAFE_REVERSE for safe iteration.
+ *
+ * @param c current node
+ * @param p previous node of current iteration, this is used for safe iteration
* @param l list to iterate
*/
-#define FOREACH_G_LIST(n, l) \
- for (n = g_list_first(l); n; n = g_list_next(n))
+#define FOREACH_G_LIST_SAFE_REVERSE(c, p, l) \
+ for (c = g_list_last(l), p = g_list_previous(c); c; c = p, p = g_list_previous(c))
/**
* @brief Convert GError to errno.
diff --git a/src/libsystem/libsystem.c b/src/libsystem/libsystem.c
index 2a8aced..c8b7c58 100644
--- a/src/libsystem/libsystem.c
+++ b/src/libsystem/libsystem.c
@@ -28,17 +28,19 @@
#include <sys/stat.h>
#include <fcntl.h>
#include <mntent.h>
+#include <stdint.h>
+#include <inttypes.h>
#include "libsystem.h"
static int _errno_old;
-#define STORE_RESET_ERRNO do { \
+#define STORE_RESET_ERRNO do { \
_errno_old = errno; \
errno = 0; \
} while (0)
-#define RESTORE_ERRNO do { \
+#define RESTORE_ERRNO do { \
errno = _errno_old; \
_errno_old = 0; \
} while (0)
@@ -81,16 +83,16 @@ char *strnappend(const char *s, const char *suffix, size_t b) {
assert(suffix);
a = strlen(s);
- if (b > ((size_t) -1) - a)
+ if (b > ((size_t) - 1) - a)
return NULL;
- r = new(char, a+b+1);
+ r = new(char, a + b + 1);
if (!r)
return NULL;
memcpy(r, s, a);
- memcpy(r+a, suffix, b);
- r[a+b] = 0;
+ memcpy(r + a, suffix, b);
+ r[a + b] = 0;
return r;
}
@@ -107,7 +109,7 @@ char *strstrip(char *s) {
s += strspn(s, WHITESPACE);
- for (e = strchr(s, 0); e > s; e --)
+ for (e = strchr(s, 0); e > s; e--)
if (!strchr(WHITESPACE, e[-1]))
break;
@@ -166,7 +168,7 @@ int strndup_strip(const char *str, size_t len, char **ret) {
return 0;
}
-bool nulstr_contains(const char*nulstr, const char *needle) {
+bool nulstr_contains(const char *nulstr, const char *needle) {
const char *i;
if (!nulstr)
@@ -221,7 +223,7 @@ char *path_kill_slashes(char *path) {
return path;
}
-char* endswith(const char *s, const char *postfix) {
+char *endswith(const char *s, const char *postfix) {
size_t sl, pl;
assert(s);
@@ -231,7 +233,7 @@ char* endswith(const char *s, const char *postfix) {
pl = strlen(postfix);
if (pl == 0)
- return (char*) s + sl;
+ return (char *) s + sl;
if (sl < pl)
return NULL;
@@ -239,7 +241,7 @@ char* endswith(const char *s, const char *postfix) {
if (memcmp(s + sl - pl, postfix, pl) != 0)
return NULL;
- return (char*) s + sl - pl;
+ return (char *) s + sl - pl;
}
int parse_boolean(const char *v) {
@@ -265,7 +267,7 @@ int parse_bytes(const char *b, size_t *s) {
return 0;
num_l = strspn(b, "0123456789");
- if (num_l < len-1)
+ if (num_l < len - 1)
return -EINVAL;
unit_l = strcspn(b, "BKMG");
@@ -306,11 +308,11 @@ int parse_percent(const char *string, size_t *percent) {
if (!len)
return 0;
- if (string[len-1] != '%')
+ if (string[len - 1] != '%')
return -EINVAL;
num_len = strspn(string, "0123456789");
- if (num_len < len-1)
+ if (num_len < len - 1)
return -EINVAL;
num = strndup(string, num_len);
@@ -376,7 +378,7 @@ char *split(const char *c, size_t *l, const char *separator, char **state) {
assert(separator);
assert(state);
- current = *state ? *state : (char*) c;
+ current = *state ? *state : (char *) c;
if (!*current || *c == 0)
return NULL;
@@ -384,7 +386,7 @@ char *split(const char *c, size_t *l, const char *separator, char **state) {
separator_include_quotes = !!strspn(separator, QUOTES);
current += strspn(current, separator);
- while((s = strcspn(current + *l, separator))) {
+ while ((s = strcspn(current + *l, separator))) {
*l += s;
if (separator_include_quotes ||
quote_complete(current, *l))
@@ -394,7 +396,7 @@ char *split(const char *c, size_t *l, const char *separator, char **state) {
*state = current + *l;
- return (char *)current;
+ return (char *) current;
}
bool is_number(const char *s, int l) {
@@ -543,9 +545,8 @@ char *strdup_unquote(const char *str, const char *quotes) {
if (l < 2)
return strdup(str);
- if (strchr(quotes, str[0]) &&
- str[0] == str[l-1])
- return strndup(str+1, l-2);
+ if (strchr(quotes, str[0]) && str[0] == str[l - 1])
+ return strndup(str + 1, l - 2);
return strdup(str);
}
@@ -559,8 +560,7 @@ int write_str_to_file(FILE *f, const char *str, enum file_write_flags flags) {
STORE_RESET_ERRNO;
(void) fputs(str, f);
- if ((flags & FILE_WRITE_NEWLINE_IF_NOT) &&
- !endswith(str, "\n"))
+ if ((flags & FILE_WRITE_NEWLINE_IF_NOT) && !endswith(str, "\n"))
(void) fputc('\n', f);
if (flags & FILE_WRITE_WITH_FFLUSH)
@@ -590,183 +590,365 @@ int write_str_to_path(const char *path, const char *str, enum file_write_flags f
return write_str_to_file(f, str, flags);
}
-int write_int32_to_file(FILE *f, int32_t i, enum file_write_flags flags) {
- int r = 0;
+int read_one_line_from_file(FILE *f, char **line) {
+ char t[LINE_MAX], *c;
assert(f);
+ assert(line);
STORE_RESET_ERRNO;
- (void) fprintf(f, "%d", i);
- if (flags & FILE_WRITE_NEWLINE_IF_NOT)
- (void) fputc('\n', f);
+ if (!fgets(t, sizeof(t), f)) {
- if (flags & FILE_WRITE_WITH_FFLUSH)
- (void) fflush(f);
+ if (ferror(f)) {
+ int r;
- if (ferror(f))
- r = errno ? -errno : -EIO;
+ r = errno ? -errno : -EIO;
+ RESTORE_ERRNO;
+ return r;
+ }
+
+ t[0] = 0;
+ }
RESTORE_ERRNO;
- return r;
+ c = strdup(t);
+ if (!c)
+ return -ENOMEM;
+
+ *line = truncate_nl(c);
+
+ return 0;
}
-int write_int32_to_path(const char *path, int32_t i, enum file_write_flags flags) {
+int read_one_line_from_path(const char *path, char **line) {
_cleanup_fclose_ FILE *f = NULL;
assert(path);
+ assert(line);
- if (flags & FILE_WRITE_APPEND)
- f = fopen(path, "ae");
- else
- f = fopen(path, "we");
+ f = fopen(path, "re");
if (!f)
return -errno;
- return write_int32_to_file(f, i, flags);
+ return read_one_line_from_file(f, line);
}
-int write_uint32_to_file(FILE *f, uint32_t u, enum file_write_flags flags) {
- int r = 0;
+#define DEFINE_WRITE_NUM_TO_FILE(type, format) \
+ int write_##type##_to_file(FILE *f, \
+ type##_t u, \
+ enum file_write_flags flags) { \
+ int r = 0; \
+ \
+ assert(f); \
+ \
+ STORE_RESET_ERRNO; \
+ \
+ (void) fprintf(f, format, u); \
+ if (flags & FILE_WRITE_NEWLINE_IF_NOT) \
+ (void) fputc('\n', f); \
+ \
+ if (flags & FILE_WRITE_WITH_FFLUSH) \
+ (void) fflush(f); \
+ \
+ if (ferror(f)) \
+ r = errno ? -errno : -EIO; \
+ \
+ RESTORE_ERRNO; \
+ \
+ return r; \
+ }
- assert(f);
+#define DEFINE_WRITE_NUM_TO_PATH(type) \
+ int write_##type##_to_path(const char *path, \
+ type##_t u, \
+ enum file_write_flags flags) { \
+ _cleanup_fclose_ FILE *f = NULL; \
+ \
+ assert(path); \
+ \
+ if (flags & FILE_WRITE_APPEND) \
+ f = fopen(path, "ae"); \
+ else \
+ f = fopen(path, "we"); \
+ if (!f) \
+ return -errno; \
+ \
+ return write_##type##_to_file(f, u, flags); \
+ }
- STORE_RESET_ERRNO;
+#define DEFINE_WRITE_NUM_DUAL(type, format) \
+ DEFINE_WRITE_NUM_TO_FILE(type, format); \
+ DEFINE_WRITE_NUM_TO_PATH(type)
+
+#define DEFINE_READ_NUM_FROM_FILE(type, format) \
+ int read_##type##_from_file(FILE *f, type##_t *num) { \
+ int r = 0; \
+ \
+ assert(f); \
+ assert(num); \
+ \
+ STORE_RESET_ERRNO; \
+ \
+ r = fscanf(f, format, num); \
+ if (r == EOF && ferror(f)) \
+ r = errno ? -errno : -EOF; \
+ \
+ RESTORE_ERRNO; \
+ \
+ return r; \
+ }
- (void) fprintf(f, "%u", u);
- if (flags & FILE_WRITE_NEWLINE_IF_NOT)
- (void) fputc('\n', f);
+#define DEFINE_READ_NUM_FROM_PATH(type) \
+ int read_##type##_from_path(const char *path, type##_t *num) { \
+ _cleanup_fclose_ FILE *f = NULL; \
+ \
+ assert(path); \
+ assert(num); \
+ \
+ f = fopen(path, "re"); \
+ if (!f) \
+ return -errno; \
+ \
+ return read_##type##_from_file(f, num); \
+ }
- if (flags & FILE_WRITE_WITH_FFLUSH)
- (void) fflush(f);
+#define DEFINE_READ_NUM_DUAL(type, format) \
+ DEFINE_READ_NUM_FROM_FILE(type, format); \
+ DEFINE_READ_NUM_FROM_PATH(type)
- if (ferror(f))
- r = errno ? -errno : -EIO;
+#define DEFINE_READ_WRITE_NUM_DUAL(type, r_format, w_format) \
+ DEFINE_READ_NUM_DUAL(type, r_format); \
+ DEFINE_WRITE_NUM_DUAL(type, w_format)
- RESTORE_ERRNO;
+DEFINE_READ_WRITE_NUM_DUAL(int32, "%d", "%d");
+DEFINE_READ_WRITE_NUM_DUAL(uint32, "%u", "%u");
+DEFINE_READ_WRITE_NUM_DUAL(int64, "%" SCNd64, "%" PRId64);
+DEFINE_READ_WRITE_NUM_DUAL(uint64, "%" SCNu64, "%" PRIu64);
- return r;
+int write_int_to_file(FILE *f, int num, enum file_write_flags flags) {
+
+ assert(f);
+ assert(num);
+
+ return write_int32_to_file(f, (int32_t) num, flags);
}
-int write_uint32_to_path(const char *path, uint32_t u, enum file_write_flags flags) {
- _cleanup_fclose_ FILE *f = NULL;
+int write_int_to_path(const char *path, int num, enum file_write_flags flags) {
assert(path);
+ assert(num);
- if (flags & FILE_WRITE_APPEND)
- f = fopen(path, "ae");
- else
- f = fopen(path, "we");
- if (!f)
- return -errno;
+ return write_int32_to_path(path, (int32_t) num, flags);
+}
- return write_uint32_to_file(f, u, flags);
+int write_unsigned_int_to_file(FILE *f, unsigned int num, enum file_write_flags flags) {
+
+ assert(f);
+ assert(num);
+
+ return write_uint32_to_file(f, (uint32_t) num, flags);
}
-int read_one_line_from_file(FILE *f, char **line) {
- char t[LINE_MAX], *c;
+int write_unsigned_int_to_path(const char *path, unsigned int num, enum file_write_flags flags) {
+
+ assert(path);
+ assert(num);
+
+ return write_uint32_to_path(path, (uint32_t) num, flags);
+}
+
+int write_long_int_to_file(FILE *f, long int num, enum file_write_flags flags) {
assert(f);
- assert(line);
+ assert(num);
- STORE_RESET_ERRNO;
+#if __WORDSIZE == 64
+ return write_int64_to_file(f, (int64_t) num, flags);
+#else
+ return write_int32_to_file(f, (int32_t) num, flags);
+#endif
+}
- if (!fgets(t, sizeof(t), f)) {
+int write_long_int_to_path(const char *path, long int num, enum file_write_flags flags) {
- if (ferror(f)) {
- int r;
+ assert(path);
+ assert(num);
- r = errno ? -errno : -EIO;
- RESTORE_ERRNO;
- return r;
- }
+#if __WORDSIZE == 64
+ return write_int64_to_path(path, (int64_t) num, flags);
+#else
+ return write_int32_to_path(path, (int32_t) num, flags);
+#endif
+}
- t[0] = 0;
- }
+int write_unsigned_long_int_to_file(FILE *f, unsigned long int num, enum file_write_flags flags) {
- RESTORE_ERRNO;
+ assert(f);
+ assert(num);
- c = strdup(t);
- if (!c)
- return -ENOMEM;
+#if __WORDSIZE == 64
+ return write_uint64_to_file(f, (uint64_t) num, flags);
+#else
+ return write_uint32_to_file(f, (uint32_t) num, flags);
+#endif
+}
- *line = truncate_nl(c);
+int write_unsigned_long_int_to_path(const char *path, unsigned long int num, enum file_write_flags flags) {
- return 0;
+ assert(path);
+ assert(num);
+
+#if __WORDSIZE == 64
+ return write_uint64_to_path(path, (uint64_t) num, flags);
+#else
+ return write_uint32_to_path(path, (uint32_t) num, flags);
+#endif
}
-int read_one_line_from_path(const char *path, char **line) {
- _cleanup_fclose_ FILE *f = NULL;
+int write_long_long_int_to_file(FILE *f, long long int num, enum file_write_flags flags) {
+
+ assert(f);
+ assert(num);
+
+ return write_int64_to_file(f, (int64_t) num, flags);
+}
+
+int write_long_long_int_to_path(const char *path, long long int num, enum file_write_flags flags) {
assert(path);
- assert(line);
+ assert(num);
- f = fopen(path, "re");
- if (!f)
- return -errno;
+ return write_int64_to_path(path, (int64_t) num, flags);
+}
- return read_one_line_from_file(f, line);
+int write_unsigned_long_long_int_to_file(FILE *f, unsigned long long int num, enum file_write_flags flags) {
+
+ assert(f);
+ assert(num);
+
+ return write_uint64_to_file(f, (uint64_t) num, flags);
}
-int read_int32_from_file(FILE *f, int32_t *i) {
- int r = 0;
+int write_unsigned_long_long_int_to_path(const char *path, unsigned long long int num, enum file_write_flags flags) {
+
+ assert(path);
+ assert(num);
+
+ return write_uint64_to_path(path, (uint64_t) num, flags);
+}
+
+int read_int_from_file(FILE *f, int *num) {
assert(f);
- assert(i);
+ assert(num);
- STORE_RESET_ERRNO;
+ return read_int32_from_file(f, (int32_t *) num);
+}
- r = fscanf(f, "%d", i);
- if (r == EOF && ferror(f))
- r = errno ? -errno : -EOF;
+int read_int_from_path(const char *path, int *num) {
- RESTORE_ERRNO;
+ assert(path);
+ assert(num);
- return r;
+ return read_int32_from_path(path, (int32_t *) num);
}
-int read_int32_from_path(const char *path, int32_t *i) {
- _cleanup_fclose_ FILE *f = NULL;
+int read_unsigned_int_from_file(FILE *f, unsigned int *num) {
+
+ assert(f);
+ assert(num);
+
+ return read_uint32_from_file(f, (uint32_t *) num);
+}
+
+int read_unsigned_int_from_path(const char *path, unsigned int *num) {
assert(path);
- assert(i);
+ assert(num);
- f = fopen(path, "re");
- if (!f)
- return -errno;
+ return read_uint32_from_path(path, (uint32_t *) num);
+}
+
+int read_long_int_from_file(FILE *f, long int *num) {
+
+ assert(f);
+ assert(num);
- return read_int32_from_file(f, i);
+#if __WORDSIZE == 64
+ return read_int64_from_file(f, (int64_t *) num);
+#else
+ return read_int32_from_file(f, (int32_t *) num);
+#endif
}
-int read_uint32_from_file(FILE *f, uint32_t *u) {
- int r = 0;
+int read_long_int_from_path(const char *path, long int *num) {
+
+ assert(path);
+ assert(num);
+
+#if __WORDSIZE == 64
+ return read_int64_from_path(path, (int64_t *) num);
+#else
+ return read_int32_from_path(path, (int32_t *) num);
+#endif
+}
+
+int read_unsigned_long_int_from_file(FILE *f, unsigned long int *num) {
assert(f);
- assert(u);
+ assert(num);
- STORE_RESET_ERRNO;
+#if __WORDSIZE == 64
+ return read_uint64_from_file(f, (uint64_t *) num);
+#else
+ return read_uint32_from_file(f, (uint32_t *) num);
+#endif
+}
- r = fscanf(f, "%u", u);
- if (r == EOF && ferror(f))
- r = errno ? -errno : -EOF;
+int read_unsigned_long_int_from_path(const char *path, unsigned long int *num) {
- RESTORE_ERRNO;
+ assert(path);
+ assert(num);
- return r;
+#if __WORDSIZE == 64
+ return read_uint64_from_path(path, (uint64_t *) num);
+#else
+ return read_uint32_from_path(path, (uint32_t *) num);
+#endif
}
-int read_uint32_from_path(const char *path, uint32_t *u) {
- _cleanup_fclose_ FILE *f = NULL;
+int read_long_long_int_from_file(FILE *f, long long *num) {
+
+ assert(f);
+ assert(num);
+
+ return read_int64_from_file(f, (int64_t *) num);
+}
+
+int read_long_long_int_from_path(const char *path, long long *num) {
assert(path);
- assert(u);
+ assert(num);
- f = fopen(path, "re");
- if (!f)
- return -errno;
+ return read_int64_from_path(path, (int64_t *) num);
+}
+
+int read_unsigned_long_long_int_from_file(FILE *f, unsigned long long *num) {
+
+ assert(f);
+ assert(num);
+
+ return read_uint64_from_file(f, (uint64_t *) num);
+}
+
+int read_unsigned_long_long_int_from_path(const char *path, unsigned long long *num) {
+
+ assert(path);
+ assert(num);
- return read_uint32_from_file(f, u);
+ return read_uint64_from_path(path, (uint64_t *) num);
}
int str_to_strv(const char *str, char ***strv, const char *separator) {
@@ -782,7 +964,7 @@ int str_to_strv(const char *str, char ***strv, const char *separator) {
return -ENOMEM;
}
- new = (char **)realloc(v, sizeof(char *) * (i + 2));
+ new = (char **) realloc(v, sizeof(char *) * (i + 2));
if (!new) {
free(p);
free(v);
@@ -793,7 +975,7 @@ int str_to_strv(const char *str, char ***strv, const char *separator) {
v = new;
v[i] = p;
- v[i+1] = NULL;
+ v[i + 1] = NULL;
i++;
}
@@ -826,7 +1008,7 @@ int strv_attach(char **first, char **second, char ***strv, bool free_second) {
if (second) {
n2 = sizeof_strv(second);
- new = (char **)realloc(first, sizeof(char *) * (n1 + n2 + 1));
+ new = (char **) realloc(first, sizeof(char *) * (n1 + n2 + 1));
if (!new)
return -ENOMEM;
diff --git a/src/libsystem/libsystem.h b/src/libsystem/libsystem.h
index 5f6df97..4452179 100644
--- a/src/libsystem/libsystem.h
+++ b/src/libsystem/libsystem.h
@@ -428,6 +428,214 @@ int write_uint32_to_file(FILE *f, uint32_t u, enum file_write_flags flags);
int write_uint32_to_path(const char *path, uint32_t u, enum file_write_flags flags);
/**
+ * @brief Write 64 bit signed decimal integer to FILE.
+ *
+ * @param f File pointer.
+ * @param i 64 bit signed integer to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_int64_to_file(FILE *f, int64_t i, enum file_write_flags flags);
+
+/**
+ * @brief Write 64 bit signed decimal integer to path.
+ *
+ * @param path File path.
+ * @param i 64 bit signed integer to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_int64_to_path(const char *path, int64_t i, enum file_write_flags flags);
+
+/**
+ * @brief Write 64 bit unsigned decimal integer to FILE.
+ *
+ * @param f File pointer
+ * @param u 64 bit Unsigned integer to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_uint64_to_file(FILE *f, uint64_t u, enum file_write_flags flags);
+
+/**
+ * @brief Write 64 bit unsigned decimal integer to path.
+ *
+ * @param path File path.
+ * @param u 64 bit Unsigned integer to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_uint64_to_path(const char *path, uint64_t u, enum file_write_flags flags);
+
+/**
+ * @brief Write int to FILE.
+ *
+ * @param f File pointer
+ * @param num int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_int_to_file(FILE *f, int num, enum file_write_flags flags);
+
+/**
+ * @brief Write int to path.
+ *
+ * @param path File path.
+ * @param num int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_int_to_path(const char *path, int num, enum file_write_flags flags);
+
+/**
+ * @brief Write type unsigned int to FILE.
+ *
+ * @param f File pointer
+ * @param num unsigned int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_unsigned_int_to_file(FILE *f, unsigned int num, enum file_write_flags flags);
+
+/**
+ * @brief Write int to path.
+ *
+ * @param path File path.
+ * @param num int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_unsigned_int_to_path(const char *path, unsigned int num, enum file_write_flags flags);
+
+/**
+ * @brief Write long int to FILE.
+ *
+ * @param f File pointer
+ * @param num long int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_long_int_to_file(FILE *f, long int num, enum file_write_flags flags);
+
+/**
+ * @brief Write int to path.
+ *
+ * @param path File path.
+ * @param num int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_long_int_to_path(const char *path, long int num, enum file_write_flags flags);
+
+/**
+ * @brief Write unsigned long int to FILE.
+ *
+ * @param f File pointer
+ * @param num unsigned long int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_unsigned_long_int_to_file(FILE *f, unsigned long int num, enum file_write_flags flags);
+
+/**
+ * @brief Write int to path.
+ *
+ * @param path File path.
+ * @param num int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_unsigned_long_int_to_path(const char *path, unsigned long int num, enum file_write_flags flags);
+
+/**
+ * @brief Write long long int to FILE.
+ *
+ * @param f File pointer
+ * @param num long long int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_long_long_int_to_file(FILE *f, long long int num, enum file_write_flags flags);
+
+/**
+ * @brief Write int to path.
+ *
+ * @param path File path.
+ * @param num int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_long_long_int_to_path(const char *path, long long int num, enum file_write_flags flags);
+
+/**
+ * @brief Write unsigned long long int to FILE.
+ *
+ * @param f File pointer
+ * @param num unsigned long long int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_unsigned_long_long_int_to_file(FILE *f, unsigned long long int num, enum file_write_flags flags);
+
+/**
+ * @brief Write int to path.
+ *
+ * @param path File path.
+ * @param num int to write.
+ * @param flags Optional flags to write file. if
+ * ::FILE_WRITE_NEWLINE_IF_NOT is set, line-end added. For detail, see
+ * ::file_write_flags.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int write_unsigned_long_long_int_to_path(const char *path, unsigned long long int num, enum file_write_flags flags);
+
+/**
* @brief Read the first line from FILE
*
* @param f File pointer.
@@ -488,6 +696,166 @@ int read_uint32_from_file(FILE *f, uint32_t *u);
* @return 0 on success, -errno on failure.
*/
int read_uint32_from_path(const char *path, uint32_t *u);
+
+/**
+ * @brief Read 64 bit signed decimal integer from FILE.
+ *
+ * @param f File pointer.
+ * @param i 64 bit signed int value pointer.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_int64_from_file(FILE *f, int64_t *i);
+
+/**
+ * @brief Read 64 bit signed decimal integer from path.
+ *
+ * @param path File path.
+ * @param i 64 bit signed int value pointer.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_int64_from_path(const char *path, int64_t *i);
+
+/**
+ * @brief Read 64 bit unsigned decimal integer from FILE.
+ *
+ * @param f File pointer.
+ * @param u 64 bit unsigned int value pointer.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_uint64_from_file(FILE *f, uint64_t *u);
+
+/**
+ * @brief Read 64 bit unsigned decimal integer from path
+ *
+ * @param path File path.
+ * @param u 64 bit unsigned int value pointer.
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_uint64_from_path(const char *path, uint64_t *u);
+
+/**
+ * @brief Read type int from FILE
+ *
+ * @param f File pointer.
+ * @param num type int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_int_from_file(FILE *f, int *num);
+
+/**
+ * @brief Read type int from path
+ *
+ * @param path File path.
+ * @param num type int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_int_from_path(const char *path, int *num);
+
+/**
+ * @brief Read type unsigned int from FILE
+ *
+ * @param f File pointer.
+ * @param num type unsigned int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_unsigned_int_from_file(FILE *f, unsigned int *num);
+
+/**
+ * @brief Read type unsigned int from path
+ *
+ * @param path File path.
+ * @param num type unsigned int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_unsigned_int_from_path(const char *path, unsigned int *num);
+
+/**
+ * @brief Read type long int from FILE
+ *
+ * @param f File pointer.
+ * @param num type long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_long_int_from_file(FILE *f, long int *num);
+
+/**
+ * @brief Read type long int from path
+ *
+ * @param path File path.
+ * @param num type long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_long_int_from_path(const char *path, long int *num);
+
+/**
+ * @brief Read type unsigned long int from FILE
+ *
+ * @param f File pointer.
+ * @param num type unsigned long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_unsigned_long_int_from_file(FILE *f, unsigned long int *num);
+
+/**
+ * @brief Read type unsigned long int from path
+ *
+ * @param path File path.
+ * @param num type unsigned long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_unsigned_long_int_from_path(const char *path, unsigned long int *num);
+
+/**
+ * @brief Read type long long int from FILE
+ *
+ * @param f File pointer.
+ * @param num type long long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_long_long_int_from_file(FILE *f, long long *num);
+
+/**
+ * @brief Read type long long int from path
+ *
+ * @param path File path.
+ * @param num type long long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_long_long_int_from_path(const char *path, long long *num);
+
+/**
+ * @brief Read type unsigned long long int from FILE
+ *
+ * @param f File pointer.
+ * @param num type unsigned long long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_unsigned_long_long_int_from_file(FILE *f, unsigned long long *num);
+
+/**
+ * @brief Read type unsigned long long int from path
+ *
+ * @param path File path.
+ * @param num type unsigned long long int pointer
+ *
+ * @return 0 on success, -errno on failure.
+ */
+int read_unsigned_long_long_int_from_path(const char *path, unsigned long long *num);
/**
* @}
*/
diff --git a/src/libsystem/proc.c b/src/libsystem/proc.c
index 6a3d3df..49ddfde 100644
--- a/src/libsystem/proc.c
+++ b/src/libsystem/proc.c
@@ -89,7 +89,7 @@ int proc_pid_of(const char *pname) {
if (r < 0)
continue;
- if (strneq(pname, comm, TASK_COMM_LEN-1))
+ if (strneq(pname, comm, TASK_COMM_LEN - 1))
return atoi(de->d_name);
}
@@ -130,9 +130,7 @@ static int add_smap_to_smaps(struct smaps *maps, struct smap *map) {
maps->n_map++;
- maps->maps = (struct smap **)realloc(
- maps->maps,
- sizeof(struct smap *) * maps->n_map);
+ maps->maps = (struct smap **) realloc(maps->maps, sizeof(struct smap *) * maps->n_map);
if (!maps->maps)
return -ENOMEM;
@@ -189,8 +187,7 @@ int proc_pid_get_smaps(pid_t pid, struct smaps **maps, enum smap_mask mask) {
goto on_error;
}
- n = sscanf(buf, "%x-%x %ms %*s %*s %*s %ms",
- &map->start, &map->end, &map->mode, &map->name);
+ n = sscanf(buf, "%x-%x %ms %*s %*s %*s %ms", &map->start, &map->end, &map->mode, &map->name);
if (n == 3 && !map->name)
map->name = strdup("[anon]");
@@ -214,8 +211,7 @@ int proc_pid_get_smaps(pid_t pid, struct smaps **maps, enum smap_mask mask) {
break;
}
- if ((*buf >= '0' && *buf <= '9') ||
- (*buf >= 'a' && *buf <= 'f')) {
+ if ((*buf >= '0' && *buf <= '9') || (*buf >= 'a' && *buf <= 'f')) {
get_line = false;
break;
}
@@ -314,8 +310,7 @@ int proc_get_meminfo(struct meminfo *mi, enum meminfo_mask mask) {
return -errno;
if (remain_mask & MEMINFO_MASK_MEM_AVAILABLE)
- remain_mask |= (MEMINFO_MASK_MEM_FREE |
- MEMINFO_MASK_CACHED);
+ remain_mask |= (MEMINFO_MASK_MEM_FREE | MEMINFO_MASK_CACHED);
while (remain_mask) {
unsigned int v = 0;
@@ -350,8 +345,7 @@ int proc_get_meminfo(struct meminfo *mi, enum meminfo_mask mask) {
}
if (remain_mask & MEMINFO_MASK_MEM_AVAILABLE) {
- mi->value[MEMINFO_ID_MEM_AVAILABLE] =
- mi->value[MEMINFO_ID_MEM_FREE]
+ mi->value[MEMINFO_ID_MEM_AVAILABLE] = mi->value[MEMINFO_ID_MEM_FREE]
+ mi->value[MEMINFO_ID_CACHED];
}
diff --git a/src/test/test-foreach-glist.c b/src/test/test-foreach-glist.c
new file mode 100644
index 0000000..ba952e0
--- /dev/null
+++ b/src/test/test-foreach-glist.c
@@ -0,0 +1,138 @@
+/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
+
+/*
+ * libsystem
+ *
+ * Copyright (c) 2016 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the License);
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <assert.h>
+#include <limits.h>
+#include <glib.h>
+
+#include "libsystem/libsystem.h"
+#include "libsystem/glib-util.h"
+
+static void gen_test_list(GList **list) {
+ GList *l = NULL;
+ int i;
+
+ assert(list);
+ assert(!*list);
+
+ for (i = 1; i <= 10; i++)
+ l = g_list_append(l, GINT_TO_POINTER(i));
+
+ *list = l;
+}
+
+static void test_foreach_g_list(void) {
+ GList *list = NULL, *node;
+ char buf[LINE_MAX];
+ int n = 0;
+
+ gen_test_list(&list);
+
+ FOREACH_G_LIST(node, list) {
+ int i = GPOINTER_TO_INT(node->data);
+
+ n += snprintf(buf + n, LINE_MAX - n - 1, "%d ", i);
+ }
+
+ assert(streq(buf, "1 2 3 4 5 6 7 8 9 10 "));
+
+ g_list_free(list);
+}
+
+static void test_foreach_g_list_reverse(void) {
+ GList *list = NULL, *node;
+ char buf[LINE_MAX];
+ int n = 0;
+
+ gen_test_list(&list);
+
+ FOREACH_G_LIST_REVERSE(node, list) {
+ int i = GPOINTER_TO_INT(node->data);
+
+ n += snprintf(buf + n, LINE_MAX - n - 1, "%d ", i);
+ }
+
+ assert(streq(buf, "10 9 8 7 6 5 4 3 2 1 "));
+
+ g_list_free(list);
+}
+
+static void test_foreach_g_list_safe(void) {
+ GList *list = NULL, *node, *next;
+ char buf[LINE_MAX];
+ int n = 0;
+
+ gen_test_list(&list);
+
+ FOREACH_G_LIST_SAFE(node, next, list) {
+ int i = GPOINTER_TO_INT(node->data);
+
+ if (i % 2)
+ list = g_list_remove_link(list, node);
+ }
+
+ FOREACH_G_LIST(node, list) {
+ int i = GPOINTER_TO_INT(node->data);
+
+ n += snprintf(buf + n, LINE_MAX - n - 1, "%d ", i);
+ }
+
+ assert(streq(buf, "2 4 6 8 10 "));
+
+ g_list_free(list);
+}
+
+static void test_foreach_g_list_safe_reverse(void) {
+ GList *list = NULL, *node, *prev;
+ char buf[LINE_MAX];
+ int n = 0;
+
+ gen_test_list(&list);
+
+ FOREACH_G_LIST_SAFE_REVERSE(node, prev, list) {
+ int i = GPOINTER_TO_INT(node->data);
+
+ if (i % 2)
+ list = g_list_remove_link(list, node);
+ }
+
+ FOREACH_G_LIST_REVERSE(node, list) {
+ int i = GPOINTER_TO_INT(node->data);
+
+ n += snprintf(buf + n, LINE_MAX - n - 1, "%d ", i);
+ }
+
+ assert(streq(buf, "10 8 6 4 2 "));
+
+ g_list_free(list);
+}
+
+int main(int argc, char *argv[]) {
+
+ test_foreach_g_list();
+ test_foreach_g_list_reverse();
+
+ test_foreach_g_list_safe();
+ test_foreach_g_list_safe_reverse();
+
+ return 0;
+}
diff --git a/src/test/test-read-write.c b/src/test/test-read-write.c
new file mode 100644
index 0000000..5661ac9
--- /dev/null
+++ b/src/test/test-read-write.c
@@ -0,0 +1,110 @@
+/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
+
+/*
+ * libsystem
+ *
+ * Copyright (c) 2016 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the License);
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <assert.h>
+#include <errno.h>
+#include <stdint.h>
+
+#include "libsystem/libsystem.h"
+
+#define TEST_READ_WRITE_FILE "/tmp/test-read-write"
+#define TEST_STRING "L!i@b#s$y%s^t&e*m(T)e-s=tS`t_r+i|n~g"
+#define TEST_INT32 0x7fabcdef
+#define TEST_UINT32 0xffabcdef
+#define TEST_INT64 0x7fabcdef00abcdef
+#define TEST_UINT64 0xffabcdef00abcdef
+
+static void test_string_read_write(void) {
+ _cleanup_free_ char *str = NULL;
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+
+ assert(write_str_to_path(TEST_READ_WRITE_FILE, TEST_STRING, 0) >= 0);
+ assert(read_one_line_from_path(TEST_READ_WRITE_FILE, &str) >= 0);
+
+ assert(streq(str, TEST_STRING));
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+}
+
+static void test_int32_read_write(void) {
+ int32_t i;
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+
+ assert(write_int32_to_path(TEST_READ_WRITE_FILE, TEST_INT32, 0) >= 0);
+ assert(read_int32_from_path(TEST_READ_WRITE_FILE, &i) >= 0);
+
+ assert(i == TEST_INT32);
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+}
+
+static void test_uint32_read_write(void) {
+ uint32_t u;
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+
+ assert(write_uint32_to_path(TEST_READ_WRITE_FILE, TEST_UINT32, 0) >= 0);
+ assert(read_uint32_from_path(TEST_READ_WRITE_FILE, &u) >= 0);
+
+ assert(u == TEST_UINT32);
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+}
+
+static void test_int64_read_write(void) {
+ int64_t i;
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+
+ assert(write_int64_to_path(TEST_READ_WRITE_FILE, TEST_INT64, 0) >= 0);
+ assert(read_int64_from_path(TEST_READ_WRITE_FILE, &i) >= 0);
+
+ assert(i == TEST_INT64);
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+}
+
+static void test_uint64_read_write(void) {
+ uint64_t u;
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+
+ assert(write_uint64_to_path(TEST_READ_WRITE_FILE, TEST_UINT64, 0) >= 0);
+ assert(read_uint64_from_path(TEST_READ_WRITE_FILE, &u) >= 0);
+
+ assert(u == TEST_UINT64);
+
+ assert(unlink(TEST_READ_WRITE_FILE) == 0 || errno == ENOENT);
+}
+
+int main(int argc, char *argv[]) {
+ test_string_read_write();
+ test_int32_read_write();
+ test_uint32_read_write();
+ test_int64_read_write();
+ test_uint64_read_write();
+
+ return 0;
+}