summaryrefslogtreecommitdiff
path: root/lib/fatfs/src
diff options
context:
space:
mode:
Diffstat (limited to 'lib/fatfs/src')
-rw-r--r--lib/fatfs/src/ff.c59
-rw-r--r--lib/fatfs/src/ff.h12
-rw-r--r--lib/fatfs/src/ffconf.h43
3 files changed, 101 insertions, 13 deletions
diff --git a/lib/fatfs/src/ff.c b/lib/fatfs/src/ff.c
index 52adc2ab..3c3f1ace 100644
--- a/lib/fatfs/src/ff.c
+++ b/lib/fatfs/src/ff.c
@@ -34,7 +34,6 @@
#error Wrong include file (ff.h).
#endif
-
/* Limits and boundaries */
#define MAX_DIR 0x200000 /* Max size of FAT directory */
#define MAX_DIR_EX 0x10000000 /* Max size of exFAT directory */
@@ -43,6 +42,10 @@
#define MAX_FAT32 0x0FFFFFF5 /* Max FAT32 clusters (not specified, practical limit) */
#define MAX_EXFAT 0x7FFFFFFD /* Max exFAT clusters (differs from specs, implementation limit) */
+#define MIN_FAT12_SEC_VOL 4 /* Min size of the FAT sector volume
+ 1 FAT, 1 root dir, 1 reserved, 1 data sector */
+#define MIN_FAT12_DATA_SEC 1 /* Min FAT data sectors */
+
/* Character code support macros */
#define IsUpper(c) ((c) >= 'A' && (c) <= 'Z')
@@ -1118,7 +1121,7 @@ static FRESULT sync_fs ( /* Returns FR_OK or FR_DISK_ERR */
if (res == FR_OK) {
if (fs->fs_type == FS_FAT32 && fs->fsi_flag == 1) { /* FAT32: Update FSInfo sector if needed */
/* Create FSInfo structure */
- memset(fs->win, 0, sizeof fs->win);
+ memset(fs->win, 0, SS(fs));
st_word(fs->win + BS_55AA, 0xAA55); /* Boot signature */
st_dword(fs->win + FSI_LeadSig, 0x41615252); /* Leading signature */
st_dword(fs->win + FSI_StrucSig, 0x61417272); /* Structure signature */
@@ -1670,7 +1673,7 @@ static FRESULT dir_clear ( /* Returns FR_OK or FR_DISK_ERR */
if (sync_window(fs) != FR_OK) return FR_DISK_ERR; /* Flush disk access window */
sect = clst2sect(fs, clst); /* Top of the cluster */
fs->winsect = sect; /* Set window to top of the cluster */
- memset(fs->win, 0, sizeof fs->win); /* Clear window buffer */
+ memset(fs->win, 0, SS(fs)); /* Clear window buffer */
#if FF_USE_LFN == 3 /* Quick table clear by using multi-secter write */
/* Allocate a temporary buffer */
for (szb = ((DWORD)fs->csize * SS(fs) >= MAX_MALLOC) ? MAX_MALLOC : fs->csize * SS(fs), ibuf = 0; szb > SS(fs) && (ibuf = ff_memalloc(szb)) == 0; szb /= 2) ;
@@ -3318,7 +3321,7 @@ static UINT check_fs ( /* 0:FAT/FAT32 VBR, 1:exFAT VBR, 2:Not FAT and valid BS,
&& ld_word(fs->win + BPB_RsvdSecCnt) != 0 /* Properness of reserved sectors (MNBZ) */
&& (UINT)fs->win[BPB_NumFATs] - 1 <= 1 /* Properness of FATs (1 or 2) */
&& ld_word(fs->win + BPB_RootEntCnt) != 0 /* Properness of root dir entries (MNBZ) */
- && (ld_word(fs->win + BPB_TotSec16) >= 128 || ld_dword(fs->win + BPB_TotSec32) >= 0x10000) /* Properness of volume sectors (>=128) */
+ && (ld_word(fs->win + BPB_TotSec16) >= MIN_FAT12_SEC_VOL || ld_dword(fs->win + BPB_TotSec32) >= 0x10000) /* Properness of volume sectors (>=MIN_FAT12_SEC_VOL) */
&& ld_word(fs->win + BPB_FATSz16) != 0) { /* Properness of FAT size (MNBZ) */
return 0; /* It can be presumed an FAT VBR */
}
@@ -3438,6 +3441,10 @@ static FRESULT mount_volume ( /* FR_OK(0): successful, !=0: an error occurred */
if (disk_ioctl(fs->pdrv, GET_SECTOR_SIZE, &SS(fs)) != RES_OK) return FR_DISK_ERR;
if (SS(fs) > FF_MAX_SS || SS(fs) < FF_MIN_SS || (SS(fs) & (SS(fs) - 1))) return FR_DISK_ERR;
#endif
+#if FF_USE_DYN_BUFFER
+ fs->win = ff_memalloc(SS(fs)); /* Allocate memory for sector buffer */
+ if (!fs->win) return FR_NOT_ENOUGH_CORE;
+#endif
/* Find an FAT volume on the hosting drive */
fmt = find_volume(fs, LD2PT(vol));
@@ -3681,6 +3688,10 @@ FRESULT f_mount (
#if FF_FS_REENTRANT /* Discard mutex of the current volume */
ff_mutex_delete(vol);
#endif
+#if FF_USE_DYN_BUFFER
+ if (cfs->fs_type) /* Check if the buffer was ever allocated */
+ ff_memfree(cfs->win); /* Deallocate buffer allocated for the filesystem object */
+#endif
cfs->fs_type = 0; /* Invalidate the filesystem object to be unregistered */
}
@@ -3868,7 +3879,19 @@ FRESULT f_open (
fp->fptr = 0; /* Set file pointer top of the file */
#if !FF_FS_READONLY
#if !FF_FS_TINY
- memset(fp->buf, 0, sizeof fp->buf); /* Clear sector buffer */
+#if FF_USE_DYN_BUFFER
+ fp->buf = NULL;
+ if (res == FR_OK) {
+ fp->buf = ff_memalloc(SS(fs));
+ if (!fp->buf) {
+ res = FR_NOT_ENOUGH_CORE; /* Not enough memory */
+ goto fail;
+ }
+ memset(fp->buf, 0, SS(fs)); /* Clear sector buffer */
+ }
+#else
+ memset(fp->buf, 0, SS(fs)); /* Clear sector buffer */
+#endif
#endif
if ((mode & FA_SEEKEND) && fp->obj.objsize > 0) { /* Seek to end of file if FA_OPEN_APPEND is specified */
fp->fptr = fp->obj.objsize; /* Offset to seek */
@@ -3901,7 +3924,19 @@ FRESULT f_open (
FREE_NAMBUF();
}
- if (res != FR_OK) fp->obj.fs = 0; /* Invalidate file object on error */
+ if (res != FR_OK) {
+ fp->obj.fs = 0; /* Invalidate file object on error */
+#if !FF_FS_TINY && FF_USE_DYN_BUFFER
+ if (fp->buf) {
+ ff_memfree(fp->buf);
+ fp->buf = NULL;
+ }
+#endif
+ }
+
+#if FF_USE_DYN_BUFFER
+fail:
+#endif
LEAVE_FF(fs, res);
}
@@ -4235,6 +4270,10 @@ FRESULT f_close (
#else
fp->obj.fs = 0; /* Invalidate file object */
#endif
+#if !FF_FS_TINY && FF_USE_DYN_BUFFER
+ ff_memfree(fp->buf);
+ fp->buf = NULL;
+#endif
#if FF_FS_REENTRANT
unlock_volume(fs, FR_OK); /* Unlock volume */
#endif
@@ -5998,7 +6037,11 @@ FRESULT f_mkfs (
}
}
}
- if (sz_vol < 128) LEAVE_MKFS(FR_MKFS_ABORTED); /* Check if volume size is >=128s */
+ if (n_fat == 1) {
+ if (sz_vol < MIN_FAT12_SEC_VOL) LEAVE_MKFS(FR_MKFS_ABORTED); /* Check if volume size is >= MIN_FAT12_SEC_VOLs */
+ } else {
+ if (sz_vol < (MIN_FAT12_SEC_VOL + 1)) LEAVE_MKFS(FR_MKFS_ABORTED); /* Check if volume size is >= (MIN_FAT12_SEC_VOL+1)s */
+ }
/* Now start to create an FAT volume at b_vol and sz_vol */
@@ -6229,7 +6272,7 @@ FRESULT f_mkfs (
}
/* Determine number of clusters and final check of validity of the FAT sub-type */
- if (sz_vol < b_data + pau * 16 - b_vol) LEAVE_MKFS(FR_MKFS_ABORTED); /* Too small volume? */
+ if (sz_vol < b_data + pau * MIN_FAT12_DATA_SEC - b_vol) LEAVE_MKFS(FR_MKFS_ABORTED); /* Too small volume? */
n_clst = ((DWORD)sz_vol - sz_rsv - sz_fat * n_fat - sz_dir) / pau;
if (fsty == FS_FAT32) {
if (n_clst <= MAX_FAT16) { /* Too few clusters for FAT32? */
diff --git a/lib/fatfs/src/ff.h b/lib/fatfs/src/ff.h
index 19854705..f4493e03 100644
--- a/lib/fatfs/src/ff.h
+++ b/lib/fatfs/src/ff.h
@@ -116,7 +116,7 @@ typedef struct {
BYTE pd; /* Physical drive number */
BYTE pt; /* Partition: 0:Auto detect, 1-4:Forced partition) */
} PARTITION;
-extern const PARTITION VolToPart[]; /* Volume - Partition mapping table */
+extern PARTITION VolToPart[]; /* Volume - Partition mapping table */
#endif
#if FF_STR_VOLUME_ID
@@ -170,7 +170,11 @@ typedef struct {
LBA_t bitbase; /* Allocation bitmap base sector */
#endif
LBA_t winsect; /* Current sector appearing in the win[] */
+#if FF_USE_DYN_BUFFER
+ BYTE* win; /* Disk access window for Directory, FAT (and file data at tiny cfg) */
+#else
BYTE win[FF_MAX_SS]; /* Disk access window for Directory, FAT (and file data at tiny cfg) */
+#endif
} FATFS;
@@ -215,8 +219,12 @@ typedef struct {
DWORD* cltbl; /* Pointer to the cluster link map table (nulled on open, set by application) */
#endif
#if !FF_FS_TINY
+#if FF_USE_DYN_BUFFER
+ BYTE* buf; /* File private data read/write window */
+#else
BYTE buf[FF_MAX_SS]; /* File private data read/write window */
#endif
+#endif
} FIL;
@@ -289,7 +297,7 @@ typedef enum {
FR_MKFS_ABORTED, /* (14) The f_mkfs() aborted due to any problem */
FR_TIMEOUT, /* (15) Could not get a grant to access the volume within defined period */
FR_LOCKED, /* (16) The operation is rejected according to the file sharing policy */
- FR_NOT_ENOUGH_CORE, /* (17) LFN working buffer could not be allocated */
+ FR_NOT_ENOUGH_CORE, /* (17) Buffer could not be allocated */
FR_TOO_MANY_OPEN_FILES, /* (18) Number of open files > FF_FS_LOCK */
FR_INVALID_PARAMETER /* (19) Given parameter is invalid */
} FRESULT;
diff --git a/lib/fatfs/src/ffconf.h b/lib/fatfs/src/ffconf.h
index a5a4ae17..d378ee6d 100644
--- a/lib/fatfs/src/ffconf.h
+++ b/lib/fatfs/src/ffconf.h
@@ -1,3 +1,6 @@
+#ifndef _FFCONF_DEFINED
+#define _FFCONF_DEFINED
+
#include "sdkconfig.h"
/*---------------------------------------------------------------------------/
@@ -40,7 +43,7 @@
/* This option switches fast seek function. (0:Disable or 1:Enable) */
-#define FF_USE_EXPAND 0
+#define FF_USE_EXPAND 1
/* This option switches f_expand function. (0:Disable or 1:Enable) */
@@ -57,11 +60,36 @@
#define FF_USE_FORWARD 1
/* This option switches f_forward() function. (0:Disable or 1:Enable) */
+#if defined(CONFIG_FATFS_USE_STRFUNC_WITHOUT_CRLF_CONV)
+#define FF_USE_STRFUNC 1
+#elif defined(CONFIG_FATFS_USE_STRFUNC_WITH_CRLF_CONV)
+#define FF_USE_STRFUNC 2
+#else /* CONFIG_FATFS_USE_STRFUNC_NONE */
+#define FF_USE_STRFUNC 0
+#endif
-#define FF_USE_STRFUNC 1
+#ifdef CONFIG_FATFS_PRINT_LLI
+#define FF_PRINT_LLI 1
+#else
#define FF_PRINT_LLI 0
+#endif
+
+#ifdef CONFIG_FATFS_PRINT_FLOAT
+#define FF_PRINT_FLOAT 1
+#else
#define FF_PRINT_FLOAT 0
+#endif
+
+#if defined(CONFIG_FATFS_STRF_ENCODE_ANSI)
+#define FF_STRF_ENCODE 0
+#elif defined(CONFIG_FATFS_STRF_ENCODE_UTF16LE)
+#define FF_STRF_ENCODE 1
+#elif defined(CONFIG_FATFS_STRF_ENCODE_UTF16BE)
+#define FF_STRF_ENCODE 2
+#else /* CONFIG_FATFS_STRF_ENCODE_UTF8 */
#define FF_STRF_ENCODE 3
+#endif
+
/* FF_USE_STRFUNC switches string functions, f_gets(), f_putc(), f_puts() and
/ f_printf().
/
@@ -271,7 +299,7 @@
/ These options have no effect in read-only configuration (FF_FS_READONLY = 1). */
-#define FF_FS_NOFSINFO 0
+#define FF_FS_NOFSINFO (CONFIG_FATFS_DONT_TRUST_FREE_CLUSTER_CNT << 0 | CONFIG_FATFS_DONT_TRUST_LAST_ALLOC << 1)
/* If you need to know correct free space on the FAT32 volume, set bit 0 of this
/ option, and f_getfree() function at the first time after volume mount will force
/ a full FAT scan. Bit 1 controls the use of last allocated cluster number.
@@ -311,6 +339,13 @@
/ The FF_FS_TIMEOUT defines timeout period in unit of O/S time tick.
*/
+#define FF_USE_DYN_BUFFER CONFIG_FATFS_USE_DYN_BUFFERS
+/* The option FF_USE_DYN_BUFFER controls source of size used for buffers in the FS and FIL objects.
+/
+/ 0: Disable dynamic buffer size and use static size buffers defined by FF_MAX_SS.
+/ 1: Enable dynamic buffer size and use ff_memmalloc() to allocate buffers.
+*/
+
#include <sys/param.h>
#include "freertos/FreeRTOS.h"
#include "freertos/semphr.h"
@@ -330,3 +365,5 @@ void ff_memfree(void*);
#define disk_read ff_disk_read
#define disk_write ff_disk_write
#define disk_ioctl ff_disk_ioctl
+
+#endif /* _FFCONF_DEFINED */