Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/littlefs-project/littlefs.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristopher Haster <chaster@utexas.edu>2018-01-30 00:20:12 +0300
committerChristopher Haster <chaster@utexas.edu>2018-02-19 10:40:23 +0300
commita3fd2d4d6d5e125f878177931a8bd52e5d114f7a (patch)
treeb28db28611d9dd9a97bacbdf10426421386b0782 /lfs_util.h
parenta0a55fb9e5942b51331947b855756abcac42a3c5 (diff)
Added more configurable utils
Note: It's still expected to modify lfs_utils.h when porting littlefs to a new target/system. There's just too much room for system-specific improvements, such as taking advantage of CRC hardware. Rather, encouraging modification of lfs_util.h and making it easy to modify and debug should result in better integration with the consuming systems. This just adds a bunch of quality-of-life improvements that should help development and integration in littlefs. - Macros that require no side-effects are all-caps - System includes are only brought in when needed - Malloc/free wrappers - LFS_NO_* checks for quickly disabling things at the command line - At least a little-bit more docs
Diffstat (limited to 'lfs_util.h')
-rw-r--r--lfs_util.h92
1 files changed, 78 insertions, 14 deletions
diff --git a/lfs_util.h b/lfs_util.h
index 9fe77de..0b7ccae 100644
--- a/lfs_util.h
+++ b/lfs_util.h
@@ -18,13 +18,60 @@
#ifndef LFS_UTIL_H
#define LFS_UTIL_H
-#include <stdlib.h>
#include <stdint.h>
+#include <stdbool.h>
+#include <string.h>
+
+#ifndef LFS_NO_MALLOC
+#include <stdlib.h>
+#endif
+#ifndef LFS_NO_ASSERT
+#include <assert.h>
+#endif
+#if !defined(LFS_NO_DEBUG) || !defined(LFS_NO_WARN) || !defined(LFS_NO_ERROR)
#include <stdio.h>
+#endif
+
+
+// Macros, may be replaced by system specific wrappers. Arguments to these
+// macros must not have side-effects as the macros can be removed for a smaller
+// code footprint
+
+// Logging functions
+#ifndef LFS_NO_DEBUG
+#define LFS_DEBUG(fmt, ...) \
+ printf("lfs debug:%d: " fmt "\n", __LINE__, __VA_ARGS__)
+#else
+#define LFS_DEBUG(fmt, ...)
+#endif
+
+#ifndef LFS_NO_WARN
+#define LFS_WARN(fmt, ...) \
+ printf("lfs warn:%d: " fmt "\n", __LINE__, __VA_ARGS__)
+#else
+#define LFS_WARN(fmt, ...)
+#endif
+
+#ifndef LFS_NO_ERROR
+#define LFS_ERROR(fmt, ...) \
+ printf("lfs error:%d: " fmt "\n", __LINE__, __VA_ARGS__)
+#else
+#define LFS_ERROR(fmt, ...)
+#endif
+
+// Runtime assertions
+#ifndef LFS_NO_ASSERT
+#define LFS_ASSERT(test) assert(test)
+#else
+#define LFS_ASSERT(test)
+#endif
-// Builtin functions, these may be replaced by more
-// efficient implementations in the system
+// Builtin functions, these may be replaced by more efficient
+// toolchain-specific implementations. LFS_NO_INTRINSICS falls back to a more
+// expensive basic C implementation for debugging purposes
+
+// Min/max functions for unsigned 32-bit numbers
static inline uint32_t lfs_max(uint32_t a, uint32_t b) {
return (a > b) ? a : b;
}
@@ -33,8 +80,9 @@ static inline uint32_t lfs_min(uint32_t a, uint32_t b) {
return (a < b) ? a : b;
}
+// Find the next smallest power of 2 less than or equal to a
static inline uint32_t lfs_npw2(uint32_t a) {
-#if defined(__GNUC__) || defined(__CC_ARM)
+#if !defined(LFS_NO_INTRINSICS) && (defined(__GNUC__) || defined(__CC_ARM))
return 32 - __builtin_clz(a-1);
#else
uint32_t r = 0;
@@ -48,16 +96,19 @@ static inline uint32_t lfs_npw2(uint32_t a) {
#endif
}
+// Count the number of trailing binary zeros in a
+// lfs_ctz(0) may be undefined
static inline uint32_t lfs_ctz(uint32_t a) {
-#if defined(__GNUC__)
+#if !defined(LFS_NO_INTRINSICS) && defined(__GNUC__)
return __builtin_ctz(a);
#else
return lfs_npw2((a & -a) + 1) - 1;
#endif
}
+// Count the number of binary ones in a
static inline uint32_t lfs_popc(uint32_t a) {
-#if defined(__GNUC__) || defined(__CC_ARM)
+#if !defined(LFS_NO_INTRINSICS) && (defined(__GNUC__) || defined(__CC_ARM))
return __builtin_popcount(a);
#else
a = a - ((a >> 1) & 0x55555555);
@@ -66,17 +117,20 @@ static inline uint32_t lfs_popc(uint32_t a) {
#endif
}
+// Find the sequence comparison of a and b, this is the distance
+// between a and b ignoring overflow
static inline int lfs_scmp(uint32_t a, uint32_t b) {
return (int)(unsigned)(a - b);
}
+// Convert from 32-bit little-endian to native order
static inline uint32_t lfs_fromle32(uint32_t a) {
-#if ( \
+#if !defined(LFS_NO_INTRINSICS) && ( \
(defined( BYTE_ORDER ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \
(defined(__BYTE_ORDER ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \
(defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__))
return a;
-#elif ( \
+#elif !defined(LFS_NO_INTRINSICS) && ( \
(defined( BYTE_ORDER ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \
(defined(__BYTE_ORDER ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \
(defined(__BYTE_ORDER__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__))
@@ -89,19 +143,29 @@ static inline uint32_t lfs_fromle32(uint32_t a) {
#endif
}
+// Convert to 32-bit little-endian from native order
static inline uint32_t lfs_tole32(uint32_t a) {
return lfs_fromle32(a);
}
-// CRC-32 with polynomial = 0x04c11db7
+// Calculate CRC-32 with polynomial = 0x04c11db7
void lfs_crc(uint32_t *crc, const void *buffer, size_t size);
+// Allocate memory, only used if buffers are not provided to littlefs
+static inline void *lfs_malloc(size_t size) {
+#ifndef LFS_NO_MALLOC
+ return malloc(size);
+#else
+ return NULL;
+#endif
+}
-// Logging functions, these may be replaced by system-specific
-// logging functions
-#define LFS_DEBUG(fmt, ...) printf("lfs debug: " fmt "\n", __VA_ARGS__)
-#define LFS_WARN(fmt, ...) printf("lfs warn: " fmt "\n", __VA_ARGS__)
-#define LFS_ERROR(fmt, ...) printf("lfs error: " fmt "\n", __VA_ARGS__)
+// Deallocate memory, only used if buffers are not provided to littlefs
+static inline void lfs_free(void *p) {
+#ifndef LFS_NO_MALLOC
+ free(p);
+#endif
+}
#endif