添加qspi存储w25q128
添加littlefs文件系统 存储挂载路径/sys
This commit is contained in:
1 parent
c7cf944e61
commit
1f345bd81f
47 files changed
+22046
-271
No files matched your search
@@ -128,7 +128,7 @@ CONFIG_DFS_USING_WORKDIR=y
|
|||||||
CONFIG_DFS_FD_MAX=16
|
CONFIG_DFS_FD_MAX=16
|
||||||
CONFIG_RT_USING_DFS_V1=y
|
CONFIG_RT_USING_DFS_V1=y
|
||||||
# CONFIG_RT_USING_DFS_V2 is not set
|
# CONFIG_RT_USING_DFS_V2 is not set
|
||||||
CONFIG_DFS_FILESYSTEMS_MAX=4
|
CONFIG_DFS_FILESYSTEMS_MAX=6
|
||||||
CONFIG_DFS_FILESYSTEM_TYPES_MAX=4
|
CONFIG_DFS_FILESYSTEM_TYPES_MAX=4
|
||||||
CONFIG_RT_USING_DFS_ELMFAT=y
|
CONFIG_RT_USING_DFS_ELMFAT=y
|
||||||
|
|
||||||
@@ -164,7 +164,12 @@ CONFIG_RT_USING_DFS_TMPFS=y
|
|||||||
# CONFIG_RT_USING_DFS_MQUEUE is not set
|
# CONFIG_RT_USING_DFS_MQUEUE is not set
|
||||||
# end of DFS: device virtual file system
|
# end of DFS: device virtual file system
|
||||||
|
|
||||||
# CONFIG_RT_USING_FAL is not set
|
CONFIG_RT_USING_FAL=y
|
||||||
|
# CONFIG_FAL_DEBUG_CONFIG is not set
|
||||||
|
CONFIG_FAL_DEBUG=0
|
||||||
|
CONFIG_FAL_PART_HAS_TABLE_CFG=y
|
||||||
|
CONFIG_FAL_USING_SFUD_PORT=y
|
||||||
|
CONFIG_FAL_USING_NOR_FLASH_DEV_NAME="W25Q128"
|
||||||
|
|
||||||
#
|
#
|
||||||
# Device Drivers
|
# Device Drivers
|
||||||
@@ -188,7 +193,7 @@ CONFIG_RT_SERIAL_RB_BUFSZ=512
|
|||||||
# CONFIG_RT_USING_ZERO is not set
|
# CONFIG_RT_USING_ZERO is not set
|
||||||
# CONFIG_RT_USING_RANDOM is not set
|
# CONFIG_RT_USING_RANDOM is not set
|
||||||
# CONFIG_RT_USING_PWM is not set
|
# CONFIG_RT_USING_PWM is not set
|
||||||
# CONFIG_RT_USING_MTD_NOR is not set
|
CONFIG_RT_USING_MTD_NOR=y
|
||||||
# CONFIG_RT_USING_MTD_NAND is not set
|
# CONFIG_RT_USING_MTD_NAND is not set
|
||||||
# CONFIG_RT_USING_PM is not set
|
# CONFIG_RT_USING_PM is not set
|
||||||
CONFIG_RT_USING_RTC=y
|
CONFIG_RT_USING_RTC=y
|
||||||
@@ -205,7 +210,12 @@ CONFIG_RT_USING_SPI=y
|
|||||||
# CONFIG_RT_USING_SPI_BITOPS is not set
|
# CONFIG_RT_USING_SPI_BITOPS is not set
|
||||||
CONFIG_RT_USING_QSPI=y
|
CONFIG_RT_USING_QSPI=y
|
||||||
CONFIG_RT_USING_SPI_MSD=y
|
CONFIG_RT_USING_SPI_MSD=y
|
||||||
# CONFIG_RT_USING_SFUD is not set
|
CONFIG_RT_USING_SFUD=y
|
||||||
|
CONFIG_RT_SFUD_USING_SFDP=y
|
||||||
|
CONFIG_RT_SFUD_USING_FLASH_INFO_TABLE=y
|
||||||
|
CONFIG_RT_SFUD_USING_QSPI=y
|
||||||
|
CONFIG_RT_SFUD_SPI_MAX_HZ=50000000
|
||||||
|
# CONFIG_RT_DEBUG_SFUD is not set
|
||||||
# CONFIG_RT_USING_ENC28J60 is not set
|
# CONFIG_RT_USING_ENC28J60 is not set
|
||||||
# CONFIG_RT_USING_SPI_WIFI is not set
|
# CONFIG_RT_USING_SPI_WIFI is not set
|
||||||
# CONFIG_RT_USING_WDT is not set
|
# CONFIG_RT_USING_WDT is not set
|
||||||
@@ -660,7 +670,31 @@ CONFIG_PKG_SQLITE_DB_NAME_MAX_LEN=64
|
|||||||
CONFIG_PKG_USING_SQLITE_V3193=y
|
CONFIG_PKG_USING_SQLITE_V3193=y
|
||||||
# CONFIG_PKG_USING_RTI is not set
|
# CONFIG_PKG_USING_RTI is not set
|
||||||
# CONFIG_PKG_USING_DFS_YAFFS is not set
|
# CONFIG_PKG_USING_DFS_YAFFS is not set
|
||||||
# CONFIG_PKG_USING_LITTLEFS is not set
|
CONFIG_PKG_USING_LITTLEFS=y
|
||||||
|
CONFIG_PKG_LITTLEFS_PATH="/packages/system/littlefs"
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V090 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V170 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V172 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V201 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V205 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V214 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V220 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V221 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V230 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V250 is not set
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_V293 is not set
|
||||||
|
CONFIG_PKG_USING_LITTLEFS_V2112=y
|
||||||
|
# CONFIG_PKG_USING_LITTLEFS_LATEST_VERSION is not set
|
||||||
|
CONFIG_LFS_READ_SIZE=256
|
||||||
|
CONFIG_LFS_PROG_SIZE=256
|
||||||
|
CONFIG_LFS_BLOCK_SIZE=4096
|
||||||
|
CONFIG_LFS_CACHE_SIZE=256
|
||||||
|
CONFIG_LFS_BLOCK_CYCLES=500
|
||||||
|
# CONFIG_DFS_LFS_READONLY is not set
|
||||||
|
CONFIG_LFS_THREADSAFE=y
|
||||||
|
CONFIG_LFS_LOOKAHEAD_MAX=128
|
||||||
|
CONFIG_RT_DEF_LFS_DRIVERS=2
|
||||||
|
CONFIG_PKG_LITTLEFS_VER="v2.11.2"
|
||||||
# CONFIG_PKG_USING_DFS_JFFS2 is not set
|
# CONFIG_PKG_USING_DFS_JFFS2 is not set
|
||||||
# CONFIG_PKG_USING_DFS_UFFS is not set
|
# CONFIG_PKG_USING_DFS_UFFS is not set
|
||||||
# CONFIG_PKG_USING_LWEXT4 is not set
|
# CONFIG_PKG_USING_LWEXT4 is not set
|
||||||
|
|||||||
@@ -3,246 +3,253 @@
|
|||||||
<storageModule moduleId="org.eclipse.cdt.core.settings">
|
<storageModule moduleId="org.eclipse.cdt.core.settings">
|
||||||
<cconfiguration id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094">
|
<cconfiguration id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094">
|
||||||
<storageModule buildSystemId="org.eclipse.cdt.managedbuilder.core.configurationDataProvider" id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094" moduleId="org.eclipse.cdt.core.settings" name="Debug">
|
<storageModule buildSystemId="org.eclipse.cdt.managedbuilder.core.configurationDataProvider" id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094" moduleId="org.eclipse.cdt.core.settings" name="Debug">
|
||||||
<externalSettings />
|
<externalSettings/>
|
||||||
<extensions>
|
<extensions>
|
||||||
<extension id="org.eclipse.cdt.core.ELF" point="org.eclipse.cdt.core.BinaryParser" />
|
<extension id="org.eclipse.cdt.core.ELF" point="org.eclipse.cdt.core.BinaryParser"/>
|
||||||
<extension id="org.eclipse.cdt.core.GASErrorParser" point="org.eclipse.cdt.core.ErrorParser" />
|
<extension id="org.eclipse.cdt.core.GASErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
|
||||||
<extension id="org.eclipse.cdt.core.GmakeErrorParser" point="org.eclipse.cdt.core.ErrorParser" />
|
<extension id="org.eclipse.cdt.core.GmakeErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
|
||||||
<extension id="org.eclipse.cdt.core.GLDErrorParser" point="org.eclipse.cdt.core.ErrorParser" />
|
<extension id="org.eclipse.cdt.core.GLDErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
|
||||||
<extension id="org.eclipse.cdt.core.CWDLocator" point="org.eclipse.cdt.core.ErrorParser" />
|
<extension id="org.eclipse.cdt.core.CWDLocator" point="org.eclipse.cdt.core.ErrorParser"/>
|
||||||
<extension id="org.eclipse.cdt.core.GCCErrorParser" point="org.eclipse.cdt.core.ErrorParser" />
|
<extension id="org.eclipse.cdt.core.GCCErrorParser" point="org.eclipse.cdt.core.ErrorParser"/>
|
||||||
</extensions>
|
</extensions>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
<storageModule moduleId="cdtBuildSystem" version="4.0.0">
|
<storageModule moduleId="cdtBuildSystem" version="4.0.0">
|
||||||
<configuration artifactName="rtthread" buildArtefactType="org.eclipse.cdt.build.core.buildArtefactType.exe" buildProperties="org.eclipse.cdt.build.core.buildArtefactType=org.eclipse.cdt.build.core.buildArtefactType.exe,org.eclipse.cdt.build.core.buildType=org.eclipse.cdt.build.core.buildType.debug" cleanCommand="${cross_rm} -rf" description="" id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094" name="Debug" parent="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug">
|
<configuration artifactName="rtthread" buildArtefactType="org.eclipse.cdt.build.core.buildArtefactType.exe" buildProperties="org.eclipse.cdt.build.core.buildArtefactType=org.eclipse.cdt.build.core.buildArtefactType.exe,org.eclipse.cdt.build.core.buildType=org.eclipse.cdt.build.core.buildType.debug" cleanCommand="${cross_rm} -rf" description="" id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094" name="Debug" parent="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug" postbuildStep="arm-none-eabi-objcopy -O ihex "rtthread.elf" "${ProjName}.hex"">
|
||||||
<folderInfo id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094." name="/" resourcePath="">
|
<folderInfo id="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094." name="/" resourcePath="">
|
||||||
<toolChain id="ilg.gnuarmeclipse.managedbuild.cross.toolchain.elf.debug.1201710416" name="ARM Cross GCC" superClass="ilg.gnuarmeclipse.managedbuild.cross.toolchain.elf.debug">
|
<toolChain id="ilg.gnuarmeclipse.managedbuild.cross.toolchain.elf.debug.1201710416" name="ARM Cross GCC" superClass="ilg.gnuarmeclipse.managedbuild.cross.toolchain.elf.debug">
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createflash.251260409" name="Create flash image" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createflash" useByScannerDiscovery="false" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createflash.251260409" name="Create flash image" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createflash" useByScannerDiscovery="false" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createlisting.1365878149" name="Create extended listing" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createlisting" useByScannerDiscovery="false" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createlisting.1365878149" name="Create extended listing" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.createlisting" useByScannerDiscovery="false"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.printsize.709136944" name="Print size" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.printsize" useByScannerDiscovery="false" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.printsize.709136944" name="Print size" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.addtools.printsize" useByScannerDiscovery="false" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.level.1986446770" name="Optimization Level" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.level" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.level.none" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.level.1986446770" name="Optimization Level" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.level" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.level.none" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.messagelength.1312975261" name="Message length (-fmessage-length=0)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.messagelength" useByScannerDiscovery="true" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.messagelength.1312975261" name="Message length (-fmessage-length=0)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.messagelength" useByScannerDiscovery="true" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.signedchar.1538128212" name="'char' is signed (-fsigned-char)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.signedchar" useByScannerDiscovery="true" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.signedchar.1538128212" name="'char' is signed (-fsigned-char)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.signedchar" useByScannerDiscovery="true" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.functionsections.2136804218" name="Function sections (-ffunction-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.functionsections" useByScannerDiscovery="true" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.functionsections.2136804218" name="Function sections (-ffunction-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.functionsections" useByScannerDiscovery="true" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.datasections.244767666" name="Data sections (-fdata-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.datasections" useByScannerDiscovery="true" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.datasections.244767666" name="Data sections (-fdata-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.optimization.datasections" useByScannerDiscovery="true" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.level.1055848773" name="Debug level" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.level" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.level.default" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.level.1055848773" name="Debug level" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.level" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.level.default" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.format.501941135" name="Debug format" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.format" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.format.dwarf2" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.format.501941135" name="Debug format" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.format" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.debugging.format.dwarf2" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.name.1696308067" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.name" useByScannerDiscovery="false" value="GNU Tools for ARM Embedded Processors" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.name.1696308067" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.name" useByScannerDiscovery="false" value="GNU Tools for ARM Embedded Processors" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.architecture.1558403188" name="Architecture" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.architecture" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.architecture.arm" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.architecture.1558403188" name="Architecture" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.architecture" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.architecture.arm" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.family.749415257" name="ARM family" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.family" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.mcpu.cortex-m7" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.family.749415257" name="ARM family" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.family" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.mcpu.cortex-m7" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.instructionset.2114153533" name="Instruction set" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.instructionset" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.instructionset.thumb" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.instructionset.2114153533" name="Instruction set" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.instructionset" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.instructionset.thumb" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.prefix.1600865811" name="Prefix" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.prefix" useByScannerDiscovery="false" value="arm-none-eabi-" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.prefix.1600865811" name="Prefix" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.prefix" useByScannerDiscovery="false" value="arm-none-eabi-" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.c.1109963929" name="C compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.c" useByScannerDiscovery="false" value="gcc" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.c.1109963929" name="C compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.c" useByScannerDiscovery="false" value="gcc" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.cpp.1040883831" name="C++ compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.cpp" useByScannerDiscovery="false" value="g++" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.cpp.1040883831" name="C++ compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.cpp" useByScannerDiscovery="false" value="g++" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.ar.1678200391" name="Archiver" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.ar" useByScannerDiscovery="false" value="ar" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.ar.1678200391" name="Archiver" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.ar" useByScannerDiscovery="false" value="ar" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.objcopy.1171840296" name="Hex/Bin converter" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.objcopy" useByScannerDiscovery="false" value="objcopy" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.objcopy.1171840296" name="Hex/Bin converter" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.objcopy" useByScannerDiscovery="false" value="objcopy" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.objdump.342604837" name="Listing generator" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.objdump" useByScannerDiscovery="false" value="objdump" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.objdump.342604837" name="Listing generator" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.objdump" useByScannerDiscovery="false" value="objdump" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.size.898269225" name="Size command" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.size" useByScannerDiscovery="false" value="size" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.size.898269225" name="Size command" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.size" useByScannerDiscovery="false" value="size" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.make.2016398076" name="Build command" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.make" useByScannerDiscovery="false" value="make" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.make.2016398076" name="Build command" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.make" useByScannerDiscovery="false" value="make" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.rm.1606171496" name="Remove command" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.rm" useByScannerDiscovery="false" value="rm" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.command.rm.1606171496" name="Remove command" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.command.rm" useByScannerDiscovery="false" value="rm" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.id.540792084" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.id" useByScannerDiscovery="false" value="1287942917" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.id.540792084" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.toolchain.id" useByScannerDiscovery="false" value="1287942917" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.architecture.430121817" name="Architecture" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.architecture" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.arch.none" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.architecture.430121817" name="Architecture" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.architecture" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.arch.none" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.abi.966735324" name="Float ABI" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.abi" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.abi.hard" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.abi.966735324" name="Float ABI" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.abi" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.abi.hard" valueType="enumerated"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.warnings.allwarn.1381561249" name="Enable all common warnings (-Wall)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.warnings.allwarn" useByScannerDiscovery="true" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.warnings.allwarn.1381561249" name="Enable all common warnings (-Wall)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.warnings.allwarn" useByScannerDiscovery="true" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.target.other.2041717463" name="Other target flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.target.other" useByScannerDiscovery="true" value="" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.target.other.2041717463" name="Other target flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.target.other" useByScannerDiscovery="true" value="" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.unit.1463655269" name="FPU Type" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.unit" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.unit.fpv5spd16" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.unit.1463655269" name="FPU Type" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.unit" useByScannerDiscovery="true" value="ilg.gnuarmeclipse.managedbuild.cross.option.arm.target.fpu.unit.fpv5spd16" valueType="enumerated"/>
|
||||||
<targetPlatform archList="all" binaryParser="org.eclipse.cdt.core.ELF" id="ilg.gnuarmeclipse.managedbuild.cross.targetPlatform.1798638225" isAbstract="false" osList="all" superClass="ilg.gnuarmeclipse.managedbuild.cross.targetPlatform" />
|
<targetPlatform archList="all" binaryParser="org.eclipse.cdt.core.ELF" id="ilg.gnuarmeclipse.managedbuild.cross.targetPlatform.1798638225" isAbstract="false" osList="all" superClass="ilg.gnuarmeclipse.managedbuild.cross.targetPlatform"/>
|
||||||
<builder buildPath="${workspace_loc:/qemu-vexpress-a9}/Debug" cleanBuildTarget="clean2" id="ilg.gnuarmeclipse.managedbuild.cross.builder.1736709688" keepEnvironmentInBuildfile="false" managedBuildOn="true" name="GNU Make Builder" parallelBuildOn="true" parallelizationNumber="optimal" superClass="ilg.gnuarmeclipse.managedbuild.cross.builder" />
|
<builder buildPath="${workspace_loc:/qemu-vexpress-a9}/Debug" cleanBuildTarget="clean2" id="ilg.gnuarmeclipse.managedbuild.cross.builder.1736709688" keepEnvironmentInBuildfile="false" managedBuildOn="true" name="GNU Make Builder" parallelBuildOn="true" parallelizationNumber="optimal" superClass="ilg.gnuarmeclipse.managedbuild.cross.builder"/>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler.1810966071" name="GNU ARM Cross Assembler" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler.1810966071" name="GNU ARM Cross Assembler" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler">
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.usepreprocessor.1072524326" name="Use preprocessor" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.usepreprocessor" useByScannerDiscovery="false" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.usepreprocessor.1072524326" name="Use preprocessor" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.usepreprocessor" useByScannerDiscovery="false" value="true" valueType="boolean"/>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.include.paths.161242639" name="Include paths (-I)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.include.paths" useByScannerDiscovery="true" valueType="includePath">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.include.paths.161242639" name="Include paths (-I)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.include.paths" useByScannerDiscovery="true" valueType="includePath">
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}}""/>
|
||||||
</option>
|
</option>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.defs.1521934876" name="Defined symbols (-D)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.defs" useByScannerDiscovery="true" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.defs.1521934876" name="Defined symbols (-D)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.defs" useByScannerDiscovery="true"/>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.flags.1325367962" name="Assembler flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.flags" useByScannerDiscovery="false" valueType="stringList">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.flags.1325367962" name="Assembler flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.assembler.flags" useByScannerDiscovery="false" valueType="stringList">
|
||||||
<listOptionValue builtIn="false" value="-mimplicit-it=thumb" />
|
<listOptionValue builtIn="false" value="-mimplicit-it=thumb"/>
|
||||||
</option>
|
</option>
|
||||||
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler.input.1843333483" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler.input" />
|
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler.input.1843333483" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.assembler.input"/>
|
||||||
</tool>
|
</tool>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.1570350559" name="GNU ARM Cross C Compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.1570350559" name="GNU ARM Cross C Compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler">
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.paths.634882052" name="Include paths (-I)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.paths" useByScannerDiscovery="true" valueType="includePath">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.paths.634882052" name="Include paths (-I)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.paths" useByScannerDiscovery="true" valueType="includePath">
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/cubemx/Inc}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/cubemx/Inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include//config}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include//config}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Device//ST//STM32H7xx//Include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Device//ST//STM32H7xx//Include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//RTOS//Template}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//RTOS//Template}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc//Legacy}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc//Legacy}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/.}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/.}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/applications}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/applications}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//.}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//.}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx/Inc}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx/Inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/cJSON-v1.7.17}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/cJSON-v1.7.17}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/sqlite-v3.19.3}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/littlefs-v2.11.2}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/devfs}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/sqlite-v3.19.3}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/elmfat}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/devfs}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/tmpfs}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/elmfat}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/tmpfs}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/spi}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/finsh}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/spi/sfud/inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/common/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/spi}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/newlib}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/fal/inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/epoll}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/finsh}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/eventfd}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/common/include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/poll}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/newlib}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/ipc}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/epoll}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/eventfd}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/common}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/poll}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/cortex-m7}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/ipc}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/include}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/common}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/cortex-m7}""/>
|
||||||
</option>
|
</option>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.defs.100549972" name="Defined symbols (-D)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.defs" useByScannerDiscovery="true" valueType="definedSymbols">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.defs.100549972" name="Defined symbols (-D)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.defs" useByScannerDiscovery="true" valueType="definedSymbols">
|
||||||
<listOptionValue builtIn="false" value="SOC_FAMILY_STM32" />
|
<listOptionValue builtIn="false" value="SOC_FAMILY_STM32"/>
|
||||||
<listOptionValue builtIn="false" value="SOC_SERIES_STM32H7" />
|
<listOptionValue builtIn="false" value="SOC_SERIES_STM32H7"/>
|
||||||
<listOptionValue builtIn="false" value="USE_HAL_DRIVER" />
|
<listOptionValue builtIn="false" value="USE_HAL_DRIVER"/>
|
||||||
<listOptionValue builtIn="false" value="STM32H743xx" />
|
<listOptionValue builtIn="false" value="STM32H743xx"/>
|
||||||
</option>
|
</option>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.other.2133065240" name="Other compiler flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.other" useByScannerDiscovery="true" value="" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.other.2133065240" name="Other compiler flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.other" useByScannerDiscovery="true" value="" valueType="string"/>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.files.714348818" name="Include files (-include)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.files" useByScannerDiscovery="true" valueType="includeFiles">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.files.714348818" name="Include files (-include)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.compiler.include.files" useByScannerDiscovery="true" valueType="includeFiles">
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/rtconfig_preinc.h}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/rtconfig_preinc.h}""/>
|
||||||
</option>
|
</option>
|
||||||
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.input.992053063" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.input" />
|
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.input.992053063" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.input"/>
|
||||||
</tool>
|
</tool>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker.869072473" name="Cross ARM C Linker" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker.869072473" name="Cross ARM C Linker" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker">
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.gcsections.1167322178" name="Remove unused sections (-Xlinker --gc-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.gcsections" useByScannerDiscovery="false" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.gcsections.1167322178" name="Remove unused sections (-Xlinker --gc-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.gcsections" useByScannerDiscovery="false" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostart.351692886" name="Do not use standard start files (-nostartfiles)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostart" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostart.351692886" name="Do not use standard start files (-nostartfiles)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostart" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostdlibs.1009243715" name="No startup or default libs (-nostdlib)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostdlibs" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostdlibs.1009243715" name="No startup or default libs (-nostdlib)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nostdlibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nodeflibs.2016026082" name="Do not use default libraries (-nodefaultlibs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nodeflibs" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nodeflibs.2016026082" name="Do not use default libraries (-nodefaultlibs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.nodeflibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.usenewlibnano.923990336" name="Use newlib-nano (--specs=nano.specs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.usenewlibnano" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.usenewlibnano.923990336" name="Use newlib-nano (--specs=nano.specs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.usenewlibnano" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option defaultValue="true" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.shared.548869459" name="Shared (-shared)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.shared" useByScannerDiscovery="false" valueType="boolean" />
|
<option defaultValue="true" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.shared.548869459" name="Shared (-shared)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.shared" useByScannerDiscovery="false" valueType="boolean"/>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.scriptfile.1818777301" name="Script files (-T)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.scriptfile" useByScannerDiscovery="false" valueType="stringList">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.scriptfile.1818777301" name="Script files (-T)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.scriptfile" useByScannerDiscovery="false" valueType="stringList">
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//linkscripts//STM32H743IITx//link.lds}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//linkscripts//STM32H743IITx//link.lds}""/>
|
||||||
</option>
|
</option>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.libs.1135656995" name="Libraries (-l)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.libs" useByScannerDiscovery="false" valueType="libs">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.libs.1135656995" name="Libraries (-l)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.libs" useByScannerDiscovery="false" valueType="libs">
|
||||||
<listOptionValue builtIn="false" value="c " />
|
<listOptionValue builtIn="false" value="c "/>
|
||||||
<listOptionValue builtIn="false" value="m " />
|
<listOptionValue builtIn="false" value="m "/>
|
||||||
</option>
|
</option>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.paths.36884122" name="Library search path (-L)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.paths" useByScannerDiscovery="false" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.paths.36884122" name="Library search path (-L)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.paths" useByScannerDiscovery="false"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.other.396049466" name="Other linker flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.other" useByScannerDiscovery="false" value="" valueType="string" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.other.396049466" name="Other linker flags" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.other" useByScannerDiscovery="false" value="" valueType="string"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.cref.1645737861" name="Cross reference (-Xlinker --cref)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.cref" useByScannerDiscovery="false" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.cref.1645737861" name="Cross reference (-Xlinker --cref)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.c.linker.cref" useByScannerDiscovery="false" value="true" valueType="boolean"/>
|
||||||
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker.input.334732222" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker.input">
|
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker.input.334732222" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.c.linker.input">
|
||||||
<additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)" />
|
<additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)"/>
|
||||||
<additionalInput kind="additionalinput" paths="$(LIBS)" />
|
<additionalInput kind="additionalinput" paths="$(LIBS)"/>
|
||||||
</inputType>
|
</inputType>
|
||||||
</tool>
|
</tool>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker.1601059928" name="GNU ARM Cross C++ Linker" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker.1601059928" name="GNU ARM Cross C++ Linker" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker">
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.gcsections.437759352" name="Remove unused sections (-Xlinker --gc-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.gcsections" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.gcsections.437759352" name="Remove unused sections (-Xlinker --gc-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.gcsections" value="true" valueType="boolean"/>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.scriptfile.1101974459" name="Script files (-T)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.scriptfile" useByScannerDiscovery="false" valueType="stringList">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.scriptfile.1101974459" name="Script files (-T)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.scriptfile" useByScannerDiscovery="false" valueType="stringList">
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//linkscripts//STM32H743IITx//link.lds}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//linkscripts//STM32H743IITx//link.lds}""/>
|
||||||
</option>
|
</option>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.cref.2007675975" name="Cross reference (-Xlinker --cref)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.cref" useByScannerDiscovery="false" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.cref.2007675975" name="Cross reference (-Xlinker --cref)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.cref" useByScannerDiscovery="false" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnano.2105838438" name="Use newlib-nano (--specs=nano.specs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnano" useByScannerDiscovery="false" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnano.2105838438" name="Use newlib-nano (--specs=nano.specs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnano" useByScannerDiscovery="false" value="true" valueType="boolean"/>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.libs.934137837" name="Libraries (-l)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.libs" useByScannerDiscovery="false" valueType="libs">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.libs.934137837" name="Libraries (-l)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.libs" useByScannerDiscovery="false" valueType="libs">
|
||||||
<listOptionValue builtIn="false" value="c " />
|
<listOptionValue builtIn="false" value="c "/>
|
||||||
<listOptionValue builtIn="false" value="m " />
|
<listOptionValue builtIn="false" value="m "/>
|
||||||
</option>
|
</option>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostart.2118356996" name="Do not use standard start files (-nostartfiles)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostart" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostart.2118356996" name="Do not use standard start files (-nostartfiles)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostart" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nodeflibs.1427884346" name="Do not use default libraries (-nodefaultlibs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nodeflibs" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nodeflibs.1427884346" name="Do not use default libraries (-nodefaultlibs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nodeflibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostdlibs.1433863653" name="No startup or default libs (-nostdlib)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostdlibs" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostdlibs.1433863653" name="No startup or default libs (-nostdlib)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.nostdlibs" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printgcsections.1387745410" name="Print removed sections (-Xlinker --print-gc-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printgcsections" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printgcsections.1387745410" name="Print removed sections (-Xlinker --print-gc-sections)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printgcsections" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.strip.1230158061" name="Omit all symbol information (-s)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.strip" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.strip.1230158061" name="Omit all symbol information (-s)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.strip" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printmap.1307581821" name="Print link map (-Xlinker --print-map)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printmap" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printmap.1307581821" name="Print link map (-Xlinker --print-map)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.printmap" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.useprintffloat.960778920" name="Use float with nano printf (-u _printf_float)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.useprintffloat" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.useprintffloat.960778920" name="Use float with nano printf (-u _printf_float)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.useprintffloat" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usescanffloat.637205035" name="Use float with nano scanf (-u _scanf_float)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usescanffloat" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usescanffloat.637205035" name="Use float with nano scanf (-u _scanf_float)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usescanffloat" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnosys.1948314201" name="Do not use syscalls (--specs=nosys.specs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnosys" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnosys.1948314201" name="Do not use syscalls (--specs=nosys.specs)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.usenewlibnosys" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.verbose.273162112" name="Verbose (-v)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.verbose" useByScannerDiscovery="false" value="false" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.verbose.273162112" name="Verbose (-v)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.verbose" useByScannerDiscovery="false" value="false" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.paths.1399535143" name="Library search path (-L)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.paths" useByScannerDiscovery="false" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.paths.1399535143" name="Library search path (-L)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.linker.paths" useByScannerDiscovery="false"/>
|
||||||
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker.input.262373798" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker.input">
|
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker.input.262373798" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.linker.input">
|
||||||
<additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)" />
|
<additionalInput kind="additionalinputdependency" paths="$(USER_OBJS)"/>
|
||||||
<additionalInput kind="additionalinput" paths="$(LIBS)" />
|
<additionalInput kind="additionalinput" paths="$(LIBS)"/>
|
||||||
</inputType>
|
</inputType>
|
||||||
</tool>
|
</tool>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.archiver.506412204" name="GNU ARM Cross Archiver" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.archiver" />
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.archiver.506412204" name="GNU ARM Cross Archiver" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.archiver"/>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.createflash.1461589245" name="GNU ARM Cross Create Flash Image" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.createflash">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.createflash.1461589245" name="GNU ARM Cross Create Flash Image" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.createflash">
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createflash.choice.1937707052" name="Output file format (-O)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createflash.choice" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.createflash.choice.binary" valueType="enumerated" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createflash.choice.1937707052" name="Output file format (-O)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createflash.choice" useByScannerDiscovery="false" value="ilg.gnuarmeclipse.managedbuild.cross.option.createflash.choice.binary" valueType="enumerated"/>
|
||||||
</tool>
|
</tool>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.createlisting.82359725" name="GNU ARM Cross Create Listing" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.createlisting">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.createlisting.82359725" name="GNU ARM Cross Create Listing" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.createlisting">
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.source.601724476" name="Display source (--source|-S)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.source" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.source.601724476" name="Display source (--source|-S)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.source" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.allheaders.692505279" name="Display all headers (--all-headers|-x)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.allheaders" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.allheaders.692505279" name="Display all headers (--all-headers|-x)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.allheaders" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.demangle.97345172" name="Demangle names (--demangle|-C)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.demangle" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.demangle.97345172" name="Demangle names (--demangle|-C)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.demangle" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.linenumbers.1342893377" name="Display line numbers (--line-numbers|-l)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.linenumbers" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.linenumbers.1342893377" name="Display line numbers (--line-numbers|-l)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.linenumbers" value="true" valueType="boolean"/>
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.wide.1533725981" name="Wide lines (--wide|-w)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.wide" value="true" valueType="boolean" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.wide.1533725981" name="Wide lines (--wide|-w)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.createlisting.wide" value="true" valueType="boolean"/>
|
||||||
</tool>
|
</tool>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.printsize.1073550295" name="GNU ARM Cross Print Size" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.printsize">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.printsize.1073550295" name="GNU ARM Cross Print Size" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.printsize">
|
||||||
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.printsize.format.946451386" name="Size format" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.printsize.format" useByScannerDiscovery="false" />
|
<option id="ilg.gnuarmeclipse.managedbuild.cross.option.printsize.format.946451386" name="Size format" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.printsize.format" useByScannerDiscovery="false"/>
|
||||||
</tool>
|
</tool>
|
||||||
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler.1302177015" name="GNU ARM Cross C++ Compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler">
|
<tool id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler.1302177015" name="GNU ARM Cross C++ Compiler" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler">
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.defs.704468062" name="Defined symbols (-D)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.defs" useByScannerDiscovery="true" valueType="definedSymbols">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.defs.704468062" name="Defined symbols (-D)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.defs" useByScannerDiscovery="true" valueType="definedSymbols">
|
||||||
<listOptionValue builtIn="false" value="SOC_FAMILY_STM32" />
|
<listOptionValue builtIn="false" value="SOC_FAMILY_STM32"/>
|
||||||
<listOptionValue builtIn="false" value="SOC_SERIES_STM32H7" />
|
<listOptionValue builtIn="false" value="SOC_SERIES_STM32H7"/>
|
||||||
<listOptionValue builtIn="false" value="USE_HAL_DRIVER" />
|
<listOptionValue builtIn="false" value="USE_HAL_DRIVER"/>
|
||||||
<listOptionValue builtIn="false" value="STM32H743xx" />
|
<listOptionValue builtIn="false" value="STM32H743xx"/>
|
||||||
</option>
|
</option>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.paths.302877723" name="Include paths (-I)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.paths" useByScannerDiscovery="true" valueType="includePath">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.paths.302877723" name="Include paths (-I)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.paths" useByScannerDiscovery="true" valueType="includePath">
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include//config}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/drivers//include//config}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Device//ST//STM32H7xx//Include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Device//ST//STM32H7xx//Include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//Include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//RTOS//Template}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//CMSIS//RTOS//Template}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc//Legacy}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/libraries//STM32H7xx_HAL_Driver//Inc//Legacy}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/.}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/.}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/applications}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}/applications}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//.}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//.}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx/Inc}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx/Inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//cubemx}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/cJSON-v1.7.17}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/cJSON-v1.7.17}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/sqlite-v3.19.3}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/littlefs-v2.11.2}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/devfs}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//packages/sqlite-v3.19.3}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/elmfat}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/devfs}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/tmpfs}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/elmfat}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/filesystems/tmpfs}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/dfs/dfs_v1/include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/spi}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/finsh}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/spi/sfud/inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/common/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/drivers/spi}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/newlib}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/fal/inc}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/epoll}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/finsh}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/eventfd}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/common/include}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/poll}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/compilers/newlib}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/ipc}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/epoll}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/include}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/eventfd}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/common}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/io/poll}""/>
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/cortex-m7}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/components/libc/posix/ipc}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/include}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/common}""/>
|
||||||
|
<listOptionValue builtIn="false" value=""${workspace_loc://${ProjName}//rt-thread/libcpu/arm/cortex-m7}""/>
|
||||||
</option>
|
</option>
|
||||||
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.files.343249373" name="Include files (-include)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.files" useByScannerDiscovery="true" valueType="includeFiles">
|
<option IS_BUILTIN_EMPTY="false" IS_VALUE_EMPTY="false" id="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.files.343249373" name="Include files (-include)" superClass="ilg.gnuarmeclipse.managedbuild.cross.option.cpp.compiler.include.files" useByScannerDiscovery="true" valueType="includeFiles">
|
||||||
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/rtconfig_preinc.h}"" />
|
<listOptionValue builtIn="false" value=""${workspace_loc:/${ProjName}/rtconfig_preinc.h}""/>
|
||||||
</option>
|
</option>
|
||||||
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler.input.45918001" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler.input" />
|
<inputType id="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler.input.45918001" superClass="ilg.gnuarmeclipse.managedbuild.cross.tool.cpp.compiler.input"/>
|
||||||
</tool>
|
</tool>
|
||||||
</toolChain>
|
</toolChain>
|
||||||
</folderInfo>
|
</folderInfo>
|
||||||
<sourceEntries>
|
<sourceEntries>
|
||||||
<entry excluding="packages/sqlite-v3.19.3/rtthread_vfs.c|//cubemx/Drivers|//cubemx/EWARM|//cubemx/Src/stm32h7xx_it.c|//cubemx/Src/system_stm32h7xx.c|//packages/sqlite-v3.19.3/dbhelper.c|//packages/sqlite-v3.19.3/rtthread_io_methods.c|//packages/sqlite-v3.19.3/rtthread_mutex.c|//packages/sqlite-v3.19.3/rtthread_vfs.c|//packages/sqlite-v3.19.3/shell.c|//packages/sqlite-v3.19.3/student_dao.c|//rt-thread/components/dfs/dfs_v1/filesystems/cromfs|//rt-thread/components/dfs/dfs_v1/filesystems/mqueue|//rt-thread/components/dfs/dfs_v1/filesystems/nfs|//rt-thread/components/dfs/dfs_v1/filesystems/ramfs|//rt-thread/components/dfs/dfs_v1/filesystems/romfs|//rt-thread/components/dfs/dfs_v1/filesystems/skeleton|//rt-thread/components/dfs/dfs_v2|//rt-thread/components/drivers/audio|//rt-thread/components/drivers/can|//rt-thread/components/drivers/clk|//rt-thread/components/drivers/core/dm.c|//rt-thread/components/drivers/core/driver.c|//rt-thread/components/drivers/core/platform.c|//rt-thread/components/drivers/core/platform_ofw.c|//rt-thread/components/drivers/cputime|//rt-thread/components/drivers/fdt|//rt-thread/components/drivers/hwcrypto|//rt-thread/components/drivers/hwtimer|//rt-thread/components/drivers/i2c|//rt-thread/components/drivers/ktime|//rt-thread/components/drivers/misc|//rt-thread/components/drivers/mtd|//rt-thread/components/drivers/ofw|//rt-thread/components/drivers/phy|//rt-thread/components/drivers/pic|//rt-thread/components/drivers/pin/pin_dm.c|//rt-thread/components/drivers/pin/pin_ofw.c|//rt-thread/components/drivers/pinctrl|//rt-thread/components/drivers/pm|//rt-thread/components/drivers/rtc/alarm.c|//rt-thread/components/drivers/sensor|//rt-thread/components/drivers/serial/serial_dm.c|//rt-thread/components/drivers/serial/serial_tty.c|//rt-thread/components/drivers/serial/serial_v2.c|//rt-thread/components/drivers/spi/enc28j60.c|//rt-thread/components/drivers/spi/sfud|//rt-thread/components/drivers/spi/spi-bit-ops.c|//rt-thread/components/drivers/spi/spi_flash_sfud.c|//rt-thread/components/drivers/spi/spi_wifi_rw009.c|//rt-thread/components/drivers/touch|//rt-thread/components/drivers/usb|//rt-thread/components/drivers/virtio|//rt-thread/components/drivers/watchdog|//rt-thread/components/drivers/wlan|//rt-thread/components/fal|//rt-thread/components/legacy|//rt-thread/components/libc/compilers/armlibc|//rt-thread/components/libc/compilers/dlib|//rt-thread/components/libc/compilers/musl|//rt-thread/components/libc/compilers/picolibc|//rt-thread/components/libc/cplusplus|//rt-thread/components/libc/posix|//rt-thread/components/lwp|//rt-thread/components/mm|//rt-thread/components/mprotect|//rt-thread/components/net|//rt-thread/components/utilities|//rt-thread/components/vbus|//rt-thread/libcpu/aarch64|//rt-thread/libcpu/arc|//rt-thread/libcpu/arm/AT91SAM7S|//rt-thread/libcpu/arm/AT91SAM7X|//rt-thread/libcpu/arm/am335x|//rt-thread/libcpu/arm/arm926|//rt-thread/libcpu/arm/armv6|//rt-thread/libcpu/arm/common/atomic_arm.c|//rt-thread/libcpu/arm/common/divsi3.S|//rt-thread/libcpu/arm/cortex-a|//rt-thread/libcpu/arm/cortex-m0|//rt-thread/libcpu/arm/cortex-m23|//rt-thread/libcpu/arm/cortex-m3|//rt-thread/libcpu/arm/cortex-m33|//rt-thread/libcpu/arm/cortex-m4|//rt-thread/libcpu/arm/cortex-m7/context_iar.S|//rt-thread/libcpu/arm/cortex-m7/context_rvds.S|//rt-thread/libcpu/arm/cortex-m7/mpu.c|//rt-thread/libcpu/arm/cortex-m85|//rt-thread/libcpu/arm/cortex-r4|//rt-thread/libcpu/arm/cortex-r52|//rt-thread/libcpu/arm/dm36x|//rt-thread/libcpu/arm/lpc214x|//rt-thread/libcpu/arm/lpc24xx|//rt-thread/libcpu/arm/realview-a8-vmm|//rt-thread/libcpu/arm/s3c24x0|//rt-thread/libcpu/arm/s3c44b0|//rt-thread/libcpu/arm/sep4020|//rt-thread/libcpu/arm/zynqmp-r5|//rt-thread/libcpu/avr32|//rt-thread/libcpu/blackfin|//rt-thread/libcpu/c-sky|//rt-thread/libcpu/ia32|//rt-thread/libcpu/m16c|//rt-thread/libcpu/mips|//rt-thread/libcpu/nios|//rt-thread/libcpu/ppc|//rt-thread/libcpu/risc-v|//rt-thread/libcpu/rx|//rt-thread/libcpu/sim|//rt-thread/libcpu/sparc-v8|//rt-thread/libcpu/ti-dsp|//rt-thread/libcpu/unicore32|//rt-thread/libcpu/v850|//rt-thread/libcpu/xilinx|//rt-thread/src/cpu.c|//rt-thread/src/mem.c|//rt-thread/src/scheduler_mp.c|//rt-thread/src/signal.c|//rt-thread/src/slab.c|//rt-thread/tools" flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name="" />
|
<entry excluding="packages/sqlite-v3.19.3/rtthread_vfs.c|//cubemx/Drivers|//cubemx/EWARM|//cubemx/Src/stm32h7xx_it.c|//cubemx/Src/system_stm32h7xx.c|//packages/littlefs-v2.11.2/runners|//packages/sqlite-v3.19.3/dbhelper.c|//packages/sqlite-v3.19.3/rtthread_io_methods.c|//packages/sqlite-v3.19.3/rtthread_mutex.c|//packages/sqlite-v3.19.3/rtthread_vfs.c|//packages/sqlite-v3.19.3/shell.c|//packages/sqlite-v3.19.3/student_dao.c|//rt-thread/components/dfs/dfs_v1/filesystems/cromfs|//rt-thread/components/dfs/dfs_v1/filesystems/mqueue|//rt-thread/components/dfs/dfs_v1/filesystems/nfs|//rt-thread/components/dfs/dfs_v1/filesystems/ramfs|//rt-thread/components/dfs/dfs_v1/filesystems/romfs|//rt-thread/components/dfs/dfs_v1/filesystems/skeleton|//rt-thread/components/dfs/dfs_v2|//rt-thread/components/drivers/audio|//rt-thread/components/drivers/can|//rt-thread/components/drivers/clk|//rt-thread/components/drivers/core/dm.c|//rt-thread/components/drivers/core/driver.c|//rt-thread/components/drivers/core/platform.c|//rt-thread/components/drivers/core/platform_ofw.c|//rt-thread/components/drivers/cputime|//rt-thread/components/drivers/fdt|//rt-thread/components/drivers/hwcrypto|//rt-thread/components/drivers/hwtimer|//rt-thread/components/drivers/i2c|//rt-thread/components/drivers/ktime|//rt-thread/components/drivers/misc|//rt-thread/components/drivers/mtd/mtd_nand.c|//rt-thread/components/drivers/ofw|//rt-thread/components/drivers/phy|//rt-thread/components/drivers/pic|//rt-thread/components/drivers/pin/pin_dm.c|//rt-thread/components/drivers/pin/pin_ofw.c|//rt-thread/components/drivers/pinctrl|//rt-thread/components/drivers/pm|//rt-thread/components/drivers/rtc/alarm.c|//rt-thread/components/drivers/sensor|//rt-thread/components/drivers/serial/serial_dm.c|//rt-thread/components/drivers/serial/serial_tty.c|//rt-thread/components/drivers/serial/serial_v2.c|//rt-thread/components/drivers/spi/enc28j60.c|//rt-thread/components/drivers/spi/spi-bit-ops.c|//rt-thread/components/drivers/spi/spi_wifi_rw009.c|//rt-thread/components/drivers/touch|//rt-thread/components/drivers/usb|//rt-thread/components/drivers/virtio|//rt-thread/components/drivers/watchdog|//rt-thread/components/drivers/wlan|//rt-thread/components/fal/samples/porting/fal_flash_stm32f2_port.c|//rt-thread/components/legacy|//rt-thread/components/libc/compilers/armlibc|//rt-thread/components/libc/compilers/dlib|//rt-thread/components/libc/compilers/musl|//rt-thread/components/libc/compilers/picolibc|//rt-thread/components/libc/cplusplus|//rt-thread/components/libc/posix|//rt-thread/components/lwp|//rt-thread/components/mm|//rt-thread/components/mprotect|//rt-thread/components/net|//rt-thread/components/utilities|//rt-thread/components/vbus|//rt-thread/libcpu/aarch64|//rt-thread/libcpu/arc|//rt-thread/libcpu/arm/AT91SAM7S|//rt-thread/libcpu/arm/AT91SAM7X|//rt-thread/libcpu/arm/am335x|//rt-thread/libcpu/arm/arm926|//rt-thread/libcpu/arm/armv6|//rt-thread/libcpu/arm/common/atomic_arm.c|//rt-thread/libcpu/arm/common/divsi3.S|//rt-thread/libcpu/arm/cortex-a|//rt-thread/libcpu/arm/cortex-m0|//rt-thread/libcpu/arm/cortex-m23|//rt-thread/libcpu/arm/cortex-m3|//rt-thread/libcpu/arm/cortex-m33|//rt-thread/libcpu/arm/cortex-m4|//rt-thread/libcpu/arm/cortex-m7/context_iar.S|//rt-thread/libcpu/arm/cortex-m7/context_rvds.S|//rt-thread/libcpu/arm/cortex-m7/mpu.c|//rt-thread/libcpu/arm/cortex-m85|//rt-thread/libcpu/arm/cortex-r4|//rt-thread/libcpu/arm/cortex-r52|//rt-thread/libcpu/arm/dm36x|//rt-thread/libcpu/arm/lpc214x|//rt-thread/libcpu/arm/lpc24xx|//rt-thread/libcpu/arm/realview-a8-vmm|//rt-thread/libcpu/arm/s3c24x0|//rt-thread/libcpu/arm/s3c44b0|//rt-thread/libcpu/arm/sep4020|//rt-thread/libcpu/arm/zynqmp-r5|//rt-thread/libcpu/avr32|//rt-thread/libcpu/blackfin|//rt-thread/libcpu/c-sky|//rt-thread/libcpu/ia32|//rt-thread/libcpu/m16c|//rt-thread/libcpu/mips|//rt-thread/libcpu/nios|//rt-thread/libcpu/ppc|//rt-thread/libcpu/risc-v|//rt-thread/libcpu/rx|//rt-thread/libcpu/sim|//rt-thread/libcpu/sparc-v8|//rt-thread/libcpu/ti-dsp|//rt-thread/libcpu/unicore32|//rt-thread/libcpu/v850|//rt-thread/libcpu/xilinx|//rt-thread/src/cpu.c|//rt-thread/src/mem.c|//rt-thread/src/scheduler_mp.c|//rt-thread/src/signal.c|//rt-thread/src/slab.c|//rt-thread/tools" flags="VALUE_WORKSPACE_PATH|RESOLVED" kind="sourcePath" name=""/>
|
||||||
</sourceEntries>
|
</sourceEntries>
|
||||||
</configuration>
|
</configuration>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
<storageModule moduleId="org.eclipse.cdt.core.externalSettings" />
|
<storageModule moduleId="org.eclipse.cdt.core.externalSettings"/>
|
||||||
|
<storageModule moduleId="ilg.gnumcueclipse.managedbuild.packs"/>
|
||||||
</cconfiguration>
|
</cconfiguration>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
<storageModule moduleId="cdtBuildSystem" version="4.0.0">
|
<storageModule moduleId="cdtBuildSystem" version="4.0.0">
|
||||||
<project id="qemu-vexpress-a9.ilg.gnuarmeclipse.managedbuild.cross.target.elf.860020518" name="Executable" projectType="ilg.gnuarmeclipse.managedbuild.cross.target.elf" />
|
<project id="qemu-vexpress-a9.ilg.gnuarmeclipse.managedbuild.cross.target.elf.860020518" name="Executable" projectType="ilg.gnuarmeclipse.managedbuild.cross.target.elf"/>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
<storageModule moduleId="scannerConfiguration">
|
<storageModule moduleId="scannerConfiguration">
|
||||||
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId="" />
|
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
|
||||||
<scannerConfigBuildInfo instanceId="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094;ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094.;ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.1570350559;ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.input.992053063">
|
<scannerConfigBuildInfo instanceId="ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094;ilg.gnuarmeclipse.managedbuild.cross.config.elf.debug.553091094.;ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.1570350559;ilg.gnuarmeclipse.managedbuild.cross.tool.c.compiler.input.992053063">
|
||||||
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId="" />
|
<autodiscovery enabled="true" problemReportingEnabled="true" selectedProfileId=""/>
|
||||||
</scannerConfigBuildInfo>
|
</scannerConfigBuildInfo>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
<storageModule moduleId="org.eclipse.cdt.core.LanguageSettingsProviders" />
|
<storageModule moduleId="org.eclipse.cdt.core.LanguageSettingsProviders"/>
|
||||||
<storageModule moduleId="refreshScope" versionNumber="2">
|
<storageModule moduleId="refreshScope" versionNumber="2">
|
||||||
<configuration configurationName="Debug">
|
<configuration configurationName="Debug">
|
||||||
<resource resourceType="PROJECT" workspacePath="/828F" />
|
<resource resourceType="PROJECT" workspacePath="/project"/>
|
||||||
</configuration>
|
</configuration>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
<storageModule moduleId="org.eclipse.cdt.make.core.buildtargets" />
|
<storageModule moduleId="org.eclipse.cdt.make.core.buildtargets"/>
|
||||||
<storageModule moduleId="org.eclipse.cdt.internal.ui.text.commentOwnerProjectMappings">
|
<storageModule moduleId="org.eclipse.cdt.internal.ui.text.commentOwnerProjectMappings">
|
||||||
<doc-comment-owner id="org.eclipse.cdt.ui.doxygen">
|
<doc-comment-owner id="org.eclipse.cdt.ui.doxygen">
|
||||||
<path value="" />
|
<path value=""/>
|
||||||
</doc-comment-owner>
|
</doc-comment-owner>
|
||||||
</storageModule>
|
</storageModule>
|
||||||
</cproject>
|
</cproject>
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<projectDescription>
|
<projectDescription>
|
||||||
<name>828F</name>
|
<name>project</name>
|
||||||
<comment />
|
<comment />
|
||||||
<projects>
|
<projects>
|
||||||
</projects>
|
</projects>
|
||||||
|
|||||||
Binary file not shown.
@@ -5,7 +5,7 @@
|
|||||||
<provider copy-of="extension" id="org.eclipse.cdt.ui.UserLanguageSettingsProvider"/>
|
<provider copy-of="extension" id="org.eclipse.cdt.ui.UserLanguageSettingsProvider"/>
|
||||||
<provider-reference id="org.eclipse.cdt.core.ReferencedProjectsLanguageSettingsProvider" ref="shared-provider"/>
|
<provider-reference id="org.eclipse.cdt.core.ReferencedProjectsLanguageSettingsProvider" ref="shared-provider"/>
|
||||||
<provider-reference id="org.eclipse.cdt.managedbuilder.core.MBSLanguageSettingsProvider" ref="shared-provider"/>
|
<provider-reference id="org.eclipse.cdt.managedbuilder.core.MBSLanguageSettingsProvider" ref="shared-provider"/>
|
||||||
<provider class="org.eclipse.cdt.managedbuilder.language.settings.providers.GCCBuiltinSpecsDetector" console="false" env-hash="-1124315701215259588" id="ilg.gnuarmeclipse.managedbuild.cross.GCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT ARM Cross GCC Built-in Compiler Settings " parameter="${COMMAND} ${FLAGS} ${cross_toolchain_flags} -E -P -v -dD "${INPUTS}"" prefer-non-shared="true">
|
<provider class="org.eclipse.cdt.managedbuilder.language.settings.providers.GCCBuiltinSpecsDetector" console="false" env-hash="-1161191500764276022" id="ilg.gnuarmeclipse.managedbuild.cross.GCCBuiltinSpecsDetector" keep-relative-paths="false" name="CDT ARM Cross GCC Built-in Compiler Settings " parameter="${COMMAND} ${FLAGS} ${cross_toolchain_flags} -E -P -v -dD "${INPUTS}"" prefer-non-shared="true">
|
||||||
<language-scope id="org.eclipse.cdt.core.gcc"/>
|
<language-scope id="org.eclipse.cdt.core.gcc"/>
|
||||||
<language-scope id="org.eclipse.cdt.core.g++"/>
|
<language-scope id="org.eclipse.cdt.core.g++"/>
|
||||||
</provider>
|
</provider>
|
||||||
|
|||||||
@@ -0,0 +1,128 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2006-2021, RT-Thread Development Team
|
||||||
|
*
|
||||||
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
|
*
|
||||||
|
* Change Logs:
|
||||||
|
* Date Author Notes
|
||||||
|
* 2025-11-22 Administrator the first version
|
||||||
|
*//*
|
||||||
|
* Copyright (c) 2006-2021, RT-Thread Development Team
|
||||||
|
*
|
||||||
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
|
*
|
||||||
|
* Change Logs:
|
||||||
|
* Date Author Notes
|
||||||
|
* 2025-11-22 Administrator the first version
|
||||||
|
*/
|
||||||
|
#include <rtthread.h>
|
||||||
|
#include <rtdevice.h>
|
||||||
|
#include "fal_cfg.h"
|
||||||
|
#include "spi_flash.h"
|
||||||
|
#include "spi_flash_sfud.h"
|
||||||
|
#include "drv_qspi.h"
|
||||||
|
#include "dfs_fs.h"
|
||||||
|
#include "fal.h"
|
||||||
|
|
||||||
|
/* 添加 DEBUG 头文件 */
|
||||||
|
#include <rtdbg.h>
|
||||||
|
|
||||||
|
char w25qxx_read_status_register2(struct rt_qspi_device *device)
|
||||||
|
{
|
||||||
|
/* 0x35 read status register2 */
|
||||||
|
char instruction = 0x35, status;
|
||||||
|
rt_qspi_send_then_recv(device, &instruction, 1, &status, 1);
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
void w25qxx_write_enable(struct rt_qspi_device *device)
|
||||||
|
{
|
||||||
|
/* 0x06 write enable */
|
||||||
|
char instruction = 0x06;
|
||||||
|
rt_qspi_send(device, &instruction, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void w25qxx_enter_qspi_mode(struct rt_qspi_device *device)
|
||||||
|
{
|
||||||
|
char status = 0;
|
||||||
|
/* 0x38 enter qspi mode */
|
||||||
|
char instruction = 0x38;
|
||||||
|
char write_status2_buf[2] = {0};
|
||||||
|
/* 0x31 write status register2 */
|
||||||
|
write_status2_buf[0] = 0x31;
|
||||||
|
status = w25qxx_read_status_register2(device);
|
||||||
|
if (!(status & 0x02))
|
||||||
|
{
|
||||||
|
status |= 1 << 1;
|
||||||
|
w25qxx_write_enable(device);
|
||||||
|
write_status2_buf[1] = status;
|
||||||
|
rt_qspi_send(device, &write_status2_buf, 2);
|
||||||
|
rt_qspi_send(device, &instruction, 1);
|
||||||
|
LOG_D("flash already enter qspi mode");
|
||||||
|
rt_thread_mdelay(10);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int spi_flash_init(void)
|
||||||
|
{
|
||||||
|
rt_err_t ret = stm32_qspi_bus_attach_device("qspi1", "qspi10", RT_NULL, 4, w25qxx_enter_qspi_mode, RT_NULL);
|
||||||
|
if (ret != RT_EOK)
|
||||||
|
{
|
||||||
|
LOG_E("qspi attach device failed\n");
|
||||||
|
return -RT_ERROR;
|
||||||
|
}
|
||||||
|
/* init W25Q256 */
|
||||||
|
// spi_flash_dev_name 需要用配置文件内的,spi_dev_name实际是SPI挂在参数
|
||||||
|
if(rt_sfud_flash_probe(FAL_USING_NOR_FLASH_DEV_NAME, "qspi10") == RT_NULL)
|
||||||
|
{
|
||||||
|
LOG_E("rt sfud flash error");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
LOG_I("SFUD flash '%s' probed successfully.", FAL_USING_NOR_FLASH_DEV_NAME);
|
||||||
|
/* 初始化 fal */
|
||||||
|
int fal_ = fal_init();
|
||||||
|
if (fal_ > 0)
|
||||||
|
{
|
||||||
|
LOG_I("FAL Number of partitions = %d",fal_);
|
||||||
|
}else{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
/* 创建 MTD 块设备 */
|
||||||
|
if (fal_mtd_nor_device_create("sysdata") == RT_NULL)
|
||||||
|
{
|
||||||
|
LOG_E("Failed to create MTD device for sysdata!");
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
LOG_I("MTD device 'sysdata' created.");
|
||||||
|
return RT_EOK;
|
||||||
|
}
|
||||||
|
INIT_DEVICE_EXPORT(spi_flash_init);
|
||||||
|
|
||||||
|
int qspi_fal(void)
|
||||||
|
{
|
||||||
|
LOG_I("Create file path /sys");
|
||||||
|
mkdir("/sys", 0777);
|
||||||
|
|
||||||
|
/* 挂载 littlefs */
|
||||||
|
if (dfs_mount("sysdata", "/sys", "lfs", 0, NULL) == RT_EOK)
|
||||||
|
{
|
||||||
|
LOG_I("Filesystem initialized!");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
LOG_E("Format memory sysdata");
|
||||||
|
/* 格式化文件系统 */
|
||||||
|
dfs_mkfs("lfs", "sysdata");
|
||||||
|
/* 挂载 littlefs */
|
||||||
|
if (dfs_mount("sysdata", "/sys", "lfs", 0, NULL) == RT_EOK)
|
||||||
|
{
|
||||||
|
LOG_I("Filesystem initialized!");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
LOG_E("Failed to initialize filesystem!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return RT_EOK;
|
||||||
|
}
|
||||||
|
INIT_APP_EXPORT(qspi_fal);
|
||||||
@@ -4,7 +4,7 @@
|
|||||||
#include"drv_common.h"
|
#include"drv_common.h"
|
||||||
#include "RUN_LED.h"
|
#include "RUN_LED.h"
|
||||||
|
|
||||||
#define LED_PIN GET_PIN(B,0)
|
#define LED_PIN GET_PIN(B,1)
|
||||||
|
|
||||||
/* 线程 1 的入口函数 */
|
/* 线程 1 的入口函数 */
|
||||||
void RUN_LED(void *parameter)
|
void RUN_LED(void *parameter)
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ void sd_mount(void *parameter)
|
|||||||
{
|
{
|
||||||
if (rt_device_find("sd") != RT_NULL)
|
if (rt_device_find("sd") != RT_NULL)
|
||||||
{
|
{
|
||||||
|
LOG_I("Create file path /sddisk");
|
||||||
mkdir("/sddisk", 0777);
|
mkdir("/sddisk", 0777);
|
||||||
if (dfs_mount("sd", "/sddisk", "elm", 0, NULL) == RT_EOK)
|
if (dfs_mount("sd", "/sddisk", "elm", 0, NULL) == RT_EOK)
|
||||||
{
|
{
|
||||||
@@ -54,7 +55,6 @@ void sd_mount(void *parameter)
|
|||||||
int stm32_sdcard_mount(void)
|
int stm32_sdcard_mount(void)
|
||||||
{
|
{
|
||||||
rt_thread_t tid;
|
rt_thread_t tid;
|
||||||
rt_thread_mdelay(1000);
|
|
||||||
// 删除旧的信号量(如果存在)
|
// 删除旧的信号量(如果存在)
|
||||||
if (mount_sem != RT_NULL)
|
if (mount_sem != RT_NULL)
|
||||||
{
|
{
|
||||||
@@ -72,7 +72,7 @@ int stm32_sdcard_mount(void)
|
|||||||
tid = rt_thread_create("sd_mount",
|
tid = rt_thread_create("sd_mount",
|
||||||
sd_mount,
|
sd_mount,
|
||||||
RT_NULL,
|
RT_NULL,
|
||||||
1024*6, // 避免溢出
|
1024*2, // 避免溢出
|
||||||
RT_THREAD_PRIORITY_MAX - 2,
|
RT_THREAD_PRIORITY_MAX - 2,
|
||||||
20);
|
20);
|
||||||
if (tid != RT_NULL)
|
if (tid != RT_NULL)
|
||||||
|
|||||||
@@ -28,11 +28,11 @@ int init_tmpfs_root(void)
|
|||||||
if (mkdir("/run", 0777) == 0) {
|
if (mkdir("/run", 0777) == 0) {
|
||||||
LOG_I("Created /run directory");
|
LOG_I("Created /run directory");
|
||||||
} else {
|
} else {
|
||||||
LOG_E("mkdir failed, errno=%d", errno);
|
LOG_E("mkdir failed, errno = %d", errno);
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 在应用初始化阶段运行(确保系统已就绪) */
|
/* 在应用初始化阶段运行(确保系统已就绪) */
|
||||||
INIT_APP_EXPORT(init_tmpfs_root);
|
INIT_DEVICE_EXPORT(init_tmpfs_root);
|
||||||
@@ -0,0 +1,30 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2006-2021, RT-Thread Development Team
|
||||||
|
*
|
||||||
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
|
*
|
||||||
|
* Change Logs:
|
||||||
|
* Date Author Notes
|
||||||
|
* 2025-11-22 Administrator the first version
|
||||||
|
*/
|
||||||
|
#ifndef _FAL_CFG_H_
|
||||||
|
#define _FAL_CFG_H_
|
||||||
|
|
||||||
|
#include <rtconfig.h>
|
||||||
|
#include <fal.h>
|
||||||
|
|
||||||
|
extern struct fal_flash_dev nor_flash0;
|
||||||
|
|
||||||
|
/* flash device table */
|
||||||
|
#define FAL_FLASH_DEV_TABLE \
|
||||||
|
{ \
|
||||||
|
&nor_flash0, \
|
||||||
|
}
|
||||||
|
|
||||||
|
/* 分区表:根据你的需求划分 */
|
||||||
|
#define FAL_PART_TABLE \
|
||||||
|
{ \
|
||||||
|
{FAL_PART_MAGIC_WORD, "sysdata","W25Q128", 0, 16 * 1024 * 1024, 0 }, \
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif /* _FAL_CFG_H_ */
|
||||||
+2
-2
@@ -1,8 +1,8 @@
|
|||||||
[PreviousLibFiles]
|
[PreviousLibFiles]
|
||||||
LibFiles=Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_fmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nor.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nand.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sdram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_bus.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_rcc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_crs.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_system.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_utils.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_flash.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_flash_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_gpio.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_gpio_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_gpio.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_hsem.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_hsem.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_dma.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_dma_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_dma.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_dmamux.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_mdma.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_pwr.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_pwr_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_pwr.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_def.h;Drivers\STM32H7xx_HAL_Driver\Inc\Legacy\stm32_hal_legacy.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_i2c.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_i2c_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_exti.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_exti.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_sdmmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sd.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_delayblock.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sd_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_mmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_mmc_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_tim.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_tim_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_uart.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_usart.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_lpuart.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_uart_ex.h;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_cortex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_fmc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nor.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sram.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nand.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sdram.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_gpio.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_hsem.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mdma.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_exti.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_sdmmc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_delayblock.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart_ex.c;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_fmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nor.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nand.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sdram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_bus.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_rcc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_crs.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_system.h;DLine truncated
|
LibFiles=Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_fmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nor.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nand.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sdram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_bus.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_rcc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_crs.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_system.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_utils.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_flash.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_flash_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_gpio.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_gpio_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_gpio.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_hsem.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_hsem.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_dma.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_dma_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_dma.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_dmamux.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_mdma.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_pwr.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_pwr_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_pwr.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_def.h;Drivers\STM32H7xx_HAL_Driver\Inc\Legacy\stm32_hal_legacy.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_i2c.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_i2c_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_exti.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_exti.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_qspi.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_delayblock.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_sdmmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sd.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sd_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_mmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_mmc_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_tim.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_tim_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_uart.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_usart.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_lpuart.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_uart_ex.h;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_cortex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_fmc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nor.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sram.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nand.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sdram.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_gpio.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_hsem.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mdma.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_exti.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_qspi.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_delayblock.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_sdmmc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim_ex.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart.c;Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart_ex.c;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_cortex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_fmc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nor.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_nand.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_sdram.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_hal_rcc_ex.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_bus.h;Drivers\STM32H7xx_HAL_Driver\Inc\stm32h7xx_ll_rcc.h;Line truncated
|
||||||
|
|
||||||
[PreviousUsedIarFiles]
|
[PreviousUsedIarFiles]
|
||||||
SourceFiles=..\Src\main.c;..\Src\stm32h7xx_it.c;..\Src\stm32h7xx_hal_msp.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_cortex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_fmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nor.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nand.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sdram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_gpio.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_hsem.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mdma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_exti.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_sdmmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_delayblock.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart_ex.c;..\Drivers\CMSIS\Device\ST\STM32H7xx\Source\Templates\system_stm32h7xx.c;..\\Src\system_stm32h7xx.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_cortex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_fmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nor.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nand.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sdram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_gpio.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_hsem.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mdma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_exti.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_sdmmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_delayblock.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart_ex.c;..\Drivers\CMSIS\Device\ST\STM32H7xx\Source\Templates\system_stm32h7xx.c;..\\Src\system_stm32h7xx.c;;;
|
SourceFiles=..\Src\main.c;..\Src\stm32h7xx_it.c;..\Src\stm32h7xx_hal_msp.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_cortex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_fmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nor.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nand.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sdram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_gpio.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_hsem.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mdma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_exti.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_qspi.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_delayblock.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_sdmmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart_ex.c;..\Drivers\CMSIS\Device\ST\STM32H7xx\Source\Templates\system_stm32h7xx.c;..\\Src\system_stm32h7xx.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_cortex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_fmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nor.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_nand.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sdram.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_rcc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_flash_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_gpio.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_hsem.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_dma_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mdma.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_pwr_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_i2c_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_exti.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_qspi.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_delayblock.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_ll_sdmmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_sd_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_mmc_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_tim_ex.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart.c;..\Drivers\STM32H7xx_HAL_Driver\Src\stm32h7xx_hal_uart_ex.c;..\Drivers\CMSIS\Device\ST\STM32H7xx\Source\Templates\system_stm32h7xx.c;..\\Src\system_stm32h7xx.c;;;
|
||||||
HeaderPath=..\Drivers\STM32H7xx_HAL_Driver\Inc;..\Drivers\STM32H7xx_HAL_Driver\Inc\Legacy;..\Drivers\CMSIS\Device\ST\STM32H7xx\Include;..\Drivers\CMSIS\Include;..\Inc;
|
HeaderPath=..\Drivers\STM32H7xx_HAL_Driver\Inc;..\Drivers\STM32H7xx_HAL_Driver\Inc\Legacy;..\Drivers\CMSIS\Device\ST\STM32H7xx\Include;..\Drivers\CMSIS\Include;..\Inc;
|
||||||
CDefines=USE_PWR_LDO_SUPPLY;USE_HAL_DRIVER;STM32H743xx;USE_HAL_DRIVER;USE_HAL_DRIVER;
|
CDefines=USE_PWR_LDO_SUPPLY;USE_HAL_DRIVER;STM32H743xx;USE_HAL_DRIVER;USE_HAL_DRIVER;
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,747 @@
|
|||||||
|
/**
|
||||||
|
******************************************************************************
|
||||||
|
* @file stm32h7xx_hal_qspi.h
|
||||||
|
* @author MCD Application Team
|
||||||
|
* @brief Header file of QSPI HAL module.
|
||||||
|
******************************************************************************
|
||||||
|
* @attention
|
||||||
|
*
|
||||||
|
* Copyright (c) 2017 STMicroelectronics.
|
||||||
|
* All rights reserved.
|
||||||
|
*
|
||||||
|
* This software is licensed under terms that can be found in the LICENSE file
|
||||||
|
* in the root directory of this software component.
|
||||||
|
* If no LICENSE file comes with this software, it is provided AS-IS.
|
||||||
|
*
|
||||||
|
******************************************************************************
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Define to prevent recursive inclusion -------------------------------------*/
|
||||||
|
#ifndef STM32H7xx_HAL_QSPI_H
|
||||||
|
#define STM32H7xx_HAL_QSPI_H
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C" {
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* Includes ------------------------------------------------------------------*/
|
||||||
|
#include "stm32h7xx_hal_def.h"
|
||||||
|
#if defined (DLYB_QUADSPI)
|
||||||
|
#include "stm32h7xx_ll_delayblock.h"
|
||||||
|
#endif /* DLYB_QUADSPI */
|
||||||
|
|
||||||
|
#if defined(QUADSPI)
|
||||||
|
|
||||||
|
/** @addtogroup STM32H7xx_HAL_Driver
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @addtogroup QSPI
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Exported types ------------------------------------------------------------*/
|
||||||
|
/** @defgroup QSPI_Exported_Types QSPI Exported Types
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QSPI Init structure definition
|
||||||
|
*/
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
uint32_t ClockPrescaler; /* Specifies the prescaler factor for generating clock based on the AHB clock.
|
||||||
|
This parameter can be a number between 0 and 255 */
|
||||||
|
uint32_t FifoThreshold; /* Specifies the threshold number of bytes in the FIFO (used only in indirect mode)
|
||||||
|
This parameter can be a value between 1 and 32 */
|
||||||
|
uint32_t SampleShifting; /* Specifies the Sample Shift. The data is sampled 1/2 clock cycle delay later to
|
||||||
|
take in account external signal delays. (It should be QSPI_SAMPLE_SHIFTING_NONE in DDR mode)
|
||||||
|
This parameter can be a value of @ref QSPI_SampleShifting */
|
||||||
|
uint32_t FlashSize; /* Specifies the Flash Size. FlashSize+1 is effectively the number of address bits
|
||||||
|
required to address the flash memory. The flash capacity can be up to 4GB
|
||||||
|
(addressed using 32 bits) in indirect mode, but the addressable space in
|
||||||
|
memory-mapped mode is limited to 256MB
|
||||||
|
This parameter can be a number between 0 and 31 */
|
||||||
|
uint32_t ChipSelectHighTime; /* Specifies the Chip Select High Time. ChipSelectHighTime+1 defines the minimum number
|
||||||
|
of clock cycles which the chip select must remain high between commands.
|
||||||
|
This parameter can be a value of @ref QSPI_ChipSelectHighTime */
|
||||||
|
uint32_t ClockMode; /* Specifies the Clock Mode. It indicates the level that clock takes between commands.
|
||||||
|
This parameter can be a value of @ref QSPI_ClockMode */
|
||||||
|
uint32_t FlashID; /* Specifies the Flash which will be used,
|
||||||
|
This parameter can be a value of @ref QSPI_Flash_Select */
|
||||||
|
uint32_t DualFlash; /* Specifies the Dual Flash Mode State
|
||||||
|
This parameter can be a value of @ref QSPI_DualFlash_Mode */
|
||||||
|
}QSPI_InitTypeDef;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief HAL QSPI State structures definition
|
||||||
|
*/
|
||||||
|
typedef enum
|
||||||
|
{
|
||||||
|
HAL_QSPI_STATE_RESET = 0x00U, /*!< Peripheral not initialized */
|
||||||
|
HAL_QSPI_STATE_READY = 0x01U, /*!< Peripheral initialized and ready for use */
|
||||||
|
HAL_QSPI_STATE_BUSY = 0x02U, /*!< Peripheral in indirect mode and busy */
|
||||||
|
HAL_QSPI_STATE_BUSY_INDIRECT_TX = 0x12U, /*!< Peripheral in indirect mode with transmission ongoing */
|
||||||
|
HAL_QSPI_STATE_BUSY_INDIRECT_RX = 0x22U, /*!< Peripheral in indirect mode with reception ongoing */
|
||||||
|
HAL_QSPI_STATE_BUSY_AUTO_POLLING = 0x42U, /*!< Peripheral in auto polling mode ongoing */
|
||||||
|
HAL_QSPI_STATE_BUSY_MEM_MAPPED = 0x82U, /*!< Peripheral in memory mapped mode ongoing */
|
||||||
|
HAL_QSPI_STATE_ABORT = 0x08U, /*!< Peripheral with abort request ongoing */
|
||||||
|
HAL_QSPI_STATE_ERROR = 0x04U /*!< Peripheral in error */
|
||||||
|
}HAL_QSPI_StateTypeDef;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QSPI Handle Structure definition
|
||||||
|
*/
|
||||||
|
#if (USE_HAL_QSPI_REGISTER_CALLBACKS == 1)
|
||||||
|
typedef struct __QSPI_HandleTypeDef
|
||||||
|
#else
|
||||||
|
typedef struct
|
||||||
|
#endif
|
||||||
|
{
|
||||||
|
QUADSPI_TypeDef *Instance; /* QSPI registers base address */
|
||||||
|
QSPI_InitTypeDef Init; /* QSPI communication parameters */
|
||||||
|
uint8_t *pTxBuffPtr; /* Pointer to QSPI Tx transfer Buffer */
|
||||||
|
__IO uint32_t TxXferSize; /* QSPI Tx Transfer size */
|
||||||
|
__IO uint32_t TxXferCount; /* QSPI Tx Transfer Counter */
|
||||||
|
uint8_t *pRxBuffPtr; /* Pointer to QSPI Rx transfer Buffer */
|
||||||
|
__IO uint32_t RxXferSize; /* QSPI Rx Transfer size */
|
||||||
|
__IO uint32_t RxXferCount; /* QSPI Rx Transfer Counter */
|
||||||
|
MDMA_HandleTypeDef *hmdma; /* QSPI Rx/Tx MDMA Handle parameters */
|
||||||
|
__IO HAL_LockTypeDef Lock; /* Locking object */
|
||||||
|
__IO HAL_QSPI_StateTypeDef State; /* QSPI communication state */
|
||||||
|
__IO uint32_t ErrorCode; /* QSPI Error code */
|
||||||
|
uint32_t Timeout; /* Timeout for the QSPI memory access */
|
||||||
|
#if (USE_HAL_QSPI_REGISTER_CALLBACKS == 1)
|
||||||
|
void (* ErrorCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* AbortCpltCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* FifoThresholdCallback)(struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* CmdCpltCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* RxCpltCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* TxCpltCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* StatusMatchCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* TimeOutCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
|
||||||
|
void (* MspInitCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
void (* MspDeInitCallback) (struct __QSPI_HandleTypeDef *hqspi);
|
||||||
|
#endif
|
||||||
|
}QSPI_HandleTypeDef;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QSPI Command structure definition
|
||||||
|
*/
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
uint32_t Instruction; /* Specifies the Instruction to be sent
|
||||||
|
This parameter can be a value (8-bit) between 0x00 and 0xFF */
|
||||||
|
uint32_t Address; /* Specifies the Address to be sent (Size from 1 to 4 bytes according AddressSize)
|
||||||
|
This parameter can be a value (32-bits) between 0x0 and 0xFFFFFFFF */
|
||||||
|
uint32_t AlternateBytes; /* Specifies the Alternate Bytes to be sent (Size from 1 to 4 bytes according AlternateBytesSize)
|
||||||
|
This parameter can be a value (32-bits) between 0x0 and 0xFFFFFFFF */
|
||||||
|
uint32_t AddressSize; /* Specifies the Address Size
|
||||||
|
This parameter can be a value of @ref QSPI_AddressSize */
|
||||||
|
uint32_t AlternateBytesSize; /* Specifies the Alternate Bytes Size
|
||||||
|
This parameter can be a value of @ref QSPI_AlternateBytesSize */
|
||||||
|
uint32_t DummyCycles; /* Specifies the Number of Dummy Cycles.
|
||||||
|
This parameter can be a number between 0 and 31 */
|
||||||
|
uint32_t InstructionMode; /* Specifies the Instruction Mode
|
||||||
|
This parameter can be a value of @ref QSPI_InstructionMode */
|
||||||
|
uint32_t AddressMode; /* Specifies the Address Mode
|
||||||
|
This parameter can be a value of @ref QSPI_AddressMode */
|
||||||
|
uint32_t AlternateByteMode; /* Specifies the Alternate Bytes Mode
|
||||||
|
This parameter can be a value of @ref QSPI_AlternateBytesMode */
|
||||||
|
uint32_t DataMode; /* Specifies the Data Mode (used for dummy cycles and data phases)
|
||||||
|
This parameter can be a value of @ref QSPI_DataMode */
|
||||||
|
uint32_t NbData; /* Specifies the number of data to transfer. (This is the number of bytes)
|
||||||
|
This parameter can be any value between 0 and 0xFFFFFFFF (0 means undefined length
|
||||||
|
until end of memory)*/
|
||||||
|
uint32_t DdrMode; /* Specifies the double data rate mode for address, alternate byte and data phase
|
||||||
|
This parameter can be a value of @ref QSPI_DdrMode */
|
||||||
|
uint32_t DdrHoldHalfCycle; /* Specifies if the DDR hold is enabled. When enabled it delays the data
|
||||||
|
output by one half of system clock in DDR mode.
|
||||||
|
This parameter can be a value of @ref QSPI_DdrHoldHalfCycle */
|
||||||
|
uint32_t SIOOMode; /* Specifies the send instruction only once mode
|
||||||
|
This parameter can be a value of @ref QSPI_SIOOMode */
|
||||||
|
}QSPI_CommandTypeDef;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QSPI Auto Polling mode configuration structure definition
|
||||||
|
*/
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
uint32_t Match; /* Specifies the value to be compared with the masked status register to get a match.
|
||||||
|
This parameter can be any value between 0 and 0xFFFFFFFF */
|
||||||
|
uint32_t Mask; /* Specifies the mask to be applied to the status bytes received.
|
||||||
|
This parameter can be any value between 0 and 0xFFFFFFFF */
|
||||||
|
uint32_t Interval; /* Specifies the number of clock cycles between two read during automatic polling phases.
|
||||||
|
This parameter can be any value between 0 and 0xFFFF */
|
||||||
|
uint32_t StatusBytesSize; /* Specifies the size of the status bytes received.
|
||||||
|
This parameter can be any value between 1 and 4 */
|
||||||
|
uint32_t MatchMode; /* Specifies the method used for determining a match.
|
||||||
|
This parameter can be a value of @ref QSPI_MatchMode */
|
||||||
|
uint32_t AutomaticStop; /* Specifies if automatic polling is stopped after a match.
|
||||||
|
This parameter can be a value of @ref QSPI_AutomaticStop */
|
||||||
|
}QSPI_AutoPollingTypeDef;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QSPI Memory Mapped mode configuration structure definition
|
||||||
|
*/
|
||||||
|
typedef struct
|
||||||
|
{
|
||||||
|
uint32_t TimeOutPeriod; /* Specifies the number of clock to wait when the FIFO is full before to release the chip select.
|
||||||
|
This parameter can be any value between 0 and 0xFFFF */
|
||||||
|
uint32_t TimeOutActivation; /* Specifies if the timeout counter is enabled to release the chip select.
|
||||||
|
This parameter can be a value of @ref QSPI_TimeOutActivation */
|
||||||
|
}QSPI_MemoryMappedTypeDef;
|
||||||
|
|
||||||
|
#if (USE_HAL_QSPI_REGISTER_CALLBACKS == 1)
|
||||||
|
/**
|
||||||
|
* @brief HAL QSPI Callback ID enumeration definition
|
||||||
|
*/
|
||||||
|
typedef enum
|
||||||
|
{
|
||||||
|
HAL_QSPI_ERROR_CB_ID = 0x00U, /*!< QSPI Error Callback ID */
|
||||||
|
HAL_QSPI_ABORT_CB_ID = 0x01U, /*!< QSPI Abort Callback ID */
|
||||||
|
HAL_QSPI_FIFO_THRESHOLD_CB_ID = 0x02U, /*!< QSPI FIFO Threshold Callback ID */
|
||||||
|
HAL_QSPI_CMD_CPLT_CB_ID = 0x03U, /*!< QSPI Command Complete Callback ID */
|
||||||
|
HAL_QSPI_RX_CPLT_CB_ID = 0x04U, /*!< QSPI Rx Complete Callback ID */
|
||||||
|
HAL_QSPI_TX_CPLT_CB_ID = 0x05U, /*!< QSPI Tx Complete Callback ID */
|
||||||
|
HAL_QSPI_STATUS_MATCH_CB_ID = 0x08U, /*!< QSPI Status Match Callback ID */
|
||||||
|
HAL_QSPI_TIMEOUT_CB_ID = 0x09U, /*!< QSPI Timeout Callback ID */
|
||||||
|
|
||||||
|
HAL_QSPI_MSP_INIT_CB_ID = 0x0AU, /*!< QSPI MspInit Callback ID */
|
||||||
|
HAL_QSPI_MSP_DEINIT_CB_ID = 0x0B0 /*!< QSPI MspDeInit Callback ID */
|
||||||
|
}HAL_QSPI_CallbackIDTypeDef;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief HAL QSPI Callback pointer definition
|
||||||
|
*/
|
||||||
|
typedef void (*pQSPI_CallbackTypeDef)(QSPI_HandleTypeDef *hqspi);
|
||||||
|
#endif
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Exported constants --------------------------------------------------------*/
|
||||||
|
/** @defgroup QSPI_Exported_Constants QSPI Exported Constants
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_ErrorCode QSPI Error Code
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define HAL_QSPI_ERROR_NONE 0x00000000U /*!< No error */
|
||||||
|
#define HAL_QSPI_ERROR_TIMEOUT 0x00000001U /*!< Timeout error */
|
||||||
|
#define HAL_QSPI_ERROR_TRANSFER 0x00000002U /*!< Transfer error */
|
||||||
|
#define HAL_QSPI_ERROR_DMA 0x00000004U /*!< DMA transfer error */
|
||||||
|
#define HAL_QSPI_ERROR_INVALID_PARAM 0x00000008U /*!< Invalid parameters error */
|
||||||
|
#if (USE_HAL_QSPI_REGISTER_CALLBACKS == 1)
|
||||||
|
#define HAL_QSPI_ERROR_INVALID_CALLBACK 0x00000010U /*!< Invalid callback error */
|
||||||
|
#endif
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_SampleShifting QSPI Sample Shifting
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_SAMPLE_SHIFTING_NONE 0x00000000U /*!<No clock cycle shift to sample data*/
|
||||||
|
#define QSPI_SAMPLE_SHIFTING_HALFCYCLE ((uint32_t)QUADSPI_CR_SSHIFT) /*!<1/2 clock cycle shift to sample data*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_ChipSelectHighTime QSPI ChipSelect High Time
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_1_CYCLE 0x00000000U /*!<nCS stay high for at least 1 clock cycle between commands*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_2_CYCLE ((uint32_t)QUADSPI_DCR_CSHT_0) /*!<nCS stay high for at least 2 clock cycles between commands*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_3_CYCLE ((uint32_t)QUADSPI_DCR_CSHT_1) /*!<nCS stay high for at least 3 clock cycles between commands*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_4_CYCLE ((uint32_t)QUADSPI_DCR_CSHT_0 | QUADSPI_DCR_CSHT_1) /*!<nCS stay high for at least 4 clock cycles between commands*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_5_CYCLE ((uint32_t)QUADSPI_DCR_CSHT_2) /*!<nCS stay high for at least 5 clock cycles between commands*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_6_CYCLE ((uint32_t)QUADSPI_DCR_CSHT_2 | QUADSPI_DCR_CSHT_0) /*!<nCS stay high for at least 6 clock cycles between commands*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_7_CYCLE ((uint32_t)QUADSPI_DCR_CSHT_2 | QUADSPI_DCR_CSHT_1) /*!<nCS stay high for at least 7 clock cycles between commands*/
|
||||||
|
#define QSPI_CS_HIGH_TIME_8_CYCLE ((uint32_t)QUADSPI_DCR_CSHT) /*!<nCS stay high for at least 8 clock cycles between commands*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_ClockMode QSPI Clock Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_CLOCK_MODE_0 0x00000000U /*!<Clk stays low while nCS is released*/
|
||||||
|
#define QSPI_CLOCK_MODE_3 ((uint32_t)QUADSPI_DCR_CKMODE) /*!<Clk goes high while nCS is released*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_Flash_Select QSPI Flash Select
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_FLASH_ID_1 0x00000000U /*!<FLASH 1 selected*/
|
||||||
|
#define QSPI_FLASH_ID_2 ((uint32_t)QUADSPI_CR_FSEL) /*!<FLASH 2 selected*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_DualFlash_Mode QSPI Dual Flash Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_DUALFLASH_ENABLE ((uint32_t)QUADSPI_CR_DFM) /*!<Dual-flash mode enabled*/
|
||||||
|
#define QSPI_DUALFLASH_DISABLE 0x00000000U /*!<Dual-flash mode disabled*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_AddressSize QSPI Address Size
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_ADDRESS_8_BITS 0x00000000U /*!<8-bit address*/
|
||||||
|
#define QSPI_ADDRESS_16_BITS ((uint32_t)QUADSPI_CCR_ADSIZE_0) /*!<16-bit address*/
|
||||||
|
#define QSPI_ADDRESS_24_BITS ((uint32_t)QUADSPI_CCR_ADSIZE_1) /*!<24-bit address*/
|
||||||
|
#define QSPI_ADDRESS_32_BITS ((uint32_t)QUADSPI_CCR_ADSIZE) /*!<32-bit address*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_AlternateBytesSize QSPI Alternate Bytes Size
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_8_BITS 0x00000000U /*!<8-bit alternate bytes*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_16_BITS ((uint32_t)QUADSPI_CCR_ABSIZE_0) /*!<16-bit alternate bytes*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_24_BITS ((uint32_t)QUADSPI_CCR_ABSIZE_1) /*!<24-bit alternate bytes*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_32_BITS ((uint32_t)QUADSPI_CCR_ABSIZE) /*!<32-bit alternate bytes*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_InstructionMode QSPI Instruction Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_INSTRUCTION_NONE 0x00000000U /*!<No instruction*/
|
||||||
|
#define QSPI_INSTRUCTION_1_LINE ((uint32_t)QUADSPI_CCR_IMODE_0) /*!<Instruction on a single line*/
|
||||||
|
#define QSPI_INSTRUCTION_2_LINES ((uint32_t)QUADSPI_CCR_IMODE_1) /*!<Instruction on two lines*/
|
||||||
|
#define QSPI_INSTRUCTION_4_LINES ((uint32_t)QUADSPI_CCR_IMODE) /*!<Instruction on four lines*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_AddressMode QSPI Address Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_ADDRESS_NONE 0x00000000U /*!<No address*/
|
||||||
|
#define QSPI_ADDRESS_1_LINE ((uint32_t)QUADSPI_CCR_ADMODE_0) /*!<Address on a single line*/
|
||||||
|
#define QSPI_ADDRESS_2_LINES ((uint32_t)QUADSPI_CCR_ADMODE_1) /*!<Address on two lines*/
|
||||||
|
#define QSPI_ADDRESS_4_LINES ((uint32_t)QUADSPI_CCR_ADMODE) /*!<Address on four lines*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_AlternateBytesMode QSPI Alternate Bytes Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_NONE 0x00000000U /*!<No alternate bytes*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_1_LINE ((uint32_t)QUADSPI_CCR_ABMODE_0) /*!<Alternate bytes on a single line*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_2_LINES ((uint32_t)QUADSPI_CCR_ABMODE_1) /*!<Alternate bytes on two lines*/
|
||||||
|
#define QSPI_ALTERNATE_BYTES_4_LINES ((uint32_t)QUADSPI_CCR_ABMODE) /*!<Alternate bytes on four lines*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_DataMode QSPI Data Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_DATA_NONE 0x00000000U /*!<No data*/
|
||||||
|
#define QSPI_DATA_1_LINE ((uint32_t)QUADSPI_CCR_DMODE_0) /*!<Data on a single line*/
|
||||||
|
#define QSPI_DATA_2_LINES ((uint32_t)QUADSPI_CCR_DMODE_1) /*!<Data on two lines*/
|
||||||
|
#define QSPI_DATA_4_LINES ((uint32_t)QUADSPI_CCR_DMODE) /*!<Data on four lines*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_DdrMode QSPI DDR Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_DDR_MODE_DISABLE 0x00000000U /*!<Double data rate mode disabled*/
|
||||||
|
#define QSPI_DDR_MODE_ENABLE ((uint32_t)QUADSPI_CCR_DDRM) /*!<Double data rate mode enabled*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_DdrHoldHalfCycle QSPI DDR Data Output Delay
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_DDR_HHC_ANALOG_DELAY 0x00000000U /*!<Delay the data output using analog delay in DDR mode*/
|
||||||
|
#define QSPI_DDR_HHC_HALF_CLK_DELAY ((uint32_t)QUADSPI_CCR_DHHC) /*!<Delay the data output by one half of system clock in DDR mode*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_SIOOMode QSPI Send Instruction Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_SIOO_INST_EVERY_CMD 0x00000000U /*!<Send instruction on every transaction*/
|
||||||
|
#define QSPI_SIOO_INST_ONLY_FIRST_CMD ((uint32_t)QUADSPI_CCR_SIOO) /*!<Send instruction only for the first command*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_MatchMode QSPI Match Mode
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_MATCH_MODE_AND 0x00000000U /*!<AND match mode between unmasked bits*/
|
||||||
|
#define QSPI_MATCH_MODE_OR ((uint32_t)QUADSPI_CR_PMM) /*!<OR match mode between unmasked bits*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_AutomaticStop QSPI Automatic Stop
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_AUTOMATIC_STOP_DISABLE 0x00000000U /*!<AutoPolling stops only with abort or QSPI disabling*/
|
||||||
|
#define QSPI_AUTOMATIC_STOP_ENABLE ((uint32_t)QUADSPI_CR_APMS) /*!<AutoPolling stops as soon as there is a match*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_TimeOutActivation QSPI Timeout Activation
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_TIMEOUT_COUNTER_DISABLE 0x00000000U /*!<Timeout counter disabled, nCS remains active*/
|
||||||
|
#define QSPI_TIMEOUT_COUNTER_ENABLE ((uint32_t)QUADSPI_CR_TCEN) /*!<Timeout counter enabled, nCS released when timeout expires*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_Flags QSPI Flags
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_FLAG_BUSY QUADSPI_SR_BUSY /*!<Busy flag: operation is ongoing*/
|
||||||
|
#define QSPI_FLAG_TO QUADSPI_SR_TOF /*!<Timeout flag: timeout occurs in memory-mapped mode*/
|
||||||
|
#define QSPI_FLAG_SM QUADSPI_SR_SMF /*!<Status match flag: received data matches in autopolling mode*/
|
||||||
|
#define QSPI_FLAG_FT QUADSPI_SR_FTF /*!<Fifo threshold flag: Fifo threshold reached or data left after read from memory is complete*/
|
||||||
|
#define QSPI_FLAG_TC QUADSPI_SR_TCF /*!<Transfer complete flag: programmed number of data have been transferred or the transfer has been aborted*/
|
||||||
|
#define QSPI_FLAG_TE QUADSPI_SR_TEF /*!<Transfer error flag: invalid address is being accessed*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_Interrupts QSPI Interrupts
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define QSPI_IT_TO QUADSPI_CR_TOIE /*!<Interrupt on the timeout flag*/
|
||||||
|
#define QSPI_IT_SM QUADSPI_CR_SMIE /*!<Interrupt on the status match flag*/
|
||||||
|
#define QSPI_IT_FT QUADSPI_CR_FTIE /*!<Interrupt on the fifo threshold flag*/
|
||||||
|
#define QSPI_IT_TC QUADSPI_CR_TCIE /*!<Interrupt on the transfer complete flag*/
|
||||||
|
#define QSPI_IT_TE QUADSPI_CR_TEIE /*!<Interrupt on the transfer error flag*/
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @defgroup QSPI_Timeout_definition QSPI Timeout definition
|
||||||
|
* @brief QSPI Timeout definition
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define HAL_QSPI_TIMEOUT_DEFAULT_VALUE 5000U /* 5 s */
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Exported macros -----------------------------------------------------------*/
|
||||||
|
/** @defgroup QSPI_Exported_Macros QSPI Exported Macros
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
/** @brief Reset QSPI handle state.
|
||||||
|
* @param __HANDLE__ QSPI handle.
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
#if (USE_HAL_QSPI_REGISTER_CALLBACKS == 1)
|
||||||
|
#define __HAL_QSPI_RESET_HANDLE_STATE(__HANDLE__) do { \
|
||||||
|
(__HANDLE__)->State = HAL_QSPI_STATE_RESET; \
|
||||||
|
(__HANDLE__)->MspInitCallback = NULL; \
|
||||||
|
(__HANDLE__)->MspDeInitCallback = NULL; \
|
||||||
|
} while(0)
|
||||||
|
#else
|
||||||
|
#define __HAL_QSPI_RESET_HANDLE_STATE(__HANDLE__) ((__HANDLE__)->State = HAL_QSPI_STATE_RESET)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/** @brief Enable the QSPI peripheral.
|
||||||
|
* @param __HANDLE__ specifies the QSPI Handle.
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
#define __HAL_QSPI_ENABLE(__HANDLE__) SET_BIT((__HANDLE__)->Instance->CR, QUADSPI_CR_EN)
|
||||||
|
|
||||||
|
/** @brief Disable the QSPI peripheral.
|
||||||
|
* @param __HANDLE__ specifies the QSPI Handle.
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
#define __HAL_QSPI_DISABLE(__HANDLE__) CLEAR_BIT((__HANDLE__)->Instance->CR, QUADSPI_CR_EN)
|
||||||
|
|
||||||
|
/** @brief Enable the specified QSPI interrupt.
|
||||||
|
* @param __HANDLE__ specifies the QSPI Handle.
|
||||||
|
* @param __INTERRUPT__ specifies the QSPI interrupt source to enable.
|
||||||
|
* This parameter can be one of the following values:
|
||||||
|
* @arg QSPI_IT_TO: QSPI Timeout interrupt
|
||||||
|
* @arg QSPI_IT_SM: QSPI Status match interrupt
|
||||||
|
* @arg QSPI_IT_FT: QSPI FIFO threshold interrupt
|
||||||
|
* @arg QSPI_IT_TC: QSPI Transfer complete interrupt
|
||||||
|
* @arg QSPI_IT_TE: QSPI Transfer error interrupt
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
#define __HAL_QSPI_ENABLE_IT(__HANDLE__, __INTERRUPT__) SET_BIT((__HANDLE__)->Instance->CR, (__INTERRUPT__))
|
||||||
|
|
||||||
|
|
||||||
|
/** @brief Disable the specified QSPI interrupt.
|
||||||
|
* @param __HANDLE__ specifies the QSPI Handle.
|
||||||
|
* @param __INTERRUPT__ specifies the QSPI interrupt source to disable.
|
||||||
|
* This parameter can be one of the following values:
|
||||||
|
* @arg QSPI_IT_TO: QSPI Timeout interrupt
|
||||||
|
* @arg QSPI_IT_SM: QSPI Status match interrupt
|
||||||
|
* @arg QSPI_IT_FT: QSPI FIFO threshold interrupt
|
||||||
|
* @arg QSPI_IT_TC: QSPI Transfer complete interrupt
|
||||||
|
* @arg QSPI_IT_TE: QSPI Transfer error interrupt
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
#define __HAL_QSPI_DISABLE_IT(__HANDLE__, __INTERRUPT__) CLEAR_BIT((__HANDLE__)->Instance->CR, (__INTERRUPT__))
|
||||||
|
|
||||||
|
/** @brief Check whether the specified QSPI interrupt source is enabled or not.
|
||||||
|
* @param __HANDLE__ specifies the QSPI Handle.
|
||||||
|
* @param __INTERRUPT__ specifies the QSPI interrupt source to check.
|
||||||
|
* This parameter can be one of the following values:
|
||||||
|
* @arg QSPI_IT_TO: QSPI Timeout interrupt
|
||||||
|
* @arg QSPI_IT_SM: QSPI Status match interrupt
|
||||||
|
* @arg QSPI_IT_FT: QSPI FIFO threshold interrupt
|
||||||
|
* @arg QSPI_IT_TC: QSPI Transfer complete interrupt
|
||||||
|
* @arg QSPI_IT_TE: QSPI Transfer error interrupt
|
||||||
|
* @retval The new state of __INTERRUPT__ (TRUE or FALSE).
|
||||||
|
*/
|
||||||
|
#define __HAL_QSPI_GET_IT_SOURCE(__HANDLE__, __INTERRUPT__) (READ_BIT((__HANDLE__)->Instance->CR, (__INTERRUPT__)) == (__INTERRUPT__))
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Check whether the selected QSPI flag is set or not.
|
||||||
|
* @param __HANDLE__ specifies the QSPI Handle.
|
||||||
|
* @param __FLAG__ specifies the QSPI flag to check.
|
||||||
|
* This parameter can be one of the following values:
|
||||||
|
* @arg QSPI_FLAG_BUSY: QSPI Busy flag
|
||||||
|
* @arg QSPI_FLAG_TO: QSPI Timeout flag
|
||||||
|
* @arg QSPI_FLAG_SM: QSPI Status match flag
|
||||||
|
* @arg QSPI_FLAG_FT: QSPI FIFO threshold flag
|
||||||
|
* @arg QSPI_FLAG_TC: QSPI Transfer complete flag
|
||||||
|
* @arg QSPI_FLAG_TE: QSPI Transfer error flag
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
#define __HAL_QSPI_GET_FLAG(__HANDLE__, __FLAG__) ((READ_BIT((__HANDLE__)->Instance->SR, (__FLAG__)) != 0U) ? SET : RESET)
|
||||||
|
|
||||||
|
/** @brief Clears the specified QSPI's flag status.
|
||||||
|
* @param __HANDLE__ specifies the QSPI Handle.
|
||||||
|
* @param __FLAG__ specifies the QSPI clear register flag that needs to be set
|
||||||
|
* This parameter can be one of the following values:
|
||||||
|
* @arg QSPI_FLAG_TO: QSPI Timeout flag
|
||||||
|
* @arg QSPI_FLAG_SM: QSPI Status match flag
|
||||||
|
* @arg QSPI_FLAG_TC: QSPI Transfer complete flag
|
||||||
|
* @arg QSPI_FLAG_TE: QSPI Transfer error flag
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
#define __HAL_QSPI_CLEAR_FLAG(__HANDLE__, __FLAG__) WRITE_REG((__HANDLE__)->Instance->FCR, (__FLAG__))
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Exported functions --------------------------------------------------------*/
|
||||||
|
/** @addtogroup QSPI_Exported_Functions
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @addtogroup QSPI_Exported_Functions_Group1
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
/* Initialization/de-initialization functions ********************************/
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Init (QSPI_HandleTypeDef *hqspi);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_DeInit (QSPI_HandleTypeDef *hqspi);
|
||||||
|
void HAL_QSPI_MspInit (QSPI_HandleTypeDef *hqspi);
|
||||||
|
void HAL_QSPI_MspDeInit(QSPI_HandleTypeDef *hqspi);
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @addtogroup QSPI_Exported_Functions_Group2
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
/* IO operation functions *****************************************************/
|
||||||
|
/* QSPI IRQ handler method */
|
||||||
|
void HAL_QSPI_IRQHandler(QSPI_HandleTypeDef *hqspi);
|
||||||
|
|
||||||
|
/* QSPI indirect mode */
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Command (QSPI_HandleTypeDef *hqspi, QSPI_CommandTypeDef *cmd, uint32_t Timeout);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Transmit (QSPI_HandleTypeDef *hqspi, uint8_t *pData, uint32_t Timeout);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Receive (QSPI_HandleTypeDef *hqspi, uint8_t *pData, uint32_t Timeout);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Command_IT (QSPI_HandleTypeDef *hqspi, QSPI_CommandTypeDef *cmd);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Transmit_IT (QSPI_HandleTypeDef *hqspi, uint8_t *pData);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Receive_IT (QSPI_HandleTypeDef *hqspi, uint8_t *pData);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Transmit_DMA (QSPI_HandleTypeDef *hqspi, uint8_t *pData);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Receive_DMA (QSPI_HandleTypeDef *hqspi, uint8_t *pData);
|
||||||
|
|
||||||
|
/* QSPI status flag polling mode */
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_AutoPolling (QSPI_HandleTypeDef *hqspi, QSPI_CommandTypeDef *cmd, QSPI_AutoPollingTypeDef *cfg, uint32_t Timeout);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_AutoPolling_IT(QSPI_HandleTypeDef *hqspi, QSPI_CommandTypeDef *cmd, QSPI_AutoPollingTypeDef *cfg);
|
||||||
|
|
||||||
|
/* QSPI memory-mapped mode */
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_MemoryMapped(QSPI_HandleTypeDef *hqspi, QSPI_CommandTypeDef *cmd, QSPI_MemoryMappedTypeDef *cfg);
|
||||||
|
|
||||||
|
/* Callback functions in non-blocking modes ***********************************/
|
||||||
|
void HAL_QSPI_ErrorCallback (QSPI_HandleTypeDef *hqspi);
|
||||||
|
void HAL_QSPI_AbortCpltCallback (QSPI_HandleTypeDef *hqspi);
|
||||||
|
void HAL_QSPI_FifoThresholdCallback(QSPI_HandleTypeDef *hqspi);
|
||||||
|
|
||||||
|
/* QSPI indirect mode */
|
||||||
|
void HAL_QSPI_CmdCpltCallback (QSPI_HandleTypeDef *hqspi);
|
||||||
|
void HAL_QSPI_RxCpltCallback (QSPI_HandleTypeDef *hqspi);
|
||||||
|
void HAL_QSPI_TxCpltCallback (QSPI_HandleTypeDef *hqspi);
|
||||||
|
|
||||||
|
/* QSPI status flag polling mode */
|
||||||
|
void HAL_QSPI_StatusMatchCallback (QSPI_HandleTypeDef *hqspi);
|
||||||
|
|
||||||
|
/* QSPI memory-mapped mode */
|
||||||
|
void HAL_QSPI_TimeOutCallback (QSPI_HandleTypeDef *hqspi);
|
||||||
|
|
||||||
|
#if (USE_HAL_QSPI_REGISTER_CALLBACKS == 1)
|
||||||
|
/* QSPI callback registering/unregistering */
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_RegisterCallback (QSPI_HandleTypeDef *hqspi, HAL_QSPI_CallbackIDTypeDef CallbackId, pQSPI_CallbackTypeDef pCallback);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_UnRegisterCallback (QSPI_HandleTypeDef *hqspi, HAL_QSPI_CallbackIDTypeDef CallbackId);
|
||||||
|
#endif
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** @addtogroup QSPI_Exported_Functions_Group3
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
/* Peripheral Control and State functions ************************************/
|
||||||
|
HAL_QSPI_StateTypeDef HAL_QSPI_GetState (const QSPI_HandleTypeDef *hqspi);
|
||||||
|
uint32_t HAL_QSPI_GetError (const QSPI_HandleTypeDef *hqspi);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Abort (QSPI_HandleTypeDef *hqspi);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_Abort_IT (QSPI_HandleTypeDef *hqspi);
|
||||||
|
void HAL_QSPI_SetTimeout (QSPI_HandleTypeDef *hqspi, uint32_t Timeout);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_SetFifoThreshold(QSPI_HandleTypeDef *hqspi, uint32_t Threshold);
|
||||||
|
uint32_t HAL_QSPI_GetFifoThreshold(const QSPI_HandleTypeDef *hqspi);
|
||||||
|
HAL_StatusTypeDef HAL_QSPI_SetFlashID (QSPI_HandleTypeDef *hqspi, uint32_t FlashID);
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
/* End of exported functions -------------------------------------------------*/
|
||||||
|
|
||||||
|
/* Private macros ------------------------------------------------------------*/
|
||||||
|
/** @defgroup QSPI_Private_Macros QSPI Private Macros
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
#define IS_QSPI_CLOCK_PRESCALER(PRESCALER) ((PRESCALER) <= 0xFFU)
|
||||||
|
|
||||||
|
#define IS_QSPI_FIFO_THRESHOLD(THR) (((THR) > 0U) && ((THR) <= 32U))
|
||||||
|
|
||||||
|
#define IS_QSPI_SSHIFT(SSHIFT) (((SSHIFT) == QSPI_SAMPLE_SHIFTING_NONE) || \
|
||||||
|
((SSHIFT) == QSPI_SAMPLE_SHIFTING_HALFCYCLE))
|
||||||
|
|
||||||
|
#define IS_QSPI_FLASH_SIZE(FSIZE) (((FSIZE) <= 31U))
|
||||||
|
|
||||||
|
#define IS_QSPI_CS_HIGH_TIME(CSHTIME) (((CSHTIME) == QSPI_CS_HIGH_TIME_1_CYCLE) || \
|
||||||
|
((CSHTIME) == QSPI_CS_HIGH_TIME_2_CYCLE) || \
|
||||||
|
((CSHTIME) == QSPI_CS_HIGH_TIME_3_CYCLE) || \
|
||||||
|
((CSHTIME) == QSPI_CS_HIGH_TIME_4_CYCLE) || \
|
||||||
|
((CSHTIME) == QSPI_CS_HIGH_TIME_5_CYCLE) || \
|
||||||
|
((CSHTIME) == QSPI_CS_HIGH_TIME_6_CYCLE) || \
|
||||||
|
((CSHTIME) == QSPI_CS_HIGH_TIME_7_CYCLE) || \
|
||||||
|
((CSHTIME) == QSPI_CS_HIGH_TIME_8_CYCLE))
|
||||||
|
|
||||||
|
#define IS_QSPI_CLOCK_MODE(CLKMODE) (((CLKMODE) == QSPI_CLOCK_MODE_0) || \
|
||||||
|
((CLKMODE) == QSPI_CLOCK_MODE_3))
|
||||||
|
|
||||||
|
#define IS_QSPI_FLASH_ID(FLASH_ID) (((FLASH_ID) == QSPI_FLASH_ID_1) || \
|
||||||
|
((FLASH_ID) == QSPI_FLASH_ID_2))
|
||||||
|
|
||||||
|
#define IS_QSPI_DUAL_FLASH_MODE(MODE) (((MODE) == QSPI_DUALFLASH_ENABLE) || \
|
||||||
|
((MODE) == QSPI_DUALFLASH_DISABLE))
|
||||||
|
|
||||||
|
#define IS_QSPI_INSTRUCTION(INSTRUCTION) ((INSTRUCTION) <= 0xFFU)
|
||||||
|
|
||||||
|
#define IS_QSPI_ADDRESS_SIZE(ADDR_SIZE) (((ADDR_SIZE) == QSPI_ADDRESS_8_BITS) || \
|
||||||
|
((ADDR_SIZE) == QSPI_ADDRESS_16_BITS) || \
|
||||||
|
((ADDR_SIZE) == QSPI_ADDRESS_24_BITS) || \
|
||||||
|
((ADDR_SIZE) == QSPI_ADDRESS_32_BITS))
|
||||||
|
|
||||||
|
#define IS_QSPI_ALTERNATE_BYTES_SIZE(SIZE) (((SIZE) == QSPI_ALTERNATE_BYTES_8_BITS) || \
|
||||||
|
((SIZE) == QSPI_ALTERNATE_BYTES_16_BITS) || \
|
||||||
|
((SIZE) == QSPI_ALTERNATE_BYTES_24_BITS) || \
|
||||||
|
((SIZE) == QSPI_ALTERNATE_BYTES_32_BITS))
|
||||||
|
|
||||||
|
#define IS_QSPI_DUMMY_CYCLES(DCY) ((DCY) <= 31U)
|
||||||
|
|
||||||
|
#define IS_QSPI_INSTRUCTION_MODE(MODE) (((MODE) == QSPI_INSTRUCTION_NONE) || \
|
||||||
|
((MODE) == QSPI_INSTRUCTION_1_LINE) || \
|
||||||
|
((MODE) == QSPI_INSTRUCTION_2_LINES) || \
|
||||||
|
((MODE) == QSPI_INSTRUCTION_4_LINES))
|
||||||
|
|
||||||
|
#define IS_QSPI_ADDRESS_MODE(MODE) (((MODE) == QSPI_ADDRESS_NONE) || \
|
||||||
|
((MODE) == QSPI_ADDRESS_1_LINE) || \
|
||||||
|
((MODE) == QSPI_ADDRESS_2_LINES) || \
|
||||||
|
((MODE) == QSPI_ADDRESS_4_LINES))
|
||||||
|
|
||||||
|
#define IS_QSPI_ALTERNATE_BYTES_MODE(MODE) (((MODE) == QSPI_ALTERNATE_BYTES_NONE) || \
|
||||||
|
((MODE) == QSPI_ALTERNATE_BYTES_1_LINE) || \
|
||||||
|
((MODE) == QSPI_ALTERNATE_BYTES_2_LINES) || \
|
||||||
|
((MODE) == QSPI_ALTERNATE_BYTES_4_LINES))
|
||||||
|
|
||||||
|
#define IS_QSPI_DATA_MODE(MODE) (((MODE) == QSPI_DATA_NONE) || \
|
||||||
|
((MODE) == QSPI_DATA_1_LINE) || \
|
||||||
|
((MODE) == QSPI_DATA_2_LINES) || \
|
||||||
|
((MODE) == QSPI_DATA_4_LINES))
|
||||||
|
|
||||||
|
#define IS_QSPI_DDR_MODE(DDR_MODE) (((DDR_MODE) == QSPI_DDR_MODE_DISABLE) || \
|
||||||
|
((DDR_MODE) == QSPI_DDR_MODE_ENABLE))
|
||||||
|
|
||||||
|
#define IS_QSPI_DDR_HHC(DDR_HHC) (((DDR_HHC) == QSPI_DDR_HHC_ANALOG_DELAY) || \
|
||||||
|
((DDR_HHC) == QSPI_DDR_HHC_HALF_CLK_DELAY))
|
||||||
|
|
||||||
|
#define IS_QSPI_SIOO_MODE(SIOO_MODE) (((SIOO_MODE) == QSPI_SIOO_INST_EVERY_CMD) || \
|
||||||
|
((SIOO_MODE) == QSPI_SIOO_INST_ONLY_FIRST_CMD))
|
||||||
|
|
||||||
|
#define IS_QSPI_INTERVAL(INTERVAL) ((INTERVAL) <= QUADSPI_PIR_INTERVAL)
|
||||||
|
|
||||||
|
#define IS_QSPI_STATUS_BYTES_SIZE(SIZE) (((SIZE) >= 1U) && ((SIZE) <= 4U))
|
||||||
|
|
||||||
|
#define IS_QSPI_MATCH_MODE(MODE) (((MODE) == QSPI_MATCH_MODE_AND) || \
|
||||||
|
((MODE) == QSPI_MATCH_MODE_OR))
|
||||||
|
|
||||||
|
#define IS_QSPI_AUTOMATIC_STOP(APMS) (((APMS) == QSPI_AUTOMATIC_STOP_DISABLE) || \
|
||||||
|
((APMS) == QSPI_AUTOMATIC_STOP_ENABLE))
|
||||||
|
|
||||||
|
#define IS_QSPI_TIMEOUT_ACTIVATION(TCEN) (((TCEN) == QSPI_TIMEOUT_COUNTER_DISABLE) || \
|
||||||
|
((TCEN) == QSPI_TIMEOUT_COUNTER_ENABLE))
|
||||||
|
|
||||||
|
#define IS_QSPI_TIMEOUT_PERIOD(PERIOD) ((PERIOD) <= 0xFFFFU)
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
/* End of private macros -----------------------------------------------------*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
#endif /* defined(QUADSPI) */
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif /* STM32H7xx_HAL_QSPI_H */
|
||||||
File diff suppressed because it is too large.
Load diff
@@ -1157,11 +1157,14 @@
|
|||||||
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_exti.c</name>
|
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_exti.c</name>
|
||||||
</file>
|
</file>
|
||||||
<file>
|
<file>
|
||||||
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_ll_sdmmc.c</name>
|
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_qspi.c</name>
|
||||||
</file>
|
</file>
|
||||||
<file>
|
<file>
|
||||||
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_ll_delayblock.c</name>
|
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_ll_delayblock.c</name>
|
||||||
</file>
|
</file>
|
||||||
|
<file>
|
||||||
|
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_ll_sdmmc.c</name>
|
||||||
|
</file>
|
||||||
<file>
|
<file>
|
||||||
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_sd.c</name>
|
<name>$PROJ_DIR$/../Drivers/STM32H7xx_HAL_Driver/Src/stm32h7xx_hal_sd.c</name>
|
||||||
</file>
|
</file>
|
||||||
|
|||||||
@@ -64,7 +64,7 @@
|
|||||||
/* #define HAL_IWDG_MODULE_ENABLED */
|
/* #define HAL_IWDG_MODULE_ENABLED */
|
||||||
/* #define HAL_LPTIM_MODULE_ENABLED */
|
/* #define HAL_LPTIM_MODULE_ENABLED */
|
||||||
/* #define HAL_LTDC_MODULE_ENABLED */
|
/* #define HAL_LTDC_MODULE_ENABLED */
|
||||||
/* #define HAL_QSPI_MODULE_ENABLED */
|
#define HAL_QSPI_MODULE_ENABLED
|
||||||
/* #define HAL_RAMECC_MODULE_ENABLED */
|
/* #define HAL_RAMECC_MODULE_ENABLED */
|
||||||
/* #define HAL_RNG_MODULE_ENABLED */
|
/* #define HAL_RNG_MODULE_ENABLED */
|
||||||
/* #define HAL_RTC_MODULE_ENABLED */
|
/* #define HAL_RTC_MODULE_ENABLED */
|
||||||
|
|||||||
@@ -59,6 +59,7 @@ void DMA1_Stream0_IRQHandler(void);
|
|||||||
void USART1_IRQHandler(void);
|
void USART1_IRQHandler(void);
|
||||||
void USART2_IRQHandler(void);
|
void USART2_IRQHandler(void);
|
||||||
void SDMMC1_IRQHandler(void);
|
void SDMMC1_IRQHandler(void);
|
||||||
|
void QUADSPI_IRQHandler(void);
|
||||||
/* USER CODE BEGIN EFP */
|
/* USER CODE BEGIN EFP */
|
||||||
|
|
||||||
/* USER CODE END EFP */
|
/* USER CODE END EFP */
|
||||||
|
|||||||
+41
-1
@@ -41,6 +41,8 @@
|
|||||||
|
|
||||||
/* Private variables ---------------------------------------------------------*/
|
/* Private variables ---------------------------------------------------------*/
|
||||||
|
|
||||||
|
QSPI_HandleTypeDef hqspi;
|
||||||
|
|
||||||
SD_HandleTypeDef hsd1;
|
SD_HandleTypeDef hsd1;
|
||||||
|
|
||||||
UART_HandleTypeDef huart1;
|
UART_HandleTypeDef huart1;
|
||||||
@@ -62,6 +64,7 @@ static void MX_FMC_Init(void);
|
|||||||
static void MX_SDMMC1_SD_Init(void);
|
static void MX_SDMMC1_SD_Init(void);
|
||||||
static void MX_USART1_UART_Init(void);
|
static void MX_USART1_UART_Init(void);
|
||||||
static void MX_USART2_UART_Init(void);
|
static void MX_USART2_UART_Init(void);
|
||||||
|
static void MX_QUADSPI_Init(void);
|
||||||
/* USER CODE BEGIN PFP */
|
/* USER CODE BEGIN PFP */
|
||||||
|
|
||||||
/* USER CODE END PFP */
|
/* USER CODE END PFP */
|
||||||
@@ -108,6 +111,7 @@ __WEAK int main(void)
|
|||||||
MX_SDMMC1_SD_Init();
|
MX_SDMMC1_SD_Init();
|
||||||
MX_USART1_UART_Init();
|
MX_USART1_UART_Init();
|
||||||
MX_USART2_UART_Init();
|
MX_USART2_UART_Init();
|
||||||
|
MX_QUADSPI_Init();
|
||||||
/* USER CODE BEGIN 2 */
|
/* USER CODE BEGIN 2 */
|
||||||
|
|
||||||
/* USER CODE END 2 */
|
/* USER CODE END 2 */
|
||||||
@@ -153,7 +157,7 @@ void SystemClock_Config(void)
|
|||||||
RCC_OscInitStruct.PLL.PLLM = 4;
|
RCC_OscInitStruct.PLL.PLLM = 4;
|
||||||
RCC_OscInitStruct.PLL.PLLN = 60;
|
RCC_OscInitStruct.PLL.PLLN = 60;
|
||||||
RCC_OscInitStruct.PLL.PLLP = 2;
|
RCC_OscInitStruct.PLL.PLLP = 2;
|
||||||
RCC_OscInitStruct.PLL.PLLQ = 6;
|
RCC_OscInitStruct.PLL.PLLQ = 8;
|
||||||
RCC_OscInitStruct.PLL.PLLR = 2;
|
RCC_OscInitStruct.PLL.PLLR = 2;
|
||||||
RCC_OscInitStruct.PLL.PLLRGE = RCC_PLL1VCIRANGE_3;
|
RCC_OscInitStruct.PLL.PLLRGE = RCC_PLL1VCIRANGE_3;
|
||||||
RCC_OscInitStruct.PLL.PLLVCOSEL = RCC_PLL1VCOWIDE;
|
RCC_OscInitStruct.PLL.PLLVCOSEL = RCC_PLL1VCOWIDE;
|
||||||
@@ -182,6 +186,41 @@ void SystemClock_Config(void)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QUADSPI Initialization Function
|
||||||
|
* @param None
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
static void MX_QUADSPI_Init(void)
|
||||||
|
{
|
||||||
|
|
||||||
|
/* USER CODE BEGIN QUADSPI_Init 0 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_Init 0 */
|
||||||
|
|
||||||
|
/* USER CODE BEGIN QUADSPI_Init 1 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_Init 1 */
|
||||||
|
/* QUADSPI parameter configuration*/
|
||||||
|
hqspi.Instance = QUADSPI;
|
||||||
|
hqspi.Init.ClockPrescaler = 255;
|
||||||
|
hqspi.Init.FifoThreshold = 1;
|
||||||
|
hqspi.Init.SampleShifting = QSPI_SAMPLE_SHIFTING_NONE;
|
||||||
|
hqspi.Init.FlashSize = 1;
|
||||||
|
hqspi.Init.ChipSelectHighTime = QSPI_CS_HIGH_TIME_1_CYCLE;
|
||||||
|
hqspi.Init.ClockMode = QSPI_CLOCK_MODE_0;
|
||||||
|
hqspi.Init.FlashID = QSPI_FLASH_ID_1;
|
||||||
|
hqspi.Init.DualFlash = QSPI_DUALFLASH_DISABLE;
|
||||||
|
if (HAL_QSPI_Init(&hqspi) != HAL_OK)
|
||||||
|
{
|
||||||
|
Error_Handler();
|
||||||
|
}
|
||||||
|
/* USER CODE BEGIN QUADSPI_Init 2 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_Init 2 */
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief SDMMC1 Initialization Function
|
* @brief SDMMC1 Initialization Function
|
||||||
* @param None
|
* @param None
|
||||||
@@ -387,6 +426,7 @@ static void MX_GPIO_Init(void)
|
|||||||
/* GPIO Ports Clock Enable */
|
/* GPIO Ports Clock Enable */
|
||||||
__HAL_RCC_GPIOF_CLK_ENABLE();
|
__HAL_RCC_GPIOF_CLK_ENABLE();
|
||||||
__HAL_RCC_GPIOC_CLK_ENABLE();
|
__HAL_RCC_GPIOC_CLK_ENABLE();
|
||||||
|
__HAL_RCC_GPIOA_CLK_ENABLE();
|
||||||
__HAL_RCC_GPIOH_CLK_ENABLE();
|
__HAL_RCC_GPIOH_CLK_ENABLE();
|
||||||
__HAL_RCC_GPIOB_CLK_ENABLE();
|
__HAL_RCC_GPIOB_CLK_ENABLE();
|
||||||
__HAL_RCC_GPIOG_CLK_ENABLE();
|
__HAL_RCC_GPIOG_CLK_ENABLE();
|
||||||
|
|||||||
@@ -77,6 +77,120 @@ void HAL_MspInit(void)
|
|||||||
/* USER CODE END MspInit 1 */
|
/* USER CODE END MspInit 1 */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QSPI MSP Initialization
|
||||||
|
* This function configures the hardware resources used in this example
|
||||||
|
* @param hqspi: QSPI handle pointer
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
void HAL_QSPI_MspInit(QSPI_HandleTypeDef* hqspi)
|
||||||
|
{
|
||||||
|
GPIO_InitTypeDef GPIO_InitStruct = {0};
|
||||||
|
RCC_PeriphCLKInitTypeDef PeriphClkInitStruct = {0};
|
||||||
|
if(hqspi->Instance==QUADSPI)
|
||||||
|
{
|
||||||
|
/* USER CODE BEGIN QUADSPI_MspInit 0 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_MspInit 0 */
|
||||||
|
|
||||||
|
/** Initializes the peripherals clock
|
||||||
|
*/
|
||||||
|
PeriphClkInitStruct.PeriphClockSelection = RCC_PERIPHCLK_QSPI;
|
||||||
|
PeriphClkInitStruct.QspiClockSelection = RCC_QSPICLKSOURCE_PLL;
|
||||||
|
if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInitStruct) != HAL_OK)
|
||||||
|
{
|
||||||
|
Error_Handler();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Peripheral clock enable */
|
||||||
|
__HAL_RCC_QSPI_CLK_ENABLE();
|
||||||
|
|
||||||
|
__HAL_RCC_GPIOF_CLK_ENABLE();
|
||||||
|
__HAL_RCC_GPIOB_CLK_ENABLE();
|
||||||
|
/**QUADSPI GPIO Configuration
|
||||||
|
PF6 ------> QUADSPI_BK1_IO3
|
||||||
|
PF7 ------> QUADSPI_BK1_IO2
|
||||||
|
PF8 ------> QUADSPI_BK1_IO0
|
||||||
|
PF9 ------> QUADSPI_BK1_IO1
|
||||||
|
PB2 ------> QUADSPI_CLK
|
||||||
|
PB6 ------> QUADSPI_BK1_NCS
|
||||||
|
*/
|
||||||
|
GPIO_InitStruct.Pin = GPIO_PIN_6|GPIO_PIN_7;
|
||||||
|
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
|
||||||
|
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||||
|
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
||||||
|
GPIO_InitStruct.Alternate = GPIO_AF9_QUADSPI;
|
||||||
|
HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
|
||||||
|
|
||||||
|
GPIO_InitStruct.Pin = GPIO_PIN_8|GPIO_PIN_9;
|
||||||
|
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
|
||||||
|
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||||
|
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
||||||
|
GPIO_InitStruct.Alternate = GPIO_AF10_QUADSPI;
|
||||||
|
HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
|
||||||
|
|
||||||
|
GPIO_InitStruct.Pin = GPIO_PIN_2;
|
||||||
|
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
|
||||||
|
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||||
|
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
||||||
|
GPIO_InitStruct.Alternate = GPIO_AF9_QUADSPI;
|
||||||
|
HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
|
||||||
|
|
||||||
|
GPIO_InitStruct.Pin = GPIO_PIN_6;
|
||||||
|
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
|
||||||
|
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||||
|
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
||||||
|
GPIO_InitStruct.Alternate = GPIO_AF10_QUADSPI;
|
||||||
|
HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);
|
||||||
|
|
||||||
|
/* QUADSPI interrupt Init */
|
||||||
|
HAL_NVIC_SetPriority(QUADSPI_IRQn, 0, 0);
|
||||||
|
HAL_NVIC_EnableIRQ(QUADSPI_IRQn);
|
||||||
|
/* USER CODE BEGIN QUADSPI_MspInit 1 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_MspInit 1 */
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief QSPI MSP De-Initialization
|
||||||
|
* This function freeze the hardware resources used in this example
|
||||||
|
* @param hqspi: QSPI handle pointer
|
||||||
|
* @retval None
|
||||||
|
*/
|
||||||
|
void HAL_QSPI_MspDeInit(QSPI_HandleTypeDef* hqspi)
|
||||||
|
{
|
||||||
|
if(hqspi->Instance==QUADSPI)
|
||||||
|
{
|
||||||
|
/* USER CODE BEGIN QUADSPI_MspDeInit 0 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_MspDeInit 0 */
|
||||||
|
/* Peripheral clock disable */
|
||||||
|
__HAL_RCC_QSPI_CLK_DISABLE();
|
||||||
|
|
||||||
|
/**QUADSPI GPIO Configuration
|
||||||
|
PF6 ------> QUADSPI_BK1_IO3
|
||||||
|
PF7 ------> QUADSPI_BK1_IO2
|
||||||
|
PF8 ------> QUADSPI_BK1_IO0
|
||||||
|
PF9 ------> QUADSPI_BK1_IO1
|
||||||
|
PB2 ------> QUADSPI_CLK
|
||||||
|
PB6 ------> QUADSPI_BK1_NCS
|
||||||
|
*/
|
||||||
|
HAL_GPIO_DeInit(GPIOF, GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9);
|
||||||
|
|
||||||
|
HAL_GPIO_DeInit(GPIOB, GPIO_PIN_2|GPIO_PIN_6);
|
||||||
|
|
||||||
|
/* QUADSPI interrupt DeInit */
|
||||||
|
HAL_NVIC_DisableIRQ(QUADSPI_IRQn);
|
||||||
|
/* USER CODE BEGIN QUADSPI_MspDeInit 1 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_MspDeInit 1 */
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief SD MSP Initialization
|
* @brief SD MSP Initialization
|
||||||
* This function configures the hardware resources used in this example
|
* This function configures the hardware resources used in this example
|
||||||
@@ -271,17 +385,17 @@ void HAL_UART_MspInit(UART_HandleTypeDef* huart)
|
|||||||
/* Peripheral clock enable */
|
/* Peripheral clock enable */
|
||||||
__HAL_RCC_USART2_CLK_ENABLE();
|
__HAL_RCC_USART2_CLK_ENABLE();
|
||||||
|
|
||||||
__HAL_RCC_GPIOD_CLK_ENABLE();
|
__HAL_RCC_GPIOA_CLK_ENABLE();
|
||||||
/**USART2 GPIO Configuration
|
/**USART2 GPIO Configuration
|
||||||
PD5 ------> USART2_TX
|
PA2 ------> USART2_TX
|
||||||
PD6 ------> USART2_RX
|
PA3 ------> USART2_RX
|
||||||
*/
|
*/
|
||||||
GPIO_InitStruct.Pin = GPIO_PIN_5|GPIO_PIN_6;
|
GPIO_InitStruct.Pin = GPIO_PIN_2|GPIO_PIN_3;
|
||||||
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
|
GPIO_InitStruct.Mode = GPIO_MODE_AF_PP;
|
||||||
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
GPIO_InitStruct.Pull = GPIO_NOPULL;
|
||||||
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
|
||||||
GPIO_InitStruct.Alternate = GPIO_AF7_USART2;
|
GPIO_InitStruct.Alternate = GPIO_AF7_USART2;
|
||||||
HAL_GPIO_Init(GPIOD, &GPIO_InitStruct);
|
HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);
|
||||||
|
|
||||||
/* USART2 interrupt Init */
|
/* USART2 interrupt Init */
|
||||||
HAL_NVIC_SetPriority(USART2_IRQn, 0, 0);
|
HAL_NVIC_SetPriority(USART2_IRQn, 0, 0);
|
||||||
@@ -333,10 +447,10 @@ void HAL_UART_MspDeInit(UART_HandleTypeDef* huart)
|
|||||||
__HAL_RCC_USART2_CLK_DISABLE();
|
__HAL_RCC_USART2_CLK_DISABLE();
|
||||||
|
|
||||||
/**USART2 GPIO Configuration
|
/**USART2 GPIO Configuration
|
||||||
PD5 ------> USART2_TX
|
PA2 ------> USART2_TX
|
||||||
PD6 ------> USART2_RX
|
PA3 ------> USART2_RX
|
||||||
*/
|
*/
|
||||||
HAL_GPIO_DeInit(GPIOD, GPIO_PIN_5|GPIO_PIN_6);
|
HAL_GPIO_DeInit(GPIOA, GPIO_PIN_2|GPIO_PIN_3);
|
||||||
|
|
||||||
/* USART2 interrupt DeInit */
|
/* USART2 interrupt DeInit */
|
||||||
HAL_NVIC_DisableIRQ(USART2_IRQn);
|
HAL_NVIC_DisableIRQ(USART2_IRQn);
|
||||||
|
|||||||
@@ -55,6 +55,7 @@
|
|||||||
/* USER CODE END 0 */
|
/* USER CODE END 0 */
|
||||||
|
|
||||||
/* External variables --------------------------------------------------------*/
|
/* External variables --------------------------------------------------------*/
|
||||||
|
extern QSPI_HandleTypeDef hqspi;
|
||||||
extern SD_HandleTypeDef hsd1;
|
extern SD_HandleTypeDef hsd1;
|
||||||
extern DMA_HandleTypeDef hdma_usart1_rx;
|
extern DMA_HandleTypeDef hdma_usart1_rx;
|
||||||
extern UART_HandleTypeDef huart1;
|
extern UART_HandleTypeDef huart1;
|
||||||
@@ -257,6 +258,20 @@ void SDMMC1_IRQHandler(void)
|
|||||||
/* USER CODE END SDMMC1_IRQn 1 */
|
/* USER CODE END SDMMC1_IRQn 1 */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief This function handles QUADSPI global interrupt.
|
||||||
|
*/
|
||||||
|
void QUADSPI_IRQHandler(void)
|
||||||
|
{
|
||||||
|
/* USER CODE BEGIN QUADSPI_IRQn 0 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_IRQn 0 */
|
||||||
|
HAL_QSPI_IRQHandler(&hqspi);
|
||||||
|
/* USER CODE BEGIN QUADSPI_IRQn 1 */
|
||||||
|
|
||||||
|
/* USER CODE END QUADSPI_IRQn 1 */
|
||||||
|
}
|
||||||
|
|
||||||
/* USER CODE BEGIN 1 */
|
/* USER CODE BEGIN 1 */
|
||||||
|
|
||||||
/* USER CODE END 1 */
|
/* USER CODE END 1 */
|
||||||
+99
-72
@@ -36,71 +36,78 @@ Mcu.CPN=STM32H743IIT6
|
|||||||
Mcu.Family=STM32H7
|
Mcu.Family=STM32H7
|
||||||
Mcu.IP0=CORTEX_M7
|
Mcu.IP0=CORTEX_M7
|
||||||
Mcu.IP1=DMA
|
Mcu.IP1=DMA
|
||||||
|
Mcu.IP10=USART2
|
||||||
Mcu.IP2=FMC
|
Mcu.IP2=FMC
|
||||||
Mcu.IP3=MEMORYMAP
|
Mcu.IP3=MEMORYMAP
|
||||||
Mcu.IP4=NVIC
|
Mcu.IP4=NVIC
|
||||||
Mcu.IP5=RCC
|
Mcu.IP5=QUADSPI
|
||||||
Mcu.IP6=SDMMC1
|
Mcu.IP6=RCC
|
||||||
Mcu.IP7=SYS
|
Mcu.IP7=SDMMC1
|
||||||
Mcu.IP8=USART1
|
Mcu.IP8=SYS
|
||||||
Mcu.IP9=USART2
|
Mcu.IP9=USART1
|
||||||
Mcu.IPNb=10
|
Mcu.IPNb=11
|
||||||
Mcu.Name=STM32H743IITx
|
Mcu.Name=STM32H743IITx
|
||||||
Mcu.Package=LQFP176
|
Mcu.Package=LQFP176
|
||||||
Mcu.Pin0=PF0
|
Mcu.Pin0=PF0
|
||||||
Mcu.Pin1=PF1
|
Mcu.Pin1=PF1
|
||||||
Mcu.Pin10=PB1
|
Mcu.Pin10=PC0
|
||||||
Mcu.Pin11=PF11
|
Mcu.Pin11=PA2
|
||||||
Mcu.Pin12=PF12
|
Mcu.Pin12=PH2
|
||||||
Mcu.Pin13=PF13
|
Mcu.Pin13=PH3
|
||||||
Mcu.Pin14=PF14
|
Mcu.Pin14=PA3
|
||||||
Mcu.Pin15=PF15
|
Mcu.Pin15=PB0
|
||||||
Mcu.Pin16=PG0
|
Mcu.Pin16=PB1
|
||||||
Mcu.Pin17=PG1
|
Mcu.Pin17=PB2
|
||||||
Mcu.Pin18=PE7
|
Mcu.Pin18=PF11
|
||||||
Mcu.Pin19=PE8
|
Mcu.Pin19=PF12
|
||||||
Mcu.Pin2=PF2
|
Mcu.Pin2=PF2
|
||||||
Mcu.Pin20=PE9
|
Mcu.Pin20=PF13
|
||||||
Mcu.Pin21=PE10
|
Mcu.Pin21=PF14
|
||||||
Mcu.Pin22=PE11
|
Mcu.Pin22=PF15
|
||||||
Mcu.Pin23=PE12
|
Mcu.Pin23=PG0
|
||||||
Mcu.Pin24=PE13
|
Mcu.Pin24=PG1
|
||||||
Mcu.Pin25=PE14
|
Mcu.Pin25=PE7
|
||||||
Mcu.Pin26=PE15
|
Mcu.Pin26=PE8
|
||||||
Mcu.Pin27=PB14
|
Mcu.Pin27=PE9
|
||||||
Mcu.Pin28=PB15
|
Mcu.Pin28=PE10
|
||||||
Mcu.Pin29=PD8
|
Mcu.Pin29=PE11
|
||||||
Mcu.Pin3=PF3
|
Mcu.Pin3=PF3
|
||||||
Mcu.Pin30=PD9
|
Mcu.Pin30=PE12
|
||||||
Mcu.Pin31=PD10
|
Mcu.Pin31=PE13
|
||||||
Mcu.Pin32=PD14
|
Mcu.Pin32=PE14
|
||||||
Mcu.Pin33=PD15
|
Mcu.Pin33=PE15
|
||||||
Mcu.Pin34=PG2
|
Mcu.Pin34=PB14
|
||||||
Mcu.Pin35=PG4
|
Mcu.Pin35=PB15
|
||||||
Mcu.Pin36=PG5
|
Mcu.Pin36=PD8
|
||||||
Mcu.Pin37=PG8
|
Mcu.Pin37=PD9
|
||||||
Mcu.Pin38=PC8
|
Mcu.Pin38=PD10
|
||||||
Mcu.Pin39=PC9
|
Mcu.Pin39=PD14
|
||||||
Mcu.Pin4=PF4
|
Mcu.Pin4=PF4
|
||||||
Mcu.Pin40=PC10
|
Mcu.Pin40=PD15
|
||||||
Mcu.Pin41=PC11
|
Mcu.Pin41=PG2
|
||||||
Mcu.Pin42=PC12
|
Mcu.Pin42=PG4
|
||||||
Mcu.Pin43=PD0
|
Mcu.Pin43=PG5
|
||||||
Mcu.Pin44=PD1
|
Mcu.Pin44=PG8
|
||||||
Mcu.Pin45=PD2
|
Mcu.Pin45=PC8
|
||||||
Mcu.Pin46=PD5
|
Mcu.Pin46=PC9
|
||||||
Mcu.Pin47=PD6
|
Mcu.Pin47=PC10
|
||||||
Mcu.Pin48=PG15
|
Mcu.Pin48=PC11
|
||||||
Mcu.Pin49=PE0
|
Mcu.Pin49=PC12
|
||||||
Mcu.Pin5=PF5
|
Mcu.Pin5=PF5
|
||||||
Mcu.Pin50=PE1
|
Mcu.Pin50=PD0
|
||||||
Mcu.Pin51=VP_SYS_VS_Systick
|
Mcu.Pin51=PD1
|
||||||
Mcu.Pin52=VP_MEMORYMAP_VS_MEMORYMAP
|
Mcu.Pin52=PD2
|
||||||
Mcu.Pin6=PC0
|
Mcu.Pin53=PG15
|
||||||
Mcu.Pin7=PH2
|
Mcu.Pin54=PB6
|
||||||
Mcu.Pin8=PH3
|
Mcu.Pin55=PE0
|
||||||
Mcu.Pin9=PB0
|
Mcu.Pin56=PE1
|
||||||
Mcu.PinsNb=53
|
Mcu.Pin57=VP_SYS_VS_Systick
|
||||||
|
Mcu.Pin58=VP_MEMORYMAP_VS_MEMORYMAP
|
||||||
|
Mcu.Pin6=PF6
|
||||||
|
Mcu.Pin7=PF7
|
||||||
|
Mcu.Pin8=PF8
|
||||||
|
Mcu.Pin9=PF9
|
||||||
|
Mcu.PinsNb=59
|
||||||
Mcu.ThirdPartyNb=0
|
Mcu.ThirdPartyNb=0
|
||||||
Mcu.UserConstants=
|
Mcu.UserConstants=
|
||||||
Mcu.UserName=STM32H743IITx
|
Mcu.UserName=STM32H743IITx
|
||||||
@@ -115,12 +122,17 @@ NVIC.MemoryManagement_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
|||||||
NVIC.NonMaskableInt_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
NVIC.NonMaskableInt_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
||||||
NVIC.PendSV_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
NVIC.PendSV_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
||||||
NVIC.PriorityGroup=NVIC_PRIORITYGROUP_4
|
NVIC.PriorityGroup=NVIC_PRIORITYGROUP_4
|
||||||
|
NVIC.QUADSPI_IRQn=true\:0\:0\:false\:false\:true\:true\:true\:true
|
||||||
NVIC.SDMMC1_IRQn=true\:0\:0\:false\:false\:true\:true\:true\:true
|
NVIC.SDMMC1_IRQn=true\:0\:0\:false\:false\:true\:true\:true\:true
|
||||||
NVIC.SVCall_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
NVIC.SVCall_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
||||||
NVIC.SysTick_IRQn=true\:15\:0\:false\:false\:true\:false\:true\:false
|
NVIC.SysTick_IRQn=true\:15\:0\:false\:false\:true\:false\:true\:false
|
||||||
NVIC.USART1_IRQn=true\:0\:0\:false\:false\:true\:true\:true\:true
|
NVIC.USART1_IRQn=true\:0\:0\:false\:false\:true\:true\:true\:true
|
||||||
NVIC.USART2_IRQn=true\:0\:0\:false\:false\:true\:true\:true\:true
|
NVIC.USART2_IRQn=true\:0\:0\:false\:false\:true\:true\:true\:true
|
||||||
NVIC.UsageFault_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
NVIC.UsageFault_IRQn=true\:0\:0\:false\:false\:true\:false\:false\:false
|
||||||
|
PA2.Mode=Asynchronous
|
||||||
|
PA2.Signal=USART2_TX
|
||||||
|
PA3.Mode=Asynchronous
|
||||||
|
PA3.Signal=USART2_RX
|
||||||
PB0.Locked=true
|
PB0.Locked=true
|
||||||
PB0.Signal=GPIO_Output
|
PB0.Signal=GPIO_Output
|
||||||
PB1.Locked=true
|
PB1.Locked=true
|
||||||
@@ -129,6 +141,12 @@ PB14.Mode=Asynchronous
|
|||||||
PB14.Signal=USART1_TX
|
PB14.Signal=USART1_TX
|
||||||
PB15.Mode=Asynchronous
|
PB15.Mode=Asynchronous
|
||||||
PB15.Signal=USART1_RX
|
PB15.Signal=USART1_RX
|
||||||
|
PB2.Locked=true
|
||||||
|
PB2.Mode=Single Bank 1
|
||||||
|
PB2.Signal=QUADSPI_CLK
|
||||||
|
PB6.Locked=true
|
||||||
|
PB6.Mode=Single Bank 1
|
||||||
|
PB6.Signal=QUADSPI_BK1_NCS
|
||||||
PC0.Signal=FMC_SDNWE
|
PC0.Signal=FMC_SDNWE
|
||||||
PC10.Mode=SD_4_bits_Wide_bus
|
PC10.Mode=SD_4_bits_Wide_bus
|
||||||
PC10.Signal=SDMMC1_D2
|
PC10.Signal=SDMMC1_D2
|
||||||
@@ -147,10 +165,6 @@ PD14.Signal=FMC_D0_DA0
|
|||||||
PD15.Signal=FMC_D1_DA1
|
PD15.Signal=FMC_D1_DA1
|
||||||
PD2.Mode=SD_4_bits_Wide_bus
|
PD2.Mode=SD_4_bits_Wide_bus
|
||||||
PD2.Signal=SDMMC1_CMD
|
PD2.Signal=SDMMC1_CMD
|
||||||
PD5.Mode=Asynchronous
|
|
||||||
PD5.Signal=USART2_TX
|
|
||||||
PD6.Mode=Asynchronous
|
|
||||||
PD6.Signal=USART2_RX
|
|
||||||
PD8.Signal=FMC_D13_DA13
|
PD8.Signal=FMC_D13_DA13
|
||||||
PD9.Signal=FMC_D14_DA14
|
PD9.Signal=FMC_D14_DA14
|
||||||
PE0.Signal=FMC_NBL0
|
PE0.Signal=FMC_NBL0
|
||||||
@@ -175,6 +189,18 @@ PF2.Signal=FMC_A2
|
|||||||
PF3.Signal=FMC_A3
|
PF3.Signal=FMC_A3
|
||||||
PF4.Signal=FMC_A4
|
PF4.Signal=FMC_A4
|
||||||
PF5.Signal=FMC_A5
|
PF5.Signal=FMC_A5
|
||||||
|
PF6.Locked=true
|
||||||
|
PF6.Mode=Single Bank 1
|
||||||
|
PF6.Signal=QUADSPI_BK1_IO3
|
||||||
|
PF7.Locked=true
|
||||||
|
PF7.Mode=Single Bank 1
|
||||||
|
PF7.Signal=QUADSPI_BK1_IO2
|
||||||
|
PF8.Locked=true
|
||||||
|
PF8.Mode=Single Bank 1
|
||||||
|
PF8.Signal=QUADSPI_BK1_IO0
|
||||||
|
PF9.Locked=true
|
||||||
|
PF9.Mode=Single Bank 1
|
||||||
|
PF9.Signal=QUADSPI_BK1_IO1
|
||||||
PG0.Signal=FMC_A10
|
PG0.Signal=FMC_A10
|
||||||
PG1.Signal=FMC_A11
|
PG1.Signal=FMC_A11
|
||||||
PG15.Signal=FMC_SDNCAS
|
PG15.Signal=FMC_SDNCAS
|
||||||
@@ -220,7 +246,7 @@ ProjectManager.ToolChainLocation=
|
|||||||
ProjectManager.UAScriptAfterPath=
|
ProjectManager.UAScriptAfterPath=
|
||||||
ProjectManager.UAScriptBeforePath=
|
ProjectManager.UAScriptBeforePath=
|
||||||
ProjectManager.UnderRoot=false
|
ProjectManager.UnderRoot=false
|
||||||
ProjectManager.functionlistsort=1-SystemClock_Config-RCC-false-HAL-false,2-MX_GPIO_Init-GPIO-false-HAL-true,3-MX_DMA_Init-DMA-false-HAL-true,4-MX_FMC_Init-FMC-false-HAL-true,5-MX_SDMMC1_SD_Init-SDMMC1-false-HAL-true,6-MX_USART1_UART_Init-USART1-false-HAL-true,7-MX_USART2_UART_Init-USART2-false-HAL-true,8-MX_LTDC_Init-LTDC-false-HAL-true,0-MX_CORTEX_M7_Init-CORTEX_M7-false-HAL-true
|
ProjectManager.functionlistsort=1-SystemClock_Config-RCC-false-HAL-false,2-MX_GPIO_Init-GPIO-false-HAL-true,3-MX_DMA_Init-DMA-false-HAL-true,4-MX_FMC_Init-FMC-false-HAL-true,5-MX_SDMMC1_SD_Init-SDMMC1-false-HAL-true,6-MX_USART1_UART_Init-USART1-false-HAL-true,7-MX_USART2_UART_Init-USART2-false-HAL-true,0-MX_CORTEX_M7_Init-CORTEX_M7-false-HAL-true
|
||||||
RCC.ADCFreq_Value=150000000
|
RCC.ADCFreq_Value=150000000
|
||||||
RCC.AHB12Freq_Value=240000000
|
RCC.AHB12Freq_Value=240000000
|
||||||
RCC.AHB4Freq_Value=240000000
|
RCC.AHB4Freq_Value=240000000
|
||||||
@@ -238,7 +264,7 @@ RCC.D1PPRE=RCC_APB3_DIV2
|
|||||||
RCC.D2PPRE1=RCC_APB1_DIV2
|
RCC.D2PPRE1=RCC_APB1_DIV2
|
||||||
RCC.D2PPRE2=RCC_APB2_DIV2
|
RCC.D2PPRE2=RCC_APB2_DIV2
|
||||||
RCC.D3PPRE=RCC_APB4_DIV2
|
RCC.D3PPRE=RCC_APB4_DIV2
|
||||||
RCC.DFSDMACLkFreq_Value=160000000
|
RCC.DFSDMACLkFreq_Value=120000000
|
||||||
RCC.DFSDMFreq_Value=120000000
|
RCC.DFSDMFreq_Value=120000000
|
||||||
RCC.DIVM1=4
|
RCC.DIVM1=4
|
||||||
RCC.DIVN1=60
|
RCC.DIVN1=60
|
||||||
@@ -246,14 +272,14 @@ RCC.DIVN2=150
|
|||||||
RCC.DIVP1Freq_Value=480000000
|
RCC.DIVP1Freq_Value=480000000
|
||||||
RCC.DIVP2Freq_Value=150000000
|
RCC.DIVP2Freq_Value=150000000
|
||||||
RCC.DIVP3Freq_Value=129000000
|
RCC.DIVP3Freq_Value=129000000
|
||||||
RCC.DIVQ1=6
|
RCC.DIVQ1=8
|
||||||
RCC.DIVQ1Freq_Value=160000000
|
RCC.DIVQ1Freq_Value=120000000
|
||||||
RCC.DIVQ2Freq_Value=150000000
|
RCC.DIVQ2Freq_Value=150000000
|
||||||
RCC.DIVQ3Freq_Value=129000000
|
RCC.DIVQ3Freq_Value=129000000
|
||||||
RCC.DIVR1Freq_Value=480000000
|
RCC.DIVR1Freq_Value=480000000
|
||||||
RCC.DIVR2Freq_Value=150000000
|
RCC.DIVR2Freq_Value=150000000
|
||||||
RCC.DIVR3Freq_Value=129000000
|
RCC.DIVR3Freq_Value=129000000
|
||||||
RCC.FDCANFreq_Value=160000000
|
RCC.FDCANFreq_Value=120000000
|
||||||
RCC.FMCFreq_Value=240000000
|
RCC.FMCFreq_Value=240000000
|
||||||
RCC.FamilyName=M
|
RCC.FamilyName=M
|
||||||
RCC.HCLK3ClockFreq_Value=240000000
|
RCC.HCLK3ClockFreq_Value=240000000
|
||||||
@@ -262,7 +288,7 @@ RCC.HPRE=RCC_HCLK_DIV2
|
|||||||
RCC.HRTIMFreq_Value=240000000
|
RCC.HRTIMFreq_Value=240000000
|
||||||
RCC.I2C123Freq_Value=120000000
|
RCC.I2C123Freq_Value=120000000
|
||||||
RCC.I2C4Freq_Value=120000000
|
RCC.I2C4Freq_Value=120000000
|
||||||
RCC.IPParameters=ADCFreq_Value,AHB12Freq_Value,AHB4Freq_Value,APB1Freq_Value,APB2Freq_Value,APB3Freq_Value,APB4Freq_Value,AXIClockFreq_Value,CECFreq_Value,CKPERFreq_Value,CortexFreq_Value,CpuClockFreq_Value,D1CPREFreq_Value,D1PPRE,D2PPRE1,D2PPRE2,D3PPRE,DFSDMACLkFreq_Value,DFSDMFreq_Value,DIVM1,DIVN1,DIVN2,DIVP1Freq_Value,DIVP2Freq_Value,DIVP3Freq_Value,DIVQ1,DIVQ1Freq_Value,DIVQ2Freq_Value,DIVQ3Freq_Value,DIVR1Freq_Value,DIVR2Freq_Value,DIVR3Freq_Value,FDCANFreq_Value,FMCFreq_Value,FamilyName,HCLK3ClockFreq_Value,HCLKFreq_Value,HPRE,HRTIMFreq_Value,I2C123Freq_Value,I2C4Freq_Value,LPTIM1Freq_Value,LPTIM2Freq_Value,LPTIM345Freq_Value,LPUART1Freq_Value,LTDCFreq_Value,MCO1PinFreq_Value,MCO2PinFreq_Value,PLL2FRACN,PLL3FRACN,PLLFRACN,QSPIFreq_Value,RNGFreq_Value,RTCFreq_Value,SAI1Freq_Value,SAI23Freq_Value,SAI4AFreq_Value,SAI4BFreq_Value,SDMMC1CLockSelection,SDMMCFreq_Value,SPDIFRXFreq_Value,SPI123Freq_Value,SPI45Freq_Value,SPI6Freq_Value,SWPMI1Freq_Value,SYSCLKFreq_VALUE,SYSCLKSource,Tim1OutputFreq_Value,Tim2OutputFreq_Value,TraceFreq_Value,USART16Freq_Value,USART234578Freq_Value,USBFreq_Value,VCO1OutputFreq_Value,VCO2OutputFreq_Value,VCO3OutputFreq_Value,VCOInput1Freq_Value,VCOInput2Freq_Value,VCOInput3Freq_Value
|
RCC.IPParameters=ADCFreq_Value,AHB12Freq_Value,AHB4Freq_Value,APB1Freq_Value,APB2Freq_Value,APB3Freq_Value,APB4Freq_Value,AXIClockFreq_Value,CECFreq_Value,CKPERFreq_Value,CortexFreq_Value,CpuClockFreq_Value,D1CPREFreq_Value,D1PPRE,D2PPRE1,D2PPRE2,D3PPRE,DFSDMACLkFreq_Value,DFSDMFreq_Value,DIVM1,DIVN1,DIVN2,DIVP1Freq_Value,DIVP2Freq_Value,DIVP3Freq_Value,DIVQ1,DIVQ1Freq_Value,DIVQ2Freq_Value,DIVQ3Freq_Value,DIVR1Freq_Value,DIVR2Freq_Value,DIVR3Freq_Value,FDCANFreq_Value,FMCFreq_Value,FamilyName,HCLK3ClockFreq_Value,HCLKFreq_Value,HPRE,HRTIMFreq_Value,I2C123Freq_Value,I2C4Freq_Value,LPTIM1Freq_Value,LPTIM2Freq_Value,LPTIM345Freq_Value,LPUART1Freq_Value,LTDCFreq_Value,MCO1PinFreq_Value,MCO2PinFreq_Value,PLL2FRACN,PLL3FRACN,PLLFRACN,QSPICLockSelection,QSPIFreq_Value,RNGFreq_Value,RTCFreq_Value,SAI1Freq_Value,SAI23Freq_Value,SAI4AFreq_Value,SAI4BFreq_Value,SDMMC1CLockSelection,SDMMCFreq_Value,SPDIFRXFreq_Value,SPI123Freq_Value,SPI45Freq_Value,SPI6Freq_Value,SWPMI1Freq_Value,SYSCLKFreq_VALUE,SYSCLKSource,Tim1OutputFreq_Value,Tim2OutputFreq_Value,TraceFreq_Value,USART16Freq_Value,USART234578Freq_Value,USBFreq_Value,VCO1OutputFreq_Value,VCO2OutputFreq_Value,VCO3OutputFreq_Value,VCOInput1Freq_Value,VCOInput2Freq_Value,VCOInput3Freq_Value
|
||||||
RCC.LPTIM1Freq_Value=120000000
|
RCC.LPTIM1Freq_Value=120000000
|
||||||
RCC.LPTIM2Freq_Value=120000000
|
RCC.LPTIM2Freq_Value=120000000
|
||||||
RCC.LPTIM345Freq_Value=120000000
|
RCC.LPTIM345Freq_Value=120000000
|
||||||
@@ -273,17 +299,18 @@ RCC.MCO2PinFreq_Value=480000000
|
|||||||
RCC.PLL2FRACN=0
|
RCC.PLL2FRACN=0
|
||||||
RCC.PLL3FRACN=0
|
RCC.PLL3FRACN=0
|
||||||
RCC.PLLFRACN=0
|
RCC.PLLFRACN=0
|
||||||
RCC.QSPIFreq_Value=240000000
|
RCC.QSPICLockSelection=RCC_QSPICLKSOURCE_PLL
|
||||||
|
RCC.QSPIFreq_Value=120000000
|
||||||
RCC.RNGFreq_Value=48000000
|
RCC.RNGFreq_Value=48000000
|
||||||
RCC.RTCFreq_Value=32000
|
RCC.RTCFreq_Value=32000
|
||||||
RCC.SAI1Freq_Value=160000000
|
RCC.SAI1Freq_Value=120000000
|
||||||
RCC.SAI23Freq_Value=160000000
|
RCC.SAI23Freq_Value=120000000
|
||||||
RCC.SAI4AFreq_Value=160000000
|
RCC.SAI4AFreq_Value=120000000
|
||||||
RCC.SAI4BFreq_Value=160000000
|
RCC.SAI4BFreq_Value=120000000
|
||||||
RCC.SDMMC1CLockSelection=RCC_SDMMCCLKSOURCE_PLL2
|
RCC.SDMMC1CLockSelection=RCC_SDMMCCLKSOURCE_PLL2
|
||||||
RCC.SDMMCFreq_Value=150000000
|
RCC.SDMMCFreq_Value=150000000
|
||||||
RCC.SPDIFRXFreq_Value=160000000
|
RCC.SPDIFRXFreq_Value=120000000
|
||||||
RCC.SPI123Freq_Value=160000000
|
RCC.SPI123Freq_Value=120000000
|
||||||
RCC.SPI45Freq_Value=120000000
|
RCC.SPI45Freq_Value=120000000
|
||||||
RCC.SPI6Freq_Value=120000000
|
RCC.SPI6Freq_Value=120000000
|
||||||
RCC.SWPMI1Freq_Value=120000000
|
RCC.SWPMI1Freq_Value=120000000
|
||||||
@@ -294,7 +321,7 @@ RCC.Tim2OutputFreq_Value=240000000
|
|||||||
RCC.TraceFreq_Value=64000000
|
RCC.TraceFreq_Value=64000000
|
||||||
RCC.USART16Freq_Value=120000000
|
RCC.USART16Freq_Value=120000000
|
||||||
RCC.USART234578Freq_Value=120000000
|
RCC.USART234578Freq_Value=120000000
|
||||||
RCC.USBFreq_Value=160000000
|
RCC.USBFreq_Value=120000000
|
||||||
RCC.VCO1OutputFreq_Value=960000000
|
RCC.VCO1OutputFreq_Value=960000000
|
||||||
RCC.VCO2OutputFreq_Value=300000000
|
RCC.VCO2OutputFreq_Value=300000000
|
||||||
RCC.VCO3OutputFreq_Value=258000000
|
RCC.VCO3OutputFreq_Value=258000000
|
||||||
|
|||||||
+1
-1
@@ -174,7 +174,7 @@ extern "C"
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
/*#define BSP_USING_QSPI*/
|
/*#define BSP_USING_QSPI*/
|
||||||
|
#define BSP_USING_QSPI
|
||||||
/*-------------------------- QSPI CONFIG END --------------------------*/
|
/*-------------------------- QSPI CONFIG END --------------------------*/
|
||||||
|
|
||||||
/*-------------------------- PWM CONFIG BEGIN --------------------------*/
|
/*-------------------------- PWM CONFIG BEGIN --------------------------*/
|
||||||
|
|||||||
@@ -0,0 +1,4 @@
|
|||||||
|
# GitHub really wants to mark littlefs as a python project, telling it to
|
||||||
|
# reclassify our test .toml files as C code (which they are 95% of anyways)
|
||||||
|
# remedies this
|
||||||
|
*.toml linguist-language=c
|
||||||
@@ -0,0 +1,34 @@
|
|||||||
|
# Compilation output
|
||||||
|
*.o
|
||||||
|
*.d
|
||||||
|
*.a
|
||||||
|
*.ci
|
||||||
|
*.csv
|
||||||
|
*.t.*
|
||||||
|
*.b.*
|
||||||
|
*.gcno
|
||||||
|
*.gcda
|
||||||
|
*.perf
|
||||||
|
lfs
|
||||||
|
liblfs.a
|
||||||
|
|
||||||
|
# Testing things
|
||||||
|
runners/test_runner
|
||||||
|
runners/bench_runner
|
||||||
|
lfs.code.csv
|
||||||
|
lfs.data.csv
|
||||||
|
lfs.stack.csv
|
||||||
|
lfs.structs.csv
|
||||||
|
lfs.cov.csv
|
||||||
|
lfs.perf.csv
|
||||||
|
lfs.perfbd.csv
|
||||||
|
lfs.test.csv
|
||||||
|
lfs.bench.csv
|
||||||
|
|
||||||
|
# Misc
|
||||||
|
tags
|
||||||
|
.gdb_history
|
||||||
|
scripts/__pycache__
|
||||||
|
|
||||||
|
# Historical, probably should remove at some point
|
||||||
|
tests/*.toml.*
|
||||||
Vendored
+2173
File diff suppressed because it is too large.
Load diff
Vendored
+25
@@ -0,0 +1,25 @@
|
|||||||
|
Copyright (c) 2022, The littlefs authors.
|
||||||
|
Copyright (c) 2017, Arm Limited. All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
- Redistributions of source code must retain the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer.
|
||||||
|
- Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
- Neither the name of ARM nor the names of its contributors may be used to
|
||||||
|
endorse or promote products derived from this software without specific prior
|
||||||
|
written permission.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
Vendored
+342
@@ -0,0 +1,342 @@
|
|||||||
|
## littlefs for RT-Thread
|
||||||
|
|
||||||
|
A little fail-safe filesystem designed for microcontrollers.
|
||||||
|
|
||||||
|
```
|
||||||
|
| | | .---._____
|
||||||
|
.-----. | |
|
||||||
|
--|o |---| littlefs |
|
||||||
|
--| |---| |
|
||||||
|
'-----' '----------'
|
||||||
|
| | |
|
||||||
|
```
|
||||||
|
|
||||||
|
**Power-loss resilience** - littlefs is designed to handle random power
|
||||||
|
failures. All file operations have strong copy-on-write guarantees and if
|
||||||
|
power is lost the filesystem will fall back to the last known good state.
|
||||||
|
|
||||||
|
**Dynamic wear leveling** - littlefs is designed with flash in mind, and
|
||||||
|
provides wear leveling over dynamic blocks. Additionally, littlefs can
|
||||||
|
detect bad blocks and work around them.
|
||||||
|
|
||||||
|
**Bounded RAM/ROM** - littlefs is designed to work with a small amount of
|
||||||
|
memory. RAM usage is strictly bounded, which means RAM consumption does not
|
||||||
|
change as the filesystem grows. The filesystem contains no unbounded
|
||||||
|
recursion and dynamic memory is limited to configurable buffers that can be
|
||||||
|
provided statically.
|
||||||
|
|
||||||
|
## Example
|
||||||
|
|
||||||
|
Here's a simple example that updates a file named `boot_count` every time
|
||||||
|
main runs. The program can be interrupted at any time without losing track
|
||||||
|
of how many times it has been booted and without corrupting the filesystem:
|
||||||
|
|
||||||
|
``` c
|
||||||
|
#include "lfs.h"
|
||||||
|
|
||||||
|
// variables used by the filesystem
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_file_t file;
|
||||||
|
|
||||||
|
// configuration of the filesystem is provided by this struct
|
||||||
|
const struct lfs_config cfg = {
|
||||||
|
// block device operations
|
||||||
|
.read = user_provided_block_device_read,
|
||||||
|
.prog = user_provided_block_device_prog,
|
||||||
|
.erase = user_provided_block_device_erase,
|
||||||
|
.sync = user_provided_block_device_sync,
|
||||||
|
|
||||||
|
// block device configuration
|
||||||
|
.read_size = 16,
|
||||||
|
.prog_size = 16,
|
||||||
|
.block_size = 4096,
|
||||||
|
.block_count = 128,
|
||||||
|
.cache_size = 16,
|
||||||
|
.lookahead_size = 16,
|
||||||
|
.block_cycles = 500,
|
||||||
|
};
|
||||||
|
|
||||||
|
// entry point
|
||||||
|
int main(void) {
|
||||||
|
// mount the filesystem
|
||||||
|
int err = lfs_mount(&lfs, &cfg);
|
||||||
|
|
||||||
|
// reformat if we can't mount the filesystem
|
||||||
|
// this should only happen on the first boot
|
||||||
|
if (err) {
|
||||||
|
lfs_format(&lfs, &cfg);
|
||||||
|
lfs_mount(&lfs, &cfg);
|
||||||
|
}
|
||||||
|
|
||||||
|
// read current count
|
||||||
|
uint32_t boot_count = 0;
|
||||||
|
lfs_file_open(&lfs, &file, "boot_count", LFS_O_RDWR | LFS_O_CREAT);
|
||||||
|
lfs_file_read(&lfs, &file, &boot_count, sizeof(boot_count));
|
||||||
|
|
||||||
|
// update boot count
|
||||||
|
boot_count += 1;
|
||||||
|
lfs_file_rewind(&lfs, &file);
|
||||||
|
lfs_file_write(&lfs, &file, &boot_count, sizeof(boot_count));
|
||||||
|
|
||||||
|
// remember the storage is not updated until the file is closed successfully
|
||||||
|
lfs_file_close(&lfs, &file);
|
||||||
|
|
||||||
|
// release any resources we were using
|
||||||
|
lfs_unmount(&lfs);
|
||||||
|
|
||||||
|
// print the boot count
|
||||||
|
printf("boot_count: %d\n", boot_count);
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
## Usage
|
||||||
|
|
||||||
|
Detailed documentation (or at least as much detail as is currently available)
|
||||||
|
can be found in the comments in [lfs.h](lfs.h).
|
||||||
|
|
||||||
|
littlefs takes in a configuration structure that defines how the filesystem
|
||||||
|
operates. The configuration struct provides the filesystem with the block
|
||||||
|
device operations and dimensions, tweakable parameters that tradeoff memory
|
||||||
|
usage for performance, and optional static buffers if the user wants to avoid
|
||||||
|
dynamic memory.
|
||||||
|
|
||||||
|
The state of the littlefs is stored in the `lfs_t` type which is left up
|
||||||
|
to the user to allocate, allowing multiple filesystems to be in use
|
||||||
|
simultaneously. With the `lfs_t` and configuration struct, a user can
|
||||||
|
format a block device or mount the filesystem.
|
||||||
|
|
||||||
|
Once mounted, the littlefs provides a full set of POSIX-like file and
|
||||||
|
directory functions, with the deviation that the allocation of filesystem
|
||||||
|
structures must be provided by the user.
|
||||||
|
|
||||||
|
All POSIX operations, such as remove and rename, are atomic, even in event
|
||||||
|
of power-loss. Additionally, file updates are not actually committed to
|
||||||
|
the filesystem until sync or close is called on the file.
|
||||||
|
|
||||||
|
## Other notes
|
||||||
|
|
||||||
|
Littlefs is written in C, and specifically should compile with any compiler
|
||||||
|
that conforms to the `C99` standard.
|
||||||
|
|
||||||
|
All littlefs calls have the potential to return a negative error code. The
|
||||||
|
errors can be either one of those found in the `enum lfs_error` in
|
||||||
|
[lfs.h](lfs.h), or an error returned by the user's block device operations.
|
||||||
|
|
||||||
|
In the configuration struct, the `prog` and `erase` function provided by the
|
||||||
|
user may return a `LFS_ERR_CORRUPT` error if the implementation already can
|
||||||
|
detect corrupt blocks. However, the wear leveling does not depend on the return
|
||||||
|
code of these functions, instead all data is read back and checked for
|
||||||
|
integrity.
|
||||||
|
|
||||||
|
If your storage caches writes, make sure that the provided `sync` function
|
||||||
|
flushes all the data to memory and ensures that the next read fetches the data
|
||||||
|
from memory, otherwise data integrity can not be guaranteed. If the `write`
|
||||||
|
function does not perform caching, and therefore each `read` or `write` call
|
||||||
|
hits the memory, the `sync` function can simply return 0.
|
||||||
|
|
||||||
|
## Design
|
||||||
|
|
||||||
|
At a high level, littlefs is a block based filesystem that uses small logs to
|
||||||
|
store metadata and larger copy-on-write (COW) structures to store file data.
|
||||||
|
|
||||||
|
In littlefs, these ingredients form a sort of two-layered cake, with the small
|
||||||
|
logs (called metadata pairs) providing fast updates to metadata anywhere on
|
||||||
|
storage, while the COW structures store file data compactly and without any
|
||||||
|
wear amplification cost.
|
||||||
|
|
||||||
|
Both of these data structures are built out of blocks, which are fed by a
|
||||||
|
common block allocator. By limiting the number of erases allowed on a block
|
||||||
|
per allocation, the allocator provides dynamic wear leveling over the entire
|
||||||
|
filesystem.
|
||||||
|
|
||||||
|
```
|
||||||
|
root
|
||||||
|
.--------.--------.
|
||||||
|
| A'| B'| |
|
||||||
|
| | |-> |
|
||||||
|
| | | |
|
||||||
|
'--------'--------'
|
||||||
|
.----' '--------------.
|
||||||
|
A v B v
|
||||||
|
.--------.--------. .--------.--------.
|
||||||
|
| C'| D'| | | E'|new| |
|
||||||
|
| | |-> | | | E'|-> |
|
||||||
|
| | | | | | | |
|
||||||
|
'--------'--------' '--------'--------'
|
||||||
|
.-' '--. | '------------------.
|
||||||
|
v v .-' v
|
||||||
|
.--------. .--------. v .--------.
|
||||||
|
| C | | D | .--------. write | new E |
|
||||||
|
| | | | | E | ==> | |
|
||||||
|
| | | | | | | |
|
||||||
|
'--------' '--------' | | '--------'
|
||||||
|
'--------' .-' |
|
||||||
|
.-' '-. .-------------|------'
|
||||||
|
v v v v
|
||||||
|
.--------. .--------. .--------.
|
||||||
|
| F | | G | | new F |
|
||||||
|
| | | | | |
|
||||||
|
| | | | | |
|
||||||
|
'--------' '--------' '--------'
|
||||||
|
```
|
||||||
|
|
||||||
|
More details on how littlefs works can be found in [DESIGN.md](DESIGN.md) and
|
||||||
|
[SPEC.md](SPEC.md).
|
||||||
|
|
||||||
|
- [DESIGN.md](DESIGN.md) - A fully detailed dive into how littlefs works.
|
||||||
|
I would suggest reading it as the tradeoffs at work are quite interesting.
|
||||||
|
|
||||||
|
- [SPEC.md](SPEC.md) - The on-disk specification of littlefs with all the
|
||||||
|
nitty-gritty details. May be useful for tooling development.
|
||||||
|
|
||||||
|
## Testing
|
||||||
|
|
||||||
|
The littlefs comes with a test suite designed to run on a PC using the
|
||||||
|
[emulated block device](bd/lfs_testbd.h) found in the `bd` directory.
|
||||||
|
The tests assume a Linux environment and can be started with make:
|
||||||
|
|
||||||
|
``` bash
|
||||||
|
make test
|
||||||
|
```
|
||||||
|
|
||||||
|
Tests are implemented in C in the .toml files found in the `tests` directory.
|
||||||
|
When developing a feature or fixing a bug, it is frequently useful to run a
|
||||||
|
single test case or suite of tests:
|
||||||
|
|
||||||
|
``` bash
|
||||||
|
./scripts/test.py -l runners/test_runner # list available test suites
|
||||||
|
./scripts/test.py -L runners/test_runner test_dirs # list available test cases
|
||||||
|
./scripts/test.py runners/test_runner test_dirs # run a specific test suite
|
||||||
|
```
|
||||||
|
|
||||||
|
If an assert fails in a test, test.py will try to print information about the
|
||||||
|
failure:
|
||||||
|
|
||||||
|
``` bash
|
||||||
|
tests/test_dirs.toml:1:failure: test_dirs_root:1g12gg2 (PROG_SIZE=16, ERASE_SIZE=512) failed
|
||||||
|
tests/test_dirs.toml:5:assert: assert failed with 0, expected eq 42
|
||||||
|
lfs_mount(&lfs, cfg) => 42;
|
||||||
|
```
|
||||||
|
|
||||||
|
This includes the test id, which can be passed to test.py to run only that
|
||||||
|
specific test permutation:
|
||||||
|
|
||||||
|
``` bash
|
||||||
|
./scripts/test.py runners/test_runner test_dirs_root:1g12gg2 # run a specific test permutation
|
||||||
|
./scripts/test.py runners/test_runner test_dirs_root:1g12gg2 --gdb # drop into gdb on failure
|
||||||
|
```
|
||||||
|
|
||||||
|
Some other flags that may be useful:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
./scripts/test.py runners/test_runner -b -j # run tests in parallel
|
||||||
|
./scripts/test.py runners/test_runner -v -O- # redirect stdout to stdout
|
||||||
|
./scripts/test.py runners/test_runner -ddisk # capture resulting disk image
|
||||||
|
```
|
||||||
|
|
||||||
|
See `-h/--help` for a full list of available flags:
|
||||||
|
|
||||||
|
``` bash
|
||||||
|
./scripts/test.py --help
|
||||||
|
```
|
||||||
|
|
||||||
|
## License
|
||||||
|
|
||||||
|
The littlefs is provided under the [BSD-3-Clause] license. See
|
||||||
|
[LICENSE.md](LICENSE.md) for more information. Contributions to this project
|
||||||
|
are accepted under the same license.
|
||||||
|
|
||||||
|
Individual files contain the following tag instead of the full license text.
|
||||||
|
|
||||||
|
SPDX-License-Identifier: BSD-3-Clause
|
||||||
|
|
||||||
|
This enables machine processing of license information based on the SPDX
|
||||||
|
License Identifiers that are here available: http://spdx.org/licenses/
|
||||||
|
|
||||||
|
## Related projects
|
||||||
|
|
||||||
|
- [littlefs-fuse] - A [FUSE] wrapper for littlefs. The project allows you to
|
||||||
|
mount littlefs directly on a Linux machine. Can be useful for debugging
|
||||||
|
littlefs if you have an SD card handy.
|
||||||
|
|
||||||
|
- [littlefs-js] - A javascript wrapper for littlefs. I'm not sure why you would
|
||||||
|
want this, but it is handy for demos. You can see it in action
|
||||||
|
[here][littlefs-js-demo].
|
||||||
|
|
||||||
|
- [littlefs-python] - A Python wrapper for littlefs. The project allows you
|
||||||
|
to create images of the filesystem on your PC. Check if littlefs will fit
|
||||||
|
your needs, create images for a later download to the target memory or
|
||||||
|
inspect the content of a binary image of the target memory.
|
||||||
|
|
||||||
|
- [littlefs-toy] - A command-line tool for creating and working with littlefs
|
||||||
|
images. Uses syntax similar to tar command for ease of use. Supports working
|
||||||
|
on littlefs images embedded inside another file (firmware image, etc).
|
||||||
|
|
||||||
|
- [littlefs2-rust] - A Rust wrapper for littlefs. This project allows you
|
||||||
|
to use littlefs in a Rust-friendly API, reaping the benefits of Rust's memory
|
||||||
|
safety and other guarantees.
|
||||||
|
|
||||||
|
- [nim-littlefs] - A Nim wrapper and API for littlefs. Includes a fuse
|
||||||
|
implementation based on [littlefs-fuse]
|
||||||
|
|
||||||
|
- [chamelon] - A pure-OCaml implementation of (most of) littlefs, designed for
|
||||||
|
use with the MirageOS library operating system project. It is interoperable
|
||||||
|
with the reference implementation, with some caveats.
|
||||||
|
|
||||||
|
- [littlefs-disk-img-viewer] - A memory-efficient web application for viewing
|
||||||
|
littlefs disk images in your web browser.
|
||||||
|
|
||||||
|
- [mklfs] - A command line tool for creating littlefs images. Used in the Lua
|
||||||
|
RTOS ecosystem.
|
||||||
|
|
||||||
|
- [mklittlefs] - A command line tool for creating littlefs images. Used in the
|
||||||
|
ESP8266 and RP2040 ecosystem.
|
||||||
|
|
||||||
|
- [pico-littlefs-usb] - An interface for littlefs that emulates a FAT12
|
||||||
|
filesystem over USB. Allows mounting littlefs on a host PC without additional
|
||||||
|
drivers.
|
||||||
|
|
||||||
|
- [ramcrc32bd] - An example block device using littlefs's 32-bit CRC for
|
||||||
|
error-correction.
|
||||||
|
|
||||||
|
- [ramrsbd] - An example block device using Reed-Solomon codes for
|
||||||
|
error-correction.
|
||||||
|
|
||||||
|
- [Mbed OS] - The easiest way to get started with littlefs is to jump into Mbed
|
||||||
|
which already has block device drivers for most forms of embedded storage.
|
||||||
|
littlefs is available in Mbed OS as the [LittleFileSystem] class.
|
||||||
|
|
||||||
|
- [SPIFFS] - Another excellent embedded filesystem for NOR flash. As a more
|
||||||
|
traditional logging filesystem with full static wear-leveling, SPIFFS will
|
||||||
|
likely outperform littlefs on small memories such as the internal flash on
|
||||||
|
microcontrollers.
|
||||||
|
|
||||||
|
- [Dhara] - An interesting NAND flash translation layer designed for small
|
||||||
|
MCUs. It offers static wear-leveling and power-resilience with only a fixed
|
||||||
|
_O(|address|)_ pointer structure stored on each block and in RAM.
|
||||||
|
|
||||||
|
- [ChaN's FatFs] - A lightweight reimplementation of the infamous FAT filesystem
|
||||||
|
for microcontroller-scale devices. Due to limitations of FAT it can't provide
|
||||||
|
power-loss resilience, but it does allow easy interop with PCs.
|
||||||
|
|
||||||
|
[BSD-3-Clause]: https://spdx.org/licenses/BSD-3-Clause.html
|
||||||
|
[littlefs-fuse]: https://github.com/geky/littlefs-fuse
|
||||||
|
[FUSE]: https://github.com/libfuse/libfuse
|
||||||
|
[littlefs-js]: https://github.com/geky/littlefs-js
|
||||||
|
[littlefs-js-demo]:http://littlefs.geky.net/demo.html
|
||||||
|
[littlefs-python]: https://pypi.org/project/littlefs-python/
|
||||||
|
[littlefs-toy]: https://github.com/tjko/littlefs-toy
|
||||||
|
[littlefs2-rust]: https://crates.io/crates/littlefs2
|
||||||
|
[nim-littlefs]: https://github.com/Graveflo/nim-littlefs
|
||||||
|
[chamelon]: https://github.com/yomimono/chamelon
|
||||||
|
[littlefs-disk-img-viewer]: https://github.com/tniessen/littlefs-disk-img-viewer
|
||||||
|
[mklfs]: https://github.com/whitecatboard/Lua-RTOS-ESP32/tree/master/components/mklfs/src
|
||||||
|
[mklittlefs]: https://github.com/earlephilhower/mklittlefs
|
||||||
|
[pico-littlefs-usb]: https://github.com/oyama/pico-littlefs-usb
|
||||||
|
[ramcrc32bd]: https://github.com/geky/ramcrc32bd
|
||||||
|
[ramrsbd]: https://github.com/geky/ramrsbd
|
||||||
|
[Mbed OS]: https://github.com/armmbed/mbed-os
|
||||||
|
[LittleFileSystem]: https://os.mbed.com/docs/mbed-os/latest/apis/littlefilesystem.html
|
||||||
|
[SPIFFS]: https://github.com/pellepl/spiffs
|
||||||
|
[Dhara]: https://github.com/dlbeer/dhara
|
||||||
|
[ChaN's FatFs]: http://elm-chan.org/fsw/ff/00index_e.html
|
||||||
Vendored
+25
@@ -0,0 +1,25 @@
|
|||||||
|
# RT-Thread building script for component
|
||||||
|
|
||||||
|
import os
|
||||||
|
import shutil
|
||||||
|
|
||||||
|
from building import *
|
||||||
|
|
||||||
|
cwd = GetCurrentDir()
|
||||||
|
src = Glob('*.c') + Glob('*.cpp')
|
||||||
|
CPPPATH = [cwd]
|
||||||
|
CPPDEFINES = ['LFS_CONFIG=lfs_config.h']
|
||||||
|
|
||||||
|
#delate non-used files
|
||||||
|
try:
|
||||||
|
shutil.rmtree(os.path.join(cwd,'.github'))
|
||||||
|
shutil.rmtree(os.path.join(cwd,'bd'))
|
||||||
|
shutil.rmtree(os.path.join(cwd,'scripts'))
|
||||||
|
shutil.rmtree(os.path.join(cwd,'tests'))
|
||||||
|
os.remove(os.path.join(cwd,'Makefile'))
|
||||||
|
except:
|
||||||
|
pass
|
||||||
|
|
||||||
|
group = DefineGroup('littlefs', src, depend = ['PKG_USING_LITTLEFS', 'RT_USING_DFS'], CPPPATH = CPPPATH, CPPDEFINES = CPPDEFINES)
|
||||||
|
|
||||||
|
Return('group')
|
||||||
Vendored
+867
@@ -0,0 +1,867 @@
|
|||||||
|
## littlefs technical specification
|
||||||
|
|
||||||
|
This is the technical specification of the little filesystem with on-disk
|
||||||
|
version lfs2.1. This document covers the technical details of how the littlefs
|
||||||
|
is stored on disk for introspection and tooling. This document assumes you are
|
||||||
|
familiar with the design of the littlefs, for more info on how littlefs works
|
||||||
|
check out [DESIGN.md](DESIGN.md).
|
||||||
|
|
||||||
|
```
|
||||||
|
| | | .---._____
|
||||||
|
.-----. | |
|
||||||
|
--|o |---| littlefs |
|
||||||
|
--| |---| |
|
||||||
|
'-----' '----------'
|
||||||
|
| | |
|
||||||
|
```
|
||||||
|
|
||||||
|
## Some quick notes
|
||||||
|
|
||||||
|
- littlefs is a block-based filesystem. The disk is divided into an array of
|
||||||
|
evenly sized blocks that are used as the logical unit of storage.
|
||||||
|
|
||||||
|
- Block pointers are stored in 32 bits, with the special value `0xffffffff`
|
||||||
|
representing a null block address.
|
||||||
|
|
||||||
|
- In addition to the logical block size (which usually matches the erase
|
||||||
|
block size), littlefs also uses a program block size and read block size.
|
||||||
|
These determine the alignment of block device operations, but don't need
|
||||||
|
to be consistent for portability.
|
||||||
|
|
||||||
|
- By default, all values in littlefs are stored in little-endian byte order.
|
||||||
|
|
||||||
|
## Directories / Metadata pairs
|
||||||
|
|
||||||
|
Metadata pairs form the backbone of littlefs and provide a system for
|
||||||
|
distributed atomic updates. Even the superblock is stored in a metadata pair.
|
||||||
|
|
||||||
|
As their name suggests, a metadata pair is stored in two blocks, with one block
|
||||||
|
providing a backup during erase cycles in case power is lost. These two blocks
|
||||||
|
are not necessarily sequential and may be anywhere on disk, so a "pointer" to a
|
||||||
|
metadata pair is stored as two block pointers.
|
||||||
|
|
||||||
|
On top of this, each metadata block behaves as an appendable log, containing a
|
||||||
|
variable number of commits. Commits can be appended to the metadata log in
|
||||||
|
order to update the metadata without requiring an erase cycles. Note that
|
||||||
|
successive commits may supersede the metadata in previous commits. Only the
|
||||||
|
most recent metadata should be considered valid.
|
||||||
|
|
||||||
|
The high-level layout of a metadata block is fairly simple:
|
||||||
|
|
||||||
|
```
|
||||||
|
.---------------------------------------.
|
||||||
|
.-| revision count | entries | \
|
||||||
|
| |-------------------+ | |
|
||||||
|
| | | |
|
||||||
|
| | | +-- 1st commit
|
||||||
|
| | | |
|
||||||
|
| | +-------------------| |
|
||||||
|
| | | CRC | /
|
||||||
|
| |-------------------+-------------------|
|
||||||
|
| | entries | \
|
||||||
|
| | | |
|
||||||
|
| | | +-- 2nd commit
|
||||||
|
| | +-------------------+--------------| |
|
||||||
|
| | | CRC | padding | /
|
||||||
|
| |----+-------------------+--------------|
|
||||||
|
| | entries | \
|
||||||
|
| | | |
|
||||||
|
| | | +-- 3rd commit
|
||||||
|
| | +-------------------+---------| |
|
||||||
|
| | | CRC | | /
|
||||||
|
| |---------+-------------------+ |
|
||||||
|
| | unwritten storage | more commits
|
||||||
|
| | | |
|
||||||
|
| | | v
|
||||||
|
| | |
|
||||||
|
| | |
|
||||||
|
| '---------------------------------------'
|
||||||
|
'---------------------------------------'
|
||||||
|
```
|
||||||
|
|
||||||
|
Each metadata block contains a 32-bit revision count followed by a number of
|
||||||
|
commits. Each commit contains a variable number of metadata entries followed
|
||||||
|
by a 32-bit CRC.
|
||||||
|
|
||||||
|
Note also that entries aren't necessarily word-aligned. This allows us to
|
||||||
|
store metadata more compactly, however we can only write to addresses that are
|
||||||
|
aligned to our program block size. This means each commit may have padding for
|
||||||
|
alignment.
|
||||||
|
|
||||||
|
Metadata block fields:
|
||||||
|
|
||||||
|
1. **Revision count (32-bits)** - Incremented every erase cycle. If both blocks
|
||||||
|
contain valid commits, only the block with the most recent revision count
|
||||||
|
should be used. Sequence comparison must be used to avoid issues with
|
||||||
|
integer overflow.
|
||||||
|
|
||||||
|
2. **CRC (32-bits)** - Detects corruption from power-loss or other write
|
||||||
|
issues. Uses a CRC-32 with a polynomial of `0x04c11db7` initialized
|
||||||
|
with `0xffffffff`.
|
||||||
|
|
||||||
|
Entries themselves are stored as a 32-bit tag followed by a variable length
|
||||||
|
blob of data. But exactly how these tags are stored is a little bit tricky.
|
||||||
|
|
||||||
|
Metadata blocks support both forward and backward iteration. In order to do
|
||||||
|
this without duplicating the space for each tag, neighboring entries have their
|
||||||
|
tags XORed together, starting with `0xffffffff`.
|
||||||
|
|
||||||
|
```
|
||||||
|
Forward iteration Backward iteration
|
||||||
|
|
||||||
|
.-------------------. 0xffffffff .-------------------.
|
||||||
|
| revision count | | | revision count |
|
||||||
|
|-------------------| v |-------------------|
|
||||||
|
| tag ~A |---> xor -> tag A | tag ~A |---> xor -> 0xffffffff
|
||||||
|
|-------------------| | |-------------------| ^
|
||||||
|
| data A | | | data A | |
|
||||||
|
| | | | | |
|
||||||
|
| | | | | |
|
||||||
|
|-------------------| v |-------------------| |
|
||||||
|
| tag AxB |---> xor -> tag B | tag AxB |---> xor -> tag A
|
||||||
|
|-------------------| | |-------------------| ^
|
||||||
|
| data B | | | data B | |
|
||||||
|
| | | | | |
|
||||||
|
| | | | | |
|
||||||
|
|-------------------| v |-------------------| |
|
||||||
|
| tag BxC |---> xor -> tag C | tag BxC |---> xor -> tag B
|
||||||
|
|-------------------| |-------------------| ^
|
||||||
|
| data C | | data C | |
|
||||||
|
| | | | tag C
|
||||||
|
| | | |
|
||||||
|
| | | |
|
||||||
|
'-------------------' '-------------------'
|
||||||
|
```
|
||||||
|
|
||||||
|
Here's a more complete example of metadata block containing 4 entries:
|
||||||
|
|
||||||
|
```
|
||||||
|
.---------------------------------------.
|
||||||
|
.-| revision count | tag ~A | \
|
||||||
|
| |-------------------+-------------------| |
|
||||||
|
| | data A | |
|
||||||
|
| | | |
|
||||||
|
| |-------------------+-------------------| |
|
||||||
|
| | tag AxB | data B | <--. |
|
||||||
|
| |-------------------+ | | |
|
||||||
|
| | | | +-- 1st commit
|
||||||
|
| | +-------------------+---------| | |
|
||||||
|
| | | tag BxC | | <-.| |
|
||||||
|
| |---------+-------------------+ | || |
|
||||||
|
| | data C | || |
|
||||||
|
| | | || |
|
||||||
|
| |-------------------+-------------------| || |
|
||||||
|
| | tag CxCRC | CRC | || /
|
||||||
|
| |-------------------+-------------------| ||
|
||||||
|
| | tag CRCxA' | data A' | || \
|
||||||
|
| |-------------------+ | || |
|
||||||
|
| | | || |
|
||||||
|
| | +-------------------+----| || +-- 2nd commit
|
||||||
|
| | | tag CRCxA' | | || |
|
||||||
|
| |--------------+-------------------+----| || |
|
||||||
|
| | CRC | padding | || /
|
||||||
|
| |--------------+----+-------------------| ||
|
||||||
|
| | tag CRCxA'' | data A'' | <---. \
|
||||||
|
| |-------------------+ | ||| |
|
||||||
|
| | | ||| |
|
||||||
|
| | +-------------------+---------| ||| |
|
||||||
|
| | | tag A''xD | | < ||| |
|
||||||
|
| |---------+-------------------+ | |||| +-- 3rd commit
|
||||||
|
| | data D | |||| |
|
||||||
|
| | +---------| |||| |
|
||||||
|
| | | tag Dx| |||| |
|
||||||
|
| |---------+-------------------+---------| |||| |
|
||||||
|
| |CRC | CRC | | |||| /
|
||||||
|
| |---------+-------------------+ | ||||
|
||||||
|
| | unwritten storage | |||| more commits
|
||||||
|
| | | |||| |
|
||||||
|
| | | |||| v
|
||||||
|
| | | ||||
|
||||||
|
| | | ||||
|
||||||
|
| '---------------------------------------' ||||
|
||||||
|
'---------------------------------------' |||'- most recent A
|
||||||
|
||'-- most recent B
|
||||||
|
|'--- most recent C
|
||||||
|
'---- most recent D
|
||||||
|
```
|
||||||
|
|
||||||
|
Two things to note before we get into the details around tag encoding:
|
||||||
|
|
||||||
|
1. Each tag contains a valid bit used to indicate if the tag and containing
|
||||||
|
commit is valid. After XORing, this bit should always be zero.
|
||||||
|
|
||||||
|
At the end of each commit, the valid bit of the previous tag is XORed
|
||||||
|
with the lowest bit in the type field of the CRC tag. This allows
|
||||||
|
the CRC tag to force the next commit to fail the valid bit test if it
|
||||||
|
has not yet been written to.
|
||||||
|
|
||||||
|
2. The valid bit alone is not enough info to know if the next commit has been
|
||||||
|
erased. We don't know the order bits will be programmed in a program block,
|
||||||
|
so it's possible that the next commit had an attempted program that left the
|
||||||
|
valid bit unchanged.
|
||||||
|
|
||||||
|
To ensure we only ever program erased bytes, each commit can contain an
|
||||||
|
optional forward-CRC (FCRC). An FCRC contains a checksum of some amount of
|
||||||
|
bytes in the next commit at the time it was erased.
|
||||||
|
|
||||||
|
```
|
||||||
|
.-------------------. \ \
|
||||||
|
| revision count | | |
|
||||||
|
|-------------------| | |
|
||||||
|
| metadata | | |
|
||||||
|
| | +---. +-- current commit
|
||||||
|
| | | | |
|
||||||
|
|-------------------| | | |
|
||||||
|
| FCRC ---|-. | |
|
||||||
|
|-------------------| / | | |
|
||||||
|
| CRC -----|-' /
|
||||||
|
|-------------------| |
|
||||||
|
| padding | | padding (does't need CRC)
|
||||||
|
| | |
|
||||||
|
|-------------------| \ | \
|
||||||
|
| erased? | +-' |
|
||||||
|
| | | | +-- next commit
|
||||||
|
| v | / |
|
||||||
|
| | /
|
||||||
|
| |
|
||||||
|
'-------------------'
|
||||||
|
```
|
||||||
|
|
||||||
|
If the FCRC is missing or the checksum does not match, we must assume a
|
||||||
|
commit was attempted but failed due to power-loss.
|
||||||
|
|
||||||
|
Note that end-of-block commits do not need an FCRC.
|
||||||
|
|
||||||
|
## Metadata tags
|
||||||
|
|
||||||
|
So in littlefs, 32-bit tags describe every type of metadata. And this means
|
||||||
|
_every_ type of metadata, including file entries, directory fields, and
|
||||||
|
global state. Even the CRCs used to mark the end of commits get their own tag.
|
||||||
|
|
||||||
|
Because of this, the tag format contains some densely packed information. Note
|
||||||
|
that there are multiple levels of types which break down into more info:
|
||||||
|
|
||||||
|
```
|
||||||
|
[---- 32 ----]
|
||||||
|
[1|-- 11 --|-- 10 --|-- 10 --]
|
||||||
|
^. ^ . ^ ^- length
|
||||||
|
|. | . '------------ id
|
||||||
|
|. '-----.------------------ type (type3)
|
||||||
|
'.-----------.------------------ valid bit
|
||||||
|
[-3-|-- 8 --]
|
||||||
|
^ ^- chunk
|
||||||
|
'------- type (type1)
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
|
Before we go further, there's one important thing to note. These tags are
|
||||||
|
**not** stored in little-endian. Tags stored in commits are actually stored
|
||||||
|
in big-endian (and is the only thing in littlefs stored in big-endian). This
|
||||||
|
little bit of craziness comes from the fact that the valid bit must be the
|
||||||
|
first bit in a commit, and when converted to little-endian, the valid bit finds
|
||||||
|
itself in byte 4. We could restructure the tag to store the valid bit lower,
|
||||||
|
but, because none of the fields are byte-aligned, this would be more
|
||||||
|
complicated than just storing the tag in big-endian.
|
||||||
|
|
||||||
|
Another thing to note is that both the tags `0x00000000` and `0xffffffff` are
|
||||||
|
invalid and can be used for null values.
|
||||||
|
|
||||||
|
Metadata tag fields:
|
||||||
|
|
||||||
|
1. **Valid bit (1-bit)** - Indicates if the tag is valid.
|
||||||
|
|
||||||
|
2. **Type3 (11-bits)** - Type of the tag. This field is broken down further
|
||||||
|
into a 3-bit abstract type and an 8-bit chunk field. Note that the value
|
||||||
|
`0x000` is invalid and not assigned a type.
|
||||||
|
|
||||||
|
1. **Type1 (3-bits)** - Abstract type of the tag. Groups the tags into
|
||||||
|
8 categories that facilitate bitmasked lookups.
|
||||||
|
|
||||||
|
2. **Chunk (8-bits)** - Chunk field used for various purposes by the different
|
||||||
|
abstract types. type1+chunk+id form a unique identifier for each tag in the
|
||||||
|
metadata block.
|
||||||
|
|
||||||
|
3. **Id (10-bits)** - File id associated with the tag. Each file in a metadata
|
||||||
|
block gets a unique id which is used to associate tags with that file. The
|
||||||
|
special value `0x3ff` is used for any tags that are not associated with a
|
||||||
|
file, such as directory and global metadata.
|
||||||
|
|
||||||
|
4. **Length (10-bits)** - Length of the data in bytes. The special value
|
||||||
|
`0x3ff` indicates that this tag has been deleted.
|
||||||
|
|
||||||
|
## Metadata types
|
||||||
|
|
||||||
|
What follows is an exhaustive list of metadata in littlefs.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x401` LFS_TYPE_CREATE
|
||||||
|
|
||||||
|
Creates a new file with this id. Note that files in a metadata block
|
||||||
|
don't necessarily need a create tag. All a create does is move over any
|
||||||
|
files using this id. In this sense a create is similar to insertion into
|
||||||
|
an imaginary array of files.
|
||||||
|
|
||||||
|
The create and delete tags allow littlefs to keep files in a directory
|
||||||
|
ordered alphabetically by filename.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x4ff` LFS_TYPE_DELETE
|
||||||
|
|
||||||
|
Deletes the file with this id. An inverse to create, this tag moves over
|
||||||
|
any files neighboring this id similar to a deletion from an imaginary
|
||||||
|
array of files.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x0xx` LFS_TYPE_NAME
|
||||||
|
|
||||||
|
Associates the id with a file name and file type.
|
||||||
|
|
||||||
|
The data contains the file name stored as an ASCII string (may be expanded to
|
||||||
|
UTF8 in the future).
|
||||||
|
|
||||||
|
The chunk field in this tag indicates an 8-bit file type which can be one of
|
||||||
|
the following.
|
||||||
|
|
||||||
|
Currently, the name tag must precede any other tags associated with the id and
|
||||||
|
can not be reassigned without deleting the file.
|
||||||
|
|
||||||
|
Layout of the name tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][--- variable length ---]
|
||||||
|
[1| 3| 8 | 10 | 10 ][--- (size * 8) ---]
|
||||||
|
^ ^ ^ ^ ^- size ^- file name
|
||||||
|
| | | '------ id
|
||||||
|
| | '----------- file type
|
||||||
|
| '-------------- type1 (0x0)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
Name fields:
|
||||||
|
|
||||||
|
1. **file type (8-bits)** - Type of the file.
|
||||||
|
|
||||||
|
2. **file name** - File name stored as an ASCII string.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x001` LFS_TYPE_REG
|
||||||
|
|
||||||
|
Initializes the id + name as a regular file.
|
||||||
|
|
||||||
|
How each file is stored depends on its struct tag, which is described below.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x002` LFS_TYPE_DIR
|
||||||
|
|
||||||
|
Initializes the id + name as a directory.
|
||||||
|
|
||||||
|
Directories in littlefs are stored on disk as a linked-list of metadata pairs,
|
||||||
|
each pair containing any number of files in alphabetical order. A pointer to
|
||||||
|
the directory is stored in the struct tag, which is described below.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x0ff` LFS_TYPE_SUPERBLOCK
|
||||||
|
|
||||||
|
Initializes the id as a superblock entry.
|
||||||
|
|
||||||
|
The superblock entry is a special entry used to store format-time configuration
|
||||||
|
and identify the filesystem.
|
||||||
|
|
||||||
|
The name is a bit of a misnomer. While the superblock entry serves the same
|
||||||
|
purpose as a superblock found in other filesystems, in littlefs the superblock
|
||||||
|
does not get a dedicated block. Instead, the superblock entry is duplicated
|
||||||
|
across a linked-list of metadata pairs rooted on the blocks 0 and 1. The last
|
||||||
|
metadata pair doubles as the root directory of the filesystem.
|
||||||
|
|
||||||
|
```
|
||||||
|
.--------. .--------. .--------. .--------. .--------.
|
||||||
|
.| super |->| super |->| super |->| super |->| file B |
|
||||||
|
|| block | || block | || block | || block | || file C |
|
||||||
|
|| | || | || | || file A | || file D |
|
||||||
|
|'--------' |'--------' |'--------' |'--------' |'--------'
|
||||||
|
'--------' '--------' '--------' '--------' '--------'
|
||||||
|
|
||||||
|
\----------------+----------------/ \----------+----------/
|
||||||
|
superblock pairs root directory
|
||||||
|
```
|
||||||
|
|
||||||
|
The filesystem starts with only the root directory. The superblock metadata
|
||||||
|
pairs grow every time the root pair is compacted in order to prolong the
|
||||||
|
life of the device exponentially.
|
||||||
|
|
||||||
|
The contents of the superblock entry are stored in a name tag with the
|
||||||
|
superblock type and an inline-struct tag. The name tag contains the magic
|
||||||
|
string "littlefs", while the inline-struct tag contains version and
|
||||||
|
configuration information.
|
||||||
|
|
||||||
|
Layout of the superblock name tag and inline-struct tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|-- 32 --]
|
||||||
|
[1|- 11 -| 10 | 10 ][--- 64 ---]
|
||||||
|
^ ^ ^ ^- size (8) ^- magic string ("littlefs")
|
||||||
|
| | '------ id (0)
|
||||||
|
| '------------ type (0x0ff)
|
||||||
|
'----------------- valid bit
|
||||||
|
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|-- 32 --|-- 32 --]
|
||||||
|
[1|- 11 -| 10 | 10 ][-- 32 --|-- 32 --|-- 32 --]
|
||||||
|
^ ^ ^ ^ ^- version ^- block size ^- block count
|
||||||
|
| | | | [-- 32 --|-- 32 --|-- 32 --]
|
||||||
|
| | | | [-- 32 --|-- 32 --|-- 32 --]
|
||||||
|
| | | | ^- name max ^- file max ^- attr max
|
||||||
|
| | | '- size (24)
|
||||||
|
| | '------ id (0)
|
||||||
|
| '------------ type (0x201)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
Superblock fields:
|
||||||
|
|
||||||
|
1. **Magic string (8-bytes)** - Magic string indicating the presence of
|
||||||
|
littlefs on the device. Must be the string "littlefs".
|
||||||
|
|
||||||
|
2. **Version (32-bits)** - The version of littlefs at format time. The version
|
||||||
|
is encoded in a 32-bit value with the upper 16-bits containing the major
|
||||||
|
version, and the lower 16-bits containing the minor version.
|
||||||
|
|
||||||
|
This specification describes version 2.0 (`0x00020000`).
|
||||||
|
|
||||||
|
3. **Block size (32-bits)** - Size of the logical block size used by the
|
||||||
|
filesystem in bytes.
|
||||||
|
|
||||||
|
4. **Block count (32-bits)** - Number of blocks in the filesystem.
|
||||||
|
|
||||||
|
5. **Name max (32-bits)** - Maximum size of file names in bytes.
|
||||||
|
|
||||||
|
6. **File max (32-bits)** - Maximum size of files in bytes.
|
||||||
|
|
||||||
|
7. **Attr max (32-bits)** - Maximum size of file attributes in bytes.
|
||||||
|
|
||||||
|
The superblock must always be the first entry (id 0) in the metadata pair, and
|
||||||
|
the name tag must always be the first tag in the metadata pair. This makes it
|
||||||
|
so that the magic string "littlefs" will always reside at offset=8 in a valid
|
||||||
|
littlefs superblock.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x2xx` LFS_TYPE_STRUCT
|
||||||
|
|
||||||
|
Associates the id with an on-disk data structure.
|
||||||
|
|
||||||
|
The exact layout of the data depends on the data structure type stored in the
|
||||||
|
chunk field and can be one of the following.
|
||||||
|
|
||||||
|
Any type of struct supersedes all other structs associated with the id. For
|
||||||
|
example, appending a ctz-struct replaces an inline-struct on the same file.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x200` LFS_TYPE_DIRSTRUCT
|
||||||
|
|
||||||
|
Gives the id a directory data structure.
|
||||||
|
|
||||||
|
Directories in littlefs are stored on disk as a linked-list of metadata pairs,
|
||||||
|
each pair containing any number of files in alphabetical order.
|
||||||
|
|
||||||
|
```
|
||||||
|
|
|
||||||
|
v
|
||||||
|
.--------. .--------. .--------. .--------. .--------. .--------.
|
||||||
|
.| file A |->| file D |->| file G |->| file I |->| file J |->| file M |
|
||||||
|
|| file B | || file E | || file H | || | || file K | || file N |
|
||||||
|
|| file C | || file F | || | || | || file L | || |
|
||||||
|
|'--------' |'--------' |'--------' |'--------' |'--------' |'--------'
|
||||||
|
'--------' '--------' '--------' '--------' '--------' '--------'
|
||||||
|
```
|
||||||
|
|
||||||
|
The dir-struct tag contains only the pointer to the first metadata-pair in the
|
||||||
|
directory. The directory size is not known without traversing the directory.
|
||||||
|
|
||||||
|
The pointer to the next metadata-pair in the directory is stored in a tail tag,
|
||||||
|
which is described below.
|
||||||
|
|
||||||
|
Layout of the dir-struct tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|-- 32 --]
|
||||||
|
[1|- 11 -| 10 | 10 ][--- 64 ---]
|
||||||
|
^ ^ ^ ^- size (8) ^- metadata pair
|
||||||
|
| | '------ id
|
||||||
|
| '------------ type (0x200)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
Dir-struct fields:
|
||||||
|
|
||||||
|
1. **Metadata pair (8-bytes)** - Pointer to the first metadata-pair
|
||||||
|
in the directory.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x201` LFS_TYPE_INLINESTRUCT
|
||||||
|
|
||||||
|
Gives the id an inline data structure.
|
||||||
|
|
||||||
|
Inline structs store small files that can fit in the metadata pair. In this
|
||||||
|
case, the file data is stored directly in the tag's data area.
|
||||||
|
|
||||||
|
Layout of the inline-struct tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][--- variable length ---]
|
||||||
|
[1|- 11 -| 10 | 10 ][--- (size * 8) ---]
|
||||||
|
^ ^ ^ ^- size ^- inline data
|
||||||
|
| | '------ id
|
||||||
|
| '------------ type (0x201)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
Inline-struct fields:
|
||||||
|
|
||||||
|
1. **Inline data** - File data stored directly in the metadata-pair.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x202` LFS_TYPE_CTZSTRUCT
|
||||||
|
|
||||||
|
Gives the id a CTZ skip-list data structure.
|
||||||
|
|
||||||
|
CTZ skip-lists store files that can not fit in the metadata pair. These files
|
||||||
|
are stored in a skip-list in reverse, with a pointer to the head of the
|
||||||
|
skip-list. Note that the head of the skip-list and the file size is enough
|
||||||
|
information to read the file.
|
||||||
|
|
||||||
|
How exactly CTZ skip-lists work is a bit complicated. A full explanation can be
|
||||||
|
found in the [DESIGN.md](DESIGN.md#ctz-skip-lists).
|
||||||
|
|
||||||
|
A quick summary: For every _n_‍th block where _n_ is divisible by
|
||||||
|
2‍_ˣ_, that block contains a pointer to block _n_-2‍_ˣ_.
|
||||||
|
These pointers are stored in increasing order of _x_ in each block of the file
|
||||||
|
before the actual data.
|
||||||
|
|
||||||
|
```
|
||||||
|
|
|
||||||
|
v
|
||||||
|
.--------. .--------. .--------. .--------. .--------. .--------.
|
||||||
|
| A |<-| D |<-| G |<-| J |<-| M |<-| P |
|
||||||
|
| B |<-| E |--| H |<-| K |--| N | | Q |
|
||||||
|
| C |<-| F |--| I |--| L |--| O | | |
|
||||||
|
'--------' '--------' '--------' '--------' '--------' '--------'
|
||||||
|
block 0 block 1 block 2 block 3 block 4 block 5
|
||||||
|
1 skip 2 skips 1 skip 3 skips 1 skip
|
||||||
|
```
|
||||||
|
|
||||||
|
Note that the maximum number of pointers in a block is bounded by the maximum
|
||||||
|
file size divided by the block size. With 32 bits for file size, this results
|
||||||
|
in a minimum block size of 104 bytes.
|
||||||
|
|
||||||
|
Layout of the CTZ-struct tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|-- 32 --]
|
||||||
|
[1|- 11 -| 10 | 10 ][-- 32 --|-- 32 --]
|
||||||
|
^ ^ ^ ^ ^ ^- file size
|
||||||
|
| | | | '-------------------- file head
|
||||||
|
| | | '- size (8)
|
||||||
|
| | '------ id
|
||||||
|
| '------------ type (0x202)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
CTZ-struct fields:
|
||||||
|
|
||||||
|
1. **File head (32-bits)** - Pointer to the block that is the head of the
|
||||||
|
file's CTZ skip-list.
|
||||||
|
|
||||||
|
2. **File size (32-bits)** - Size of the file in bytes.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x3xx` LFS_TYPE_USERATTR
|
||||||
|
|
||||||
|
Attaches a user attribute to an id.
|
||||||
|
|
||||||
|
littlefs has a concept of "user attributes". These are small user-provided
|
||||||
|
attributes that can be used to store things like timestamps, hashes,
|
||||||
|
permissions, etc.
|
||||||
|
|
||||||
|
Each user attribute is uniquely identified by an 8-bit type which is stored in
|
||||||
|
the chunk field, and the user attribute itself can be found in the tag's data.
|
||||||
|
|
||||||
|
There are currently no standard user attributes and a portable littlefs
|
||||||
|
implementation should work with any user attributes missing.
|
||||||
|
|
||||||
|
Layout of the user-attr tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][--- variable length ---]
|
||||||
|
[1| 3| 8 | 10 | 10 ][--- (size * 8) ---]
|
||||||
|
^ ^ ^ ^ ^- size ^- attr data
|
||||||
|
| | | '------ id
|
||||||
|
| | '----------- attr type
|
||||||
|
| '-------------- type1 (0x3)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
User-attr fields:
|
||||||
|
|
||||||
|
1. **Attr type (8-bits)** - Type of the user attributes.
|
||||||
|
|
||||||
|
2. **Attr data** - The data associated with the user attribute.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x6xx` LFS_TYPE_TAIL
|
||||||
|
|
||||||
|
Provides the tail pointer for the metadata pair itself.
|
||||||
|
|
||||||
|
The metadata pair's tail pointer is used in littlefs for a linked-list
|
||||||
|
containing all metadata pairs. The chunk field contains the type of the tail,
|
||||||
|
which indicates if the following metadata pair is a part of the directory
|
||||||
|
(hard-tail) or only used to traverse the filesystem (soft-tail).
|
||||||
|
|
||||||
|
```
|
||||||
|
.--------.
|
||||||
|
.| dir A |-.
|
||||||
|
||softtail| |
|
||||||
|
.--------| |-'
|
||||||
|
| |'--------'
|
||||||
|
| '---|--|-'
|
||||||
|
| .-' '-------------.
|
||||||
|
| v v
|
||||||
|
| .--------. .--------. .--------.
|
||||||
|
'->| dir B |->| dir B |->| dir C |
|
||||||
|
||hardtail| ||softtail| || |
|
||||||
|
|| | || | || |
|
||||||
|
|'--------' |'--------' |'--------'
|
||||||
|
'--------' '--------' '--------'
|
||||||
|
```
|
||||||
|
|
||||||
|
Currently any type supersedes any other preceding tails in the metadata pair,
|
||||||
|
but this may change if additional metadata pair state is added.
|
||||||
|
|
||||||
|
A note about the metadata pair linked-list: Normally, this linked-list contains
|
||||||
|
every metadata pair in the filesystem. However, there are some operations that
|
||||||
|
can cause this linked-list to become out of sync if a power-loss were to occur.
|
||||||
|
When this happens, littlefs sets the "sync" flag in the global state. How
|
||||||
|
exactly this flag is stored is described below.
|
||||||
|
|
||||||
|
When the sync flag is set:
|
||||||
|
|
||||||
|
1. The linked-list may contain an orphaned directory that has been removed in
|
||||||
|
the filesystem.
|
||||||
|
2. The linked-list may contain a metadata pair with a bad block that has been
|
||||||
|
replaced in the filesystem.
|
||||||
|
|
||||||
|
If the sync flag is set, the threaded linked-list must be checked for these
|
||||||
|
errors before it can be used reliably. Note that the threaded linked-list can
|
||||||
|
be ignored if littlefs is mounted read-only.
|
||||||
|
|
||||||
|
Layout of the tail tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|-- 32 --]
|
||||||
|
[1| 3| 8 | 10 | 10 ][--- 64 ---]
|
||||||
|
^ ^ ^ ^ ^- size (8) ^- metadata pair
|
||||||
|
| | | '------ id
|
||||||
|
| | '---------- tail type
|
||||||
|
| '------------- type1 (0x6)
|
||||||
|
'---------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
Tail fields:
|
||||||
|
|
||||||
|
1. **Tail type (8-bits)** - Type of the tail pointer.
|
||||||
|
|
||||||
|
2. **Metadata pair (8-bytes)** - Pointer to the next metadata-pair.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x600` LFS_TYPE_SOFTTAIL
|
||||||
|
|
||||||
|
Provides a tail pointer that points to the next metadata pair in the
|
||||||
|
filesystem.
|
||||||
|
|
||||||
|
In this case, the next metadata pair is not a part of our current directory
|
||||||
|
and should only be followed when traversing the entire filesystem.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x601` LFS_TYPE_HARDTAIL
|
||||||
|
|
||||||
|
Provides a tail pointer that points to the next metadata pair in the
|
||||||
|
directory.
|
||||||
|
|
||||||
|
In this case, the next metadata pair belongs to the current directory. Note
|
||||||
|
that because directories in littlefs are sorted alphabetically, the next
|
||||||
|
metadata pair should only contain filenames greater than any filename in the
|
||||||
|
current pair.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x7xx` LFS_TYPE_GSTATE
|
||||||
|
|
||||||
|
Provides delta bits for global state entries.
|
||||||
|
|
||||||
|
littlefs has a concept of "global state". This is a small set of state that
|
||||||
|
can be updated by a commit to _any_ metadata pair in the filesystem.
|
||||||
|
|
||||||
|
The way this works is that the global state is stored as a set of deltas
|
||||||
|
distributed across the filesystem such that the global state can be found by
|
||||||
|
the xor-sum of these deltas.
|
||||||
|
|
||||||
|
```
|
||||||
|
.--------. .--------. .--------. .--------. .--------.
|
||||||
|
.| |->| gdelta |->| |->| gdelta |->| gdelta |
|
||||||
|
|| | || 0x23 | || | || 0xff | || 0xce |
|
||||||
|
|| | || | || | || | || |
|
||||||
|
|'--------' |'--------' |'--------' |'--------' |'--------'
|
||||||
|
'--------' '----|---' '--------' '----|---' '----|---'
|
||||||
|
v v v
|
||||||
|
0x00 --> xor ------------------> xor ------> xor --> gstate = 0x12
|
||||||
|
```
|
||||||
|
|
||||||
|
Note that storing globals this way is very expensive in terms of storage usage,
|
||||||
|
so any global state should be kept very small.
|
||||||
|
|
||||||
|
The size and format of each piece of global state depends on the type, which
|
||||||
|
is stored in the chunk field. Currently, the only global state is move state,
|
||||||
|
which is outlined below.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x7ff` LFS_TYPE_MOVESTATE
|
||||||
|
|
||||||
|
Provides delta bits for the global move state.
|
||||||
|
|
||||||
|
The move state in littlefs is used to store info about operations that could
|
||||||
|
cause to filesystem to go out of sync if the power is lost. The operations
|
||||||
|
where this could occur is moves of files between metadata pairs and any
|
||||||
|
operation that changes metadata pairs on the threaded linked-list.
|
||||||
|
|
||||||
|
In the case of moves, the move state contains a tag + metadata pair describing
|
||||||
|
the source of the ongoing move. If this tag is non-zero, that means that power
|
||||||
|
was lost during a move, and the file exists in two different locations. If this
|
||||||
|
happens, the source of the move should be considered deleted, and the move
|
||||||
|
should be completed (the source should be deleted) before any other write
|
||||||
|
operations to the filesystem.
|
||||||
|
|
||||||
|
In the case of operations to the threaded linked-list, a single "sync" bit is
|
||||||
|
used to indicate that a modification is ongoing. If this sync flag is set, the
|
||||||
|
threaded linked-list will need to be checked for errors before it can be used
|
||||||
|
reliably. The exact cases to check for are described above in the tail tag.
|
||||||
|
|
||||||
|
Layout of the move state:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|-- 32 --|-- 32 --]
|
||||||
|
[1|- 11 -| 10 | 10 ][1|- 11 -| 10 | 10 |--- 64 ---]
|
||||||
|
^ ^ ^ ^ ^ ^ ^ ^- padding (0) ^- metadata pair
|
||||||
|
| | | | | | '------ move id
|
||||||
|
| | | | | '------------ move type
|
||||||
|
| | | | '----------------- sync bit
|
||||||
|
| | | |
|
||||||
|
| | | '- size (12)
|
||||||
|
| | '------ id (0x3ff)
|
||||||
|
| '------------ type (0x7ff)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
Move state fields:
|
||||||
|
|
||||||
|
1. **Sync bit (1-bit)** - Indicates if the metadata pair threaded linked-list
|
||||||
|
is in-sync. If set, the threaded linked-list should be checked for errors.
|
||||||
|
|
||||||
|
2. **Move type (11-bits)** - Type of move being performed. Must be either
|
||||||
|
`0x000`, indicating no move, or `0x4ff` indicating the source file should
|
||||||
|
be deleted.
|
||||||
|
|
||||||
|
3. **Move id (10-bits)** - The file id being moved.
|
||||||
|
|
||||||
|
4. **Metadata pair (8-bytes)** - Pointer to the metadata-pair containing
|
||||||
|
the move.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x5xx` LFS_TYPE_CRC
|
||||||
|
|
||||||
|
Last but not least, the CRC tag marks the end of a commit and provides a
|
||||||
|
checksum for any commits to the metadata block.
|
||||||
|
|
||||||
|
The first 32-bits of the data contain a CRC-32 with a polynomial of
|
||||||
|
`0x04c11db7` initialized with `0xffffffff`. This CRC provides a checksum for
|
||||||
|
all metadata since the previous CRC tag, including the CRC tag itself. For
|
||||||
|
the first commit, this includes the revision count for the metadata block.
|
||||||
|
|
||||||
|
However, the size of the data is not limited to 32-bits. The data field may
|
||||||
|
larger to pad the commit to the next program-aligned boundary.
|
||||||
|
|
||||||
|
In addition, the CRC tag's chunk field contains a set of flags which can
|
||||||
|
change the behaviour of commits. Currently the only flag in use is the lowest
|
||||||
|
bit, which determines the expected state of the valid bit for any following
|
||||||
|
tags. This is used to guarantee that unwritten storage in a metadata block
|
||||||
|
will be detected as invalid.
|
||||||
|
|
||||||
|
Layout of the CRC tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|--- variable length ---]
|
||||||
|
[1| 3| 8 | 10 | 10 ][-- 32 --|--- (size * 8 - 32) ---]
|
||||||
|
^ ^ ^ ^ ^ ^- crc ^- padding
|
||||||
|
| | | | '- size
|
||||||
|
| | | '------ id (0x3ff)
|
||||||
|
| | '----------- valid state
|
||||||
|
| '-------------- type1 (0x5)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
CRC fields:
|
||||||
|
|
||||||
|
1. **Valid state (1-bit)** - Indicates the expected value of the valid bit for
|
||||||
|
any tags in the next commit.
|
||||||
|
|
||||||
|
2. **CRC (32-bits)** - CRC-32 with a polynomial of `0x04c11db7` initialized
|
||||||
|
with `0xffffffff`.
|
||||||
|
|
||||||
|
3. **Padding** - Padding to the next program-aligned boundary. No guarantees
|
||||||
|
are made about the contents.
|
||||||
|
|
||||||
|
---
|
||||||
|
#### `0x5ff` LFS_TYPE_FCRC
|
||||||
|
|
||||||
|
Added in lfs2.1, the optional FCRC tag contains a checksum of some amount of
|
||||||
|
bytes in the next commit at the time it was erased. This allows us to ensure
|
||||||
|
that we only ever program erased bytes, even if a previous commit failed due
|
||||||
|
to power-loss.
|
||||||
|
|
||||||
|
When programming a commit, the FCRC size must be at least as large as the
|
||||||
|
program block size. However, the program block is not saved on disk, and can
|
||||||
|
change between mounts, so the FCRC size on disk may be different than the
|
||||||
|
current program block size.
|
||||||
|
|
||||||
|
If the FCRC is missing or the checksum does not match, we must assume a
|
||||||
|
commit was attempted but failed due to power-loss.
|
||||||
|
|
||||||
|
Layout of the FCRC tag:
|
||||||
|
|
||||||
|
```
|
||||||
|
tag data
|
||||||
|
[-- 32 --][-- 32 --|-- 32 --]
|
||||||
|
[1|- 11 -| 10 | 10 ][-- 32 --|-- 32 --]
|
||||||
|
^ ^ ^ ^ ^- fcrc size ^- fcrc
|
||||||
|
| | | '- size (8)
|
||||||
|
| | '------ id (0x3ff)
|
||||||
|
| '------------ type (0x5ff)
|
||||||
|
'----------------- valid bit
|
||||||
|
```
|
||||||
|
|
||||||
|
FCRC fields:
|
||||||
|
|
||||||
|
1. **FCRC size (32-bits)** - Number of bytes after this commit's CRC tag's
|
||||||
|
padding to include in the FCRC.
|
||||||
|
|
||||||
|
2. **FCRC (32-bits)** - CRC of the bytes after this commit's CRC tag's padding
|
||||||
|
when erased. Like the CRC tag, this uses a CRC-32 with a polynomial of
|
||||||
|
`0x04c11db7` initialized with `0xffffffff`.
|
||||||
|
|
||||||
|
---
|
||||||
+270
@@ -0,0 +1,270 @@
|
|||||||
|
[cases.bench_dir_open]
|
||||||
|
# 0 = in-order
|
||||||
|
# 1 = reversed-order
|
||||||
|
# 2 = random-order
|
||||||
|
defines.ORDER = [0, 1, 2]
|
||||||
|
defines.N = 1024
|
||||||
|
defines.FILE_SIZE = 8
|
||||||
|
defines.CHUNK_SIZE = 8
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
|
||||||
|
// first create the files
|
||||||
|
char name[256];
|
||||||
|
uint8_t buffer[CHUNK_SIZE];
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
sprintf(name, "file%08x", i);
|
||||||
|
lfs_file_t file;
|
||||||
|
lfs_file_open(&lfs, &file, name,
|
||||||
|
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
|
||||||
|
|
||||||
|
uint32_t file_prng = i;
|
||||||
|
for (lfs_size_t j = 0; j < FILE_SIZE; j += CHUNK_SIZE) {
|
||||||
|
for (lfs_size_t k = 0; k < CHUNK_SIZE; k++) {
|
||||||
|
buffer[k] = BENCH_PRNG(&file_prng);
|
||||||
|
}
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// then read the files
|
||||||
|
BENCH_START();
|
||||||
|
uint32_t prng = 42;
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
lfs_off_t i_
|
||||||
|
= (ORDER == 0) ? i
|
||||||
|
: (ORDER == 1) ? (N-1-i)
|
||||||
|
: BENCH_PRNG(&prng) % N;
|
||||||
|
sprintf(name, "file%08x", i_);
|
||||||
|
lfs_file_t file;
|
||||||
|
lfs_file_open(&lfs, &file, name, LFS_O_RDONLY) => 0;
|
||||||
|
|
||||||
|
uint32_t file_prng = i_;
|
||||||
|
for (lfs_size_t j = 0; j < FILE_SIZE; j += CHUNK_SIZE) {
|
||||||
|
lfs_file_read(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
for (lfs_size_t k = 0; k < CHUNK_SIZE; k++) {
|
||||||
|
assert(buffer[k] == BENCH_PRNG(&file_prng));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
}
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_dir_creat]
|
||||||
|
# 0 = in-order
|
||||||
|
# 1 = reversed-order
|
||||||
|
# 2 = random-order
|
||||||
|
defines.ORDER = [0, 1, 2]
|
||||||
|
defines.N = 1024
|
||||||
|
defines.FILE_SIZE = 8
|
||||||
|
defines.CHUNK_SIZE = 8
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
|
||||||
|
BENCH_START();
|
||||||
|
uint32_t prng = 42;
|
||||||
|
char name[256];
|
||||||
|
uint8_t buffer[CHUNK_SIZE];
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
lfs_off_t i_
|
||||||
|
= (ORDER == 0) ? i
|
||||||
|
: (ORDER == 1) ? (N-1-i)
|
||||||
|
: BENCH_PRNG(&prng) % N;
|
||||||
|
sprintf(name, "file%08x", i_);
|
||||||
|
lfs_file_t file;
|
||||||
|
lfs_file_open(&lfs, &file, name,
|
||||||
|
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC) => 0;
|
||||||
|
|
||||||
|
uint32_t file_prng = i_;
|
||||||
|
for (lfs_size_t j = 0; j < FILE_SIZE; j += CHUNK_SIZE) {
|
||||||
|
for (lfs_size_t k = 0; k < CHUNK_SIZE; k++) {
|
||||||
|
buffer[k] = BENCH_PRNG(&file_prng);
|
||||||
|
}
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
}
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_dir_remove]
|
||||||
|
# 0 = in-order
|
||||||
|
# 1 = reversed-order
|
||||||
|
# 2 = random-order
|
||||||
|
defines.ORDER = [0, 1, 2]
|
||||||
|
defines.N = 1024
|
||||||
|
defines.FILE_SIZE = 8
|
||||||
|
defines.CHUNK_SIZE = 8
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
|
||||||
|
// first create the files
|
||||||
|
char name[256];
|
||||||
|
uint8_t buffer[CHUNK_SIZE];
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
sprintf(name, "file%08x", i);
|
||||||
|
lfs_file_t file;
|
||||||
|
lfs_file_open(&lfs, &file, name,
|
||||||
|
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
|
||||||
|
|
||||||
|
uint32_t file_prng = i;
|
||||||
|
for (lfs_size_t j = 0; j < FILE_SIZE; j += CHUNK_SIZE) {
|
||||||
|
for (lfs_size_t k = 0; k < CHUNK_SIZE; k++) {
|
||||||
|
buffer[k] = BENCH_PRNG(&file_prng);
|
||||||
|
}
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// then remove the files
|
||||||
|
BENCH_START();
|
||||||
|
uint32_t prng = 42;
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
lfs_off_t i_
|
||||||
|
= (ORDER == 0) ? i
|
||||||
|
: (ORDER == 1) ? (N-1-i)
|
||||||
|
: BENCH_PRNG(&prng) % N;
|
||||||
|
sprintf(name, "file%08x", i_);
|
||||||
|
int err = lfs_remove(&lfs, name);
|
||||||
|
assert(!err || err == LFS_ERR_NOENT);
|
||||||
|
}
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_dir_read]
|
||||||
|
defines.N = 1024
|
||||||
|
defines.FILE_SIZE = 8
|
||||||
|
defines.CHUNK_SIZE = 8
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
|
||||||
|
// first create the files
|
||||||
|
char name[256];
|
||||||
|
uint8_t buffer[CHUNK_SIZE];
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
sprintf(name, "file%08x", i);
|
||||||
|
lfs_file_t file;
|
||||||
|
lfs_file_open(&lfs, &file, name,
|
||||||
|
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
|
||||||
|
|
||||||
|
uint32_t file_prng = i;
|
||||||
|
for (lfs_size_t j = 0; j < FILE_SIZE; j += CHUNK_SIZE) {
|
||||||
|
for (lfs_size_t k = 0; k < CHUNK_SIZE; k++) {
|
||||||
|
buffer[k] = BENCH_PRNG(&file_prng);
|
||||||
|
}
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// then read the directory
|
||||||
|
BENCH_START();
|
||||||
|
lfs_dir_t dir;
|
||||||
|
lfs_dir_open(&lfs, &dir, "/") => 0;
|
||||||
|
struct lfs_info info;
|
||||||
|
lfs_dir_read(&lfs, &dir, &info) => 1;
|
||||||
|
assert(info.type == LFS_TYPE_DIR);
|
||||||
|
assert(strcmp(info.name, ".") == 0);
|
||||||
|
lfs_dir_read(&lfs, &dir, &info) => 1;
|
||||||
|
assert(info.type == LFS_TYPE_DIR);
|
||||||
|
assert(strcmp(info.name, "..") == 0);
|
||||||
|
for (int i = 0; i < N; i++) {
|
||||||
|
sprintf(name, "file%08x", i);
|
||||||
|
lfs_dir_read(&lfs, &dir, &info) => 1;
|
||||||
|
assert(info.type == LFS_TYPE_REG);
|
||||||
|
assert(strcmp(info.name, name) == 0);
|
||||||
|
}
|
||||||
|
lfs_dir_read(&lfs, &dir, &info) => 0;
|
||||||
|
lfs_dir_close(&lfs, &dir) => 0;
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_dir_mkdir]
|
||||||
|
# 0 = in-order
|
||||||
|
# 1 = reversed-order
|
||||||
|
# 2 = random-order
|
||||||
|
defines.ORDER = [0, 1, 2]
|
||||||
|
defines.N = 8
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
|
||||||
|
BENCH_START();
|
||||||
|
uint32_t prng = 42;
|
||||||
|
char name[256];
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
lfs_off_t i_
|
||||||
|
= (ORDER == 0) ? i
|
||||||
|
: (ORDER == 1) ? (N-1-i)
|
||||||
|
: BENCH_PRNG(&prng) % N;
|
||||||
|
printf("hm %d\n", i);
|
||||||
|
sprintf(name, "dir%08x", i_);
|
||||||
|
int err = lfs_mkdir(&lfs, name);
|
||||||
|
assert(!err || err == LFS_ERR_EXIST);
|
||||||
|
}
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_dir_rmdir]
|
||||||
|
# 0 = in-order
|
||||||
|
# 1 = reversed-order
|
||||||
|
# 2 = random-order
|
||||||
|
defines.ORDER = [0, 1, 2]
|
||||||
|
defines.N = 8
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
|
||||||
|
// first create the dirs
|
||||||
|
char name[256];
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
sprintf(name, "dir%08x", i);
|
||||||
|
lfs_mkdir(&lfs, name) => 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// then remove the dirs
|
||||||
|
BENCH_START();
|
||||||
|
uint32_t prng = 42;
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
lfs_off_t i_
|
||||||
|
= (ORDER == 0) ? i
|
||||||
|
: (ORDER == 1) ? (N-1-i)
|
||||||
|
: BENCH_PRNG(&prng) % N;
|
||||||
|
sprintf(name, "dir%08x", i_);
|
||||||
|
int err = lfs_remove(&lfs, name);
|
||||||
|
assert(!err || err == LFS_ERR_NOENT);
|
||||||
|
}
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
|
||||||
@@ -0,0 +1,95 @@
|
|||||||
|
[cases.bench_file_read]
|
||||||
|
# 0 = in-order
|
||||||
|
# 1 = reversed-order
|
||||||
|
# 2 = random-order
|
||||||
|
defines.ORDER = [0, 1, 2]
|
||||||
|
defines.SIZE = '128*1024'
|
||||||
|
defines.CHUNK_SIZE = 64
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
lfs_size_t chunks = (SIZE+CHUNK_SIZE-1)/CHUNK_SIZE;
|
||||||
|
|
||||||
|
// first write the file
|
||||||
|
lfs_file_t file;
|
||||||
|
uint8_t buffer[CHUNK_SIZE];
|
||||||
|
lfs_file_open(&lfs, &file, "file",
|
||||||
|
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
|
||||||
|
for (lfs_size_t i = 0; i < chunks; i++) {
|
||||||
|
uint32_t chunk_prng = i;
|
||||||
|
for (lfs_size_t j = 0; j < CHUNK_SIZE; j++) {
|
||||||
|
buffer[j] = BENCH_PRNG(&chunk_prng);
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
}
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
|
||||||
|
// then read the file
|
||||||
|
BENCH_START();
|
||||||
|
lfs_file_open(&lfs, &file, "file", LFS_O_RDONLY) => 0;
|
||||||
|
|
||||||
|
uint32_t prng = 42;
|
||||||
|
for (lfs_size_t i = 0; i < chunks; i++) {
|
||||||
|
lfs_off_t i_
|
||||||
|
= (ORDER == 0) ? i
|
||||||
|
: (ORDER == 1) ? (chunks-1-i)
|
||||||
|
: BENCH_PRNG(&prng) % chunks;
|
||||||
|
lfs_file_seek(&lfs, &file, i_*CHUNK_SIZE, LFS_SEEK_SET)
|
||||||
|
=> i_*CHUNK_SIZE;
|
||||||
|
lfs_file_read(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
|
||||||
|
uint32_t chunk_prng = i_;
|
||||||
|
for (lfs_size_t j = 0; j < CHUNK_SIZE; j++) {
|
||||||
|
assert(buffer[j] == BENCH_PRNG(&chunk_prng));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_file_write]
|
||||||
|
# 0 = in-order
|
||||||
|
# 1 = reversed-order
|
||||||
|
# 2 = random-order
|
||||||
|
defines.ORDER = [0, 1, 2]
|
||||||
|
defines.SIZE = '128*1024'
|
||||||
|
defines.CHUNK_SIZE = 64
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
lfs_size_t chunks = (SIZE+CHUNK_SIZE-1)/CHUNK_SIZE;
|
||||||
|
|
||||||
|
BENCH_START();
|
||||||
|
lfs_file_t file;
|
||||||
|
lfs_file_open(&lfs, &file, "file",
|
||||||
|
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
|
||||||
|
|
||||||
|
uint8_t buffer[CHUNK_SIZE];
|
||||||
|
uint32_t prng = 42;
|
||||||
|
for (lfs_size_t i = 0; i < chunks; i++) {
|
||||||
|
lfs_off_t i_
|
||||||
|
= (ORDER == 0) ? i
|
||||||
|
: (ORDER == 1) ? (chunks-1-i)
|
||||||
|
: BENCH_PRNG(&prng) % chunks;
|
||||||
|
uint32_t chunk_prng = i_;
|
||||||
|
for (lfs_size_t j = 0; j < CHUNK_SIZE; j++) {
|
||||||
|
buffer[j] = BENCH_PRNG(&chunk_prng);
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_seek(&lfs, &file, i_*CHUNK_SIZE, LFS_SEEK_SET)
|
||||||
|
=> i_*CHUNK_SIZE;
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
@@ -0,0 +1,56 @@
|
|||||||
|
[cases.bench_superblocks_found]
|
||||||
|
# support benchmarking with files
|
||||||
|
defines.N = [0, 1024]
|
||||||
|
defines.FILE_SIZE = 8
|
||||||
|
defines.CHUNK_SIZE = 8
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
|
||||||
|
// create files?
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
char name[256];
|
||||||
|
uint8_t buffer[CHUNK_SIZE];
|
||||||
|
for (lfs_size_t i = 0; i < N; i++) {
|
||||||
|
sprintf(name, "file%08x", i);
|
||||||
|
lfs_file_t file;
|
||||||
|
lfs_file_open(&lfs, &file, name,
|
||||||
|
LFS_O_WRONLY | LFS_O_CREAT | LFS_O_EXCL) => 0;
|
||||||
|
|
||||||
|
for (lfs_size_t j = 0; j < FILE_SIZE; j += CHUNK_SIZE) {
|
||||||
|
for (lfs_size_t k = 0; k < CHUNK_SIZE; k++) {
|
||||||
|
buffer[k] = i+j+k;
|
||||||
|
}
|
||||||
|
lfs_file_write(&lfs, &file, buffer, CHUNK_SIZE) => CHUNK_SIZE;
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_file_close(&lfs, &file) => 0;
|
||||||
|
}
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
|
||||||
|
BENCH_START();
|
||||||
|
lfs_mount(&lfs, cfg) => 0;
|
||||||
|
BENCH_STOP();
|
||||||
|
|
||||||
|
lfs_unmount(&lfs) => 0;
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_superblocks_missing]
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
|
||||||
|
BENCH_START();
|
||||||
|
int err = lfs_mount(&lfs, cfg);
|
||||||
|
assert(err != 0);
|
||||||
|
BENCH_STOP();
|
||||||
|
'''
|
||||||
|
|
||||||
|
[cases.bench_superblocks_format]
|
||||||
|
code = '''
|
||||||
|
lfs_t lfs;
|
||||||
|
|
||||||
|
BENCH_START();
|
||||||
|
lfs_format(&lfs, cfg) => 0;
|
||||||
|
BENCH_STOP();
|
||||||
|
'''
|
||||||
|
|
||||||
Vendored
+977
@@ -0,0 +1,977 @@
|
|||||||
|
#include <rtdevice.h>
|
||||||
|
#include <rtthread.h>
|
||||||
|
|
||||||
|
#include <dfs_file.h>
|
||||||
|
#include <dfs_fs.h>
|
||||||
|
|
||||||
|
#include "lfs.h"
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#if defined(RT_VERSION_CHECK) && (RTTHREAD_VERSION >= RT_VERSION_CHECK(5, 0, 2))
|
||||||
|
#define DFS_LFS_RW_RETURN_TYPE ssize_t
|
||||||
|
#define DFS_LFS_LSK_RETURN_TYPE off_t
|
||||||
|
#define DFS_LFS_MKFS(dev_id, fs_name) _dfs_lfs_mkfs(dev_id, fs_name)
|
||||||
|
#else
|
||||||
|
#define DFS_LFS_RW_RETURN_TYPE int
|
||||||
|
#define DFS_LFS_LSK_RETURN_TYPE int
|
||||||
|
#define DFS_LFS_MKFS(dev_id, fs_name) _dfs_lfs_mkfs(dev_id)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef RT_DEF_LFS_DRIVERS
|
||||||
|
#define RT_DEF_LFS_DRIVERS 1
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if (RT_DEF_LFS_DRIVERS < 1)
|
||||||
|
#error "#define RT_DEF_LFS_DRIVERS must > 0"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_READ_SIZE
|
||||||
|
#define LFS_READ_SIZE 256
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_PROG_SIZE
|
||||||
|
#define LFS_PROG_SIZE 256
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_BLOCK_SIZE
|
||||||
|
#define LFS_BLOCK_SIZE 4096
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_CACHE_SIZE
|
||||||
|
#define LFS_CACHE_SIZE LFS_PROG_SIZE
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_BLOCK_CYCLES
|
||||||
|
#define LFS_BLOCK_CYCLES (-1)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_LOOKAHEAD_MAX
|
||||||
|
#define LFS_LOOKAHEAD_MAX 128
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#define ATTR_TIMESTAMP 0x74
|
||||||
|
|
||||||
|
typedef struct _dfs_lfs_s
|
||||||
|
{
|
||||||
|
struct lfs lfs;
|
||||||
|
struct lfs_config cfg;
|
||||||
|
struct rt_mutex lock;
|
||||||
|
} dfs_lfs_t;
|
||||||
|
|
||||||
|
typedef struct _dfs_lfs_fd_s
|
||||||
|
{
|
||||||
|
struct lfs* lfs;
|
||||||
|
union
|
||||||
|
{
|
||||||
|
struct lfs_file file;
|
||||||
|
struct lfs_dir dir;
|
||||||
|
} u;
|
||||||
|
} dfs_lfs_fd_t;
|
||||||
|
|
||||||
|
static struct _dfs_lfs_s* _lfs_mount_tbl[RT_DEF_LFS_DRIVERS] = {0};
|
||||||
|
|
||||||
|
#ifdef LFS_THREADSAFE
|
||||||
|
// Lock the underlying block device. Negative error codes
|
||||||
|
// are propogated to the user.
|
||||||
|
int _lfs_lock(const struct lfs_config *c)
|
||||||
|
{
|
||||||
|
dfs_lfs_t *dfs_lfs = rt_container_of(c, dfs_lfs_t, cfg);
|
||||||
|
|
||||||
|
if (rt_mutex_take(&dfs_lfs->lock, RT_WAITING_FOREVER) != RT_EOK)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Unlock the underlying block device. Negative error codes
|
||||||
|
// are propogated to the user.
|
||||||
|
int _lfs_unlock(const struct lfs_config *c)
|
||||||
|
{
|
||||||
|
dfs_lfs_t *dfs_lfs = rt_container_of(c, dfs_lfs_t, cfg);
|
||||||
|
|
||||||
|
if (rt_mutex_release(&dfs_lfs->lock) != RT_EOK)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Read a region in a block. Negative error codes are propogated
|
||||||
|
// to the user.
|
||||||
|
static int _lfs_flash_read(const struct lfs_config* c, lfs_block_t block, lfs_off_t off, void* buffer, lfs_size_t size)
|
||||||
|
{
|
||||||
|
struct rt_mtd_nor_device* mtd_nor;
|
||||||
|
|
||||||
|
RT_ASSERT(c != RT_NULL);
|
||||||
|
RT_ASSERT(c->context != RT_NULL);
|
||||||
|
|
||||||
|
mtd_nor = (struct rt_mtd_nor_device*)c->context;
|
||||||
|
if (rt_mtd_nor_read(mtd_nor, block * c->block_size + off, buffer, size) != size)
|
||||||
|
{
|
||||||
|
return LFS_ERR_IO;
|
||||||
|
}
|
||||||
|
|
||||||
|
return LFS_ERR_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Program a region in a block. The block must have previously
|
||||||
|
// been erased. Negative error codes are propogated to the user.
|
||||||
|
// May return LFS_ERR_CORRUPT if the block should be considered bad.
|
||||||
|
static int _lfs_flash_prog(const struct lfs_config* c, lfs_block_t block, lfs_off_t off, const void* buffer, lfs_size_t size)
|
||||||
|
{
|
||||||
|
struct rt_mtd_nor_device* mtd_nor;
|
||||||
|
|
||||||
|
RT_ASSERT(c != RT_NULL);
|
||||||
|
RT_ASSERT(c->context != RT_NULL);
|
||||||
|
|
||||||
|
mtd_nor = (struct rt_mtd_nor_device*)c->context;
|
||||||
|
if (rt_mtd_nor_write(mtd_nor, block * c->block_size + off, buffer, size) != size)
|
||||||
|
{
|
||||||
|
return LFS_ERR_IO;
|
||||||
|
}
|
||||||
|
|
||||||
|
return LFS_ERR_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Erase a block. A block must be erased before being programmed.
|
||||||
|
// The state of an erased block is undefined. Negative error codes
|
||||||
|
// are propogated to the user.
|
||||||
|
// May return LFS_ERR_CORRUPT if the block should be considered bad.
|
||||||
|
static int _lfs_flash_erase(const struct lfs_config* c, lfs_block_t block)
|
||||||
|
{
|
||||||
|
struct rt_mtd_nor_device* mtd_nor;
|
||||||
|
|
||||||
|
RT_ASSERT(c != RT_NULL);
|
||||||
|
RT_ASSERT(c->context != RT_NULL);
|
||||||
|
|
||||||
|
mtd_nor = (struct rt_mtd_nor_device*)c->context;
|
||||||
|
if (rt_mtd_nor_erase_block(mtd_nor, block * c->block_size, c->block_size) != RT_EOK)
|
||||||
|
{
|
||||||
|
return LFS_ERR_IO;
|
||||||
|
}
|
||||||
|
|
||||||
|
return LFS_ERR_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Sync the state of the underlying block device. Negative error codes
|
||||||
|
// are propogated to the user.
|
||||||
|
static int _lfs_flash_sync(const struct lfs_config* c)
|
||||||
|
{
|
||||||
|
return LFS_ERR_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* results:
|
||||||
|
* -1, no space to install fatfs driver
|
||||||
|
* >= 0, there is an space to install littlefs driver
|
||||||
|
*/
|
||||||
|
static int _get_disk(rt_device_t dev_id)
|
||||||
|
{
|
||||||
|
int index;
|
||||||
|
|
||||||
|
if (dev_id == RT_NULL)
|
||||||
|
{
|
||||||
|
for (index = 0; index < RT_DEF_LFS_DRIVERS; index ++)
|
||||||
|
{
|
||||||
|
if(_lfs_mount_tbl[index] == RT_NULL)
|
||||||
|
{
|
||||||
|
return index;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
for (index = 0; index < RT_DEF_LFS_DRIVERS; index ++)
|
||||||
|
{
|
||||||
|
if ((_lfs_mount_tbl[index] != RT_NULL) && (_lfs_mount_tbl[index]->cfg.context == (void *)dev_id))
|
||||||
|
{
|
||||||
|
return index;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _lfs_result_to_dfs(int result)
|
||||||
|
{
|
||||||
|
int status = 0;
|
||||||
|
|
||||||
|
switch (result)
|
||||||
|
{
|
||||||
|
case LFS_ERR_OK:
|
||||||
|
break;
|
||||||
|
|
||||||
|
case LFS_ERR_IO:
|
||||||
|
status = -EIO;
|
||||||
|
break; // Error during device operation
|
||||||
|
|
||||||
|
case LFS_ERR_NOENT:
|
||||||
|
status = -ENOENT;
|
||||||
|
break; // No directory entry
|
||||||
|
|
||||||
|
case LFS_ERR_EXIST:
|
||||||
|
status = -EEXIST;
|
||||||
|
break; // Entry already exists
|
||||||
|
|
||||||
|
case LFS_ERR_NOTDIR:
|
||||||
|
status = -ENOTDIR;
|
||||||
|
break; // Entry is not a dir
|
||||||
|
|
||||||
|
case LFS_ERR_ISDIR:
|
||||||
|
status = -EISDIR;
|
||||||
|
break; // Entry is a dir
|
||||||
|
|
||||||
|
case LFS_ERR_NOTEMPTY:
|
||||||
|
status = -ENOTEMPTY;
|
||||||
|
break; // Dir is not empty
|
||||||
|
|
||||||
|
case LFS_ERR_BADF:
|
||||||
|
status = -EBADF;
|
||||||
|
break; // Bad file number
|
||||||
|
|
||||||
|
case LFS_ERR_INVAL:
|
||||||
|
status = -EINVAL;
|
||||||
|
break; // Invalid parameter
|
||||||
|
|
||||||
|
case LFS_ERR_NOSPC:
|
||||||
|
status = -ENOSPC;
|
||||||
|
break; // No space left on device
|
||||||
|
|
||||||
|
case LFS_ERR_NOMEM:
|
||||||
|
status = -ENOMEM;
|
||||||
|
break; // No more memory available
|
||||||
|
|
||||||
|
case LFS_ERR_CORRUPT:
|
||||||
|
status = -52;
|
||||||
|
break; // Corrupted
|
||||||
|
|
||||||
|
default:
|
||||||
|
status = -EIO;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void _lfs_load_config(struct lfs_config* lfs_cfg, struct rt_mtd_nor_device* mtd_nor)
|
||||||
|
{
|
||||||
|
uint64_t mtd_size;
|
||||||
|
|
||||||
|
lfs_cfg->context = (void*)mtd_nor;
|
||||||
|
|
||||||
|
lfs_cfg->read_size = LFS_READ_SIZE;
|
||||||
|
lfs_cfg->prog_size = LFS_PROG_SIZE;
|
||||||
|
|
||||||
|
lfs_cfg->block_size = mtd_nor->block_size;
|
||||||
|
if (lfs_cfg->block_size < LFS_BLOCK_SIZE)
|
||||||
|
{
|
||||||
|
lfs_cfg->block_size = LFS_BLOCK_SIZE;
|
||||||
|
}
|
||||||
|
|
||||||
|
lfs_cfg->cache_size = LFS_CACHE_SIZE;
|
||||||
|
lfs_cfg->block_cycles = LFS_BLOCK_CYCLES;
|
||||||
|
|
||||||
|
mtd_size = mtd_nor->block_end - mtd_nor->block_start;
|
||||||
|
mtd_size *= mtd_nor->block_size;
|
||||||
|
lfs_cfg->block_count = mtd_size / lfs_cfg->block_size;
|
||||||
|
|
||||||
|
lfs_cfg->lookahead_size = 32 * ((lfs_cfg->block_count + 31) / 32);
|
||||||
|
if (lfs_cfg->lookahead_size > LFS_LOOKAHEAD_MAX)
|
||||||
|
{
|
||||||
|
lfs_cfg->lookahead_size = LFS_LOOKAHEAD_MAX;
|
||||||
|
}
|
||||||
|
#ifdef LFS_THREADSAFE
|
||||||
|
lfs_cfg->lock = _lfs_lock;
|
||||||
|
lfs_cfg->unlock = _lfs_unlock;
|
||||||
|
#endif
|
||||||
|
lfs_cfg->read = _lfs_flash_read;
|
||||||
|
lfs_cfg->prog = _lfs_flash_prog;
|
||||||
|
lfs_cfg->erase = _lfs_flash_erase;
|
||||||
|
lfs_cfg->sync = _lfs_flash_sync;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _dfs_lfs_mount(struct dfs_filesystem* dfs, unsigned long rwflag, const void* data)
|
||||||
|
{
|
||||||
|
int result;
|
||||||
|
int index;
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
|
||||||
|
/* Check Device Type */
|
||||||
|
if (dfs->dev_id->type != RT_Device_Class_MTD)
|
||||||
|
{
|
||||||
|
rt_kprintf("The flash device type must be MTD!\n");
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* get an empty position */
|
||||||
|
index = _get_disk(RT_NULL);
|
||||||
|
if (index == -1)
|
||||||
|
{
|
||||||
|
return -EIO;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*create lfs handle */
|
||||||
|
dfs_lfs = (dfs_lfs_t*)rt_malloc(sizeof(dfs_lfs_t));
|
||||||
|
if (dfs_lfs == RT_NULL)
|
||||||
|
{
|
||||||
|
rt_kprintf("ERROR:no memory!\n");
|
||||||
|
return -ENOMEM;
|
||||||
|
}
|
||||||
|
rt_memset(dfs_lfs, 0, sizeof(dfs_lfs_t));
|
||||||
|
rt_mutex_init(&dfs_lfs->lock, "lfslock", RT_IPC_FLAG_PRIO);
|
||||||
|
_lfs_load_config(&dfs_lfs->cfg, (struct rt_mtd_nor_device*)dfs->dev_id);
|
||||||
|
|
||||||
|
/* mount lfs*/
|
||||||
|
result = lfs_mount(&dfs_lfs->lfs, &dfs_lfs->cfg);
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
rt_mutex_detach(&dfs_lfs->lock);
|
||||||
|
/* release memory */
|
||||||
|
rt_free(dfs_lfs);
|
||||||
|
|
||||||
|
return -EIO;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* mount succeed! */
|
||||||
|
dfs->data = (void*)dfs_lfs;
|
||||||
|
_lfs_mount_tbl[index] = dfs_lfs;
|
||||||
|
return RT_EOK;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _dfs_lfs_unmount(struct dfs_filesystem* dfs)
|
||||||
|
{
|
||||||
|
int result;
|
||||||
|
int index;
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
|
||||||
|
RT_ASSERT(dfs != RT_NULL);
|
||||||
|
RT_ASSERT(dfs->data != RT_NULL);
|
||||||
|
|
||||||
|
/* find the device index and then umount it */
|
||||||
|
index = _get_disk(dfs->dev_id);
|
||||||
|
if (index == -1)
|
||||||
|
{
|
||||||
|
return -ENOENT;
|
||||||
|
}
|
||||||
|
_lfs_mount_tbl[index] = RT_NULL;
|
||||||
|
|
||||||
|
dfs_lfs = (dfs_lfs_t*)dfs->data;
|
||||||
|
dfs->data = RT_NULL;
|
||||||
|
|
||||||
|
result = lfs_unmount(&dfs_lfs->lfs);
|
||||||
|
rt_mutex_detach(&dfs_lfs->lock);
|
||||||
|
rt_free(dfs_lfs);
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
static int DFS_LFS_MKFS(rt_device_t dev_id, const char *fs_name)
|
||||||
|
{
|
||||||
|
int result;
|
||||||
|
int index;
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
|
||||||
|
if (dev_id == RT_NULL)
|
||||||
|
{
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Check Device Type */
|
||||||
|
if (dev_id->type != RT_Device_Class_MTD)
|
||||||
|
{
|
||||||
|
rt_kprintf("The flash device type must be MTD!\n");
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
index = _get_disk(dev_id);
|
||||||
|
if (index == -1)
|
||||||
|
{
|
||||||
|
/* create lfs handle */
|
||||||
|
dfs_lfs = rt_malloc(sizeof(dfs_lfs_t));
|
||||||
|
if (dfs_lfs == RT_NULL)
|
||||||
|
{
|
||||||
|
rt_kprintf("ERROR:no memory!\n");
|
||||||
|
return -ENOMEM;
|
||||||
|
}
|
||||||
|
rt_memset(dfs_lfs, 0, sizeof(dfs_lfs_t));
|
||||||
|
rt_mutex_init(&dfs_lfs->lock, "lfslock", RT_IPC_FLAG_PRIO);
|
||||||
|
_lfs_load_config(&dfs_lfs->cfg, (struct rt_mtd_nor_device*)dev_id);
|
||||||
|
|
||||||
|
/* format flash device */
|
||||||
|
result = lfs_format(&dfs_lfs->lfs, &dfs_lfs->cfg);
|
||||||
|
rt_mutex_detach(&dfs_lfs->lock);
|
||||||
|
rt_free(dfs_lfs);
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
dfs_lfs = _lfs_mount_tbl[index];
|
||||||
|
|
||||||
|
/* unmount it */
|
||||||
|
result = lfs_unmount(&dfs_lfs->lfs);
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
_lfs_mount_tbl[index] = RT_NULL;
|
||||||
|
|
||||||
|
/* format flash device */
|
||||||
|
result = lfs_format(&dfs_lfs->lfs, &dfs_lfs->cfg);
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
_lfs_load_config(&dfs_lfs->cfg, (struct rt_mtd_nor_device*)dev_id);
|
||||||
|
|
||||||
|
/* mount lfs*/
|
||||||
|
result = lfs_mount(&dfs_lfs->lfs, &dfs_lfs->cfg);
|
||||||
|
if (result == LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
_lfs_mount_tbl[index] = dfs_lfs;
|
||||||
|
}
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static int _dfs_lfs_statfs_count(void* p, lfs_block_t b)
|
||||||
|
{
|
||||||
|
*(lfs_size_t*)p += 1;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _dfs_lfs_statfs(struct dfs_filesystem* dfs, struct statfs* buf)
|
||||||
|
{
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
int result;
|
||||||
|
lfs_size_t in_use = 0;
|
||||||
|
|
||||||
|
RT_ASSERT(buf != RT_NULL);
|
||||||
|
RT_ASSERT(dfs != RT_NULL);
|
||||||
|
RT_ASSERT(dfs->data != RT_NULL);
|
||||||
|
|
||||||
|
dfs_lfs = (dfs_lfs_t*)dfs->data;
|
||||||
|
|
||||||
|
/* Get total sectors and free sectors */
|
||||||
|
result = lfs_fs_traverse(&dfs_lfs->lfs, _dfs_lfs_statfs_count, &in_use);
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
buf->f_bsize = dfs_lfs->cfg.block_size;
|
||||||
|
buf->f_blocks = dfs_lfs->cfg.block_count;
|
||||||
|
buf->f_bfree = dfs_lfs->cfg.block_count - in_use;
|
||||||
|
|
||||||
|
return RT_EOK;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
static int _dfs_lfs_unlink(struct dfs_filesystem* dfs, const char* path)
|
||||||
|
{
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
int result;
|
||||||
|
|
||||||
|
RT_ASSERT(dfs != RT_NULL);
|
||||||
|
RT_ASSERT(dfs->data != RT_NULL);
|
||||||
|
|
||||||
|
dfs_lfs = (dfs_lfs_t*)dfs->data;
|
||||||
|
result = lfs_remove(&dfs_lfs->lfs, path);
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static void _dfs_lfs_tostat(struct stat* st, struct lfs_info* info, time_t mtime)
|
||||||
|
{
|
||||||
|
memset(st, 0, sizeof(struct stat));
|
||||||
|
|
||||||
|
/* convert to dfs stat structure */
|
||||||
|
st->st_dev = 0;
|
||||||
|
st->st_size = info->size;
|
||||||
|
st->st_mode = S_IRWXU | S_IRWXG | S_IRWXO;
|
||||||
|
|
||||||
|
switch (info->type)
|
||||||
|
{
|
||||||
|
case LFS_TYPE_DIR:
|
||||||
|
st->st_mode |= S_IFDIR;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case LFS_TYPE_REG:
|
||||||
|
st->st_mode |= S_IFREG;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
st->st_mtime = mtime;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _dfs_lfs_stat(struct dfs_filesystem* dfs, const char* path, struct stat* st)
|
||||||
|
{
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
int result;
|
||||||
|
struct lfs_info info;
|
||||||
|
|
||||||
|
RT_ASSERT(dfs != RT_NULL);
|
||||||
|
RT_ASSERT(dfs->data != RT_NULL);
|
||||||
|
|
||||||
|
dfs_lfs = (dfs_lfs_t*)dfs->data;
|
||||||
|
result = lfs_stat(&dfs_lfs->lfs, path, &info);
|
||||||
|
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
time_t mtime = 0;
|
||||||
|
lfs_getattr(&dfs_lfs->lfs, path, ATTR_TIMESTAMP, &mtime, sizeof(time_t));
|
||||||
|
|
||||||
|
_dfs_lfs_tostat(st, &info, mtime);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
static int _dfs_lfs_rename(struct dfs_filesystem* dfs, const char* from, const char* to)
|
||||||
|
{
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
int result;
|
||||||
|
|
||||||
|
RT_ASSERT(dfs != RT_NULL);
|
||||||
|
RT_ASSERT(dfs->data != RT_NULL);
|
||||||
|
|
||||||
|
dfs_lfs = (dfs_lfs_t*)dfs->data;
|
||||||
|
result = lfs_rename(&dfs_lfs->lfs, from, to);
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/******************************************************************************
|
||||||
|
* file operations
|
||||||
|
******************************************************************************/
|
||||||
|
static int _dfs_lfs_open(struct dfs_file* file)
|
||||||
|
{
|
||||||
|
struct dfs_filesystem* dfs;
|
||||||
|
dfs_lfs_t* dfs_lfs;
|
||||||
|
int result;
|
||||||
|
int flags = 0;
|
||||||
|
|
||||||
|
RT_ASSERT(file != RT_NULL);
|
||||||
|
|
||||||
|
dfs = (struct dfs_filesystem*)file->vnode->fs;
|
||||||
|
|
||||||
|
RT_ASSERT(file->vnode->ref_count > 0);
|
||||||
|
if (file->vnode->ref_count > 1)
|
||||||
|
{
|
||||||
|
if (file->vnode->type == FT_DIRECTORY
|
||||||
|
&& !(file->flags & O_DIRECTORY))
|
||||||
|
{
|
||||||
|
return -ENOENT;
|
||||||
|
}
|
||||||
|
file->pos = 0;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
dfs_lfs = (dfs_lfs_t*)dfs->data;
|
||||||
|
|
||||||
|
if (file->flags & O_DIRECTORY)
|
||||||
|
{
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd = rt_malloc(sizeof(dfs_lfs_fd_t));
|
||||||
|
if (dfs_lfs_fd == RT_NULL)
|
||||||
|
{
|
||||||
|
rt_kprintf("ERROR:no memory!\n");
|
||||||
|
result = -ENOMEM;
|
||||||
|
|
||||||
|
goto _error_dir;
|
||||||
|
}
|
||||||
|
rt_memset(dfs_lfs_fd, 0, sizeof(dfs_lfs_fd_t));
|
||||||
|
dfs_lfs_fd->lfs = &dfs_lfs->lfs;
|
||||||
|
|
||||||
|
if (file->flags & O_CREAT)
|
||||||
|
{
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
result = lfs_mkdir(dfs_lfs_fd->lfs, file->vnode->path);
|
||||||
|
#else
|
||||||
|
result = -EINVAL;
|
||||||
|
#endif
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
goto _error_dir;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
time_t now = time(RT_NULL);
|
||||||
|
lfs_setattr(dfs_lfs_fd->lfs, file->vnode->path, ATTR_TIMESTAMP, &now, sizeof(time_t));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
result = lfs_dir_open(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.dir, file->vnode->path);
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
goto _error_dir;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
file->data = (void*)dfs_lfs_fd;
|
||||||
|
return RT_EOK;
|
||||||
|
}
|
||||||
|
|
||||||
|
_error_dir:
|
||||||
|
if (dfs_lfs_fd != RT_NULL)
|
||||||
|
{
|
||||||
|
rt_free(dfs_lfs_fd);
|
||||||
|
}
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd = rt_malloc(sizeof(dfs_lfs_fd_t));
|
||||||
|
if (dfs_lfs_fd == RT_NULL)
|
||||||
|
{
|
||||||
|
rt_kprintf("ERROR:no memory!\n");
|
||||||
|
result = -ENOMEM;
|
||||||
|
|
||||||
|
goto _error_file;
|
||||||
|
}
|
||||||
|
rt_memset(dfs_lfs_fd, 0, sizeof(dfs_lfs_fd_t));
|
||||||
|
dfs_lfs_fd->lfs = &dfs_lfs->lfs;
|
||||||
|
|
||||||
|
if ((file->flags & 3) == O_RDONLY)
|
||||||
|
flags |= LFS_O_RDONLY;
|
||||||
|
if ((file->flags & 3) == O_WRONLY)
|
||||||
|
flags |= LFS_O_WRONLY;
|
||||||
|
if ((file->flags & 3) == O_RDWR)
|
||||||
|
flags |= LFS_O_RDWR;
|
||||||
|
if (file->flags & O_CREAT)
|
||||||
|
flags |= LFS_O_CREAT;
|
||||||
|
if (file->flags & O_EXCL)
|
||||||
|
flags |= LFS_O_EXCL;
|
||||||
|
if (file->flags & O_TRUNC)
|
||||||
|
flags |= LFS_O_TRUNC;
|
||||||
|
if (file->flags & O_APPEND)
|
||||||
|
flags |= LFS_O_APPEND;
|
||||||
|
|
||||||
|
result = lfs_file_open(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file, file->vnode->path, flags);
|
||||||
|
if (result != LFS_ERR_OK)
|
||||||
|
{
|
||||||
|
goto _error_file;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
file->data = (void*)dfs_lfs_fd;
|
||||||
|
file->pos = dfs_lfs_fd->u.file.pos;
|
||||||
|
file->vnode->size = dfs_lfs_fd->u.file.ctz.size;
|
||||||
|
return RT_EOK;
|
||||||
|
}
|
||||||
|
|
||||||
|
_error_file:
|
||||||
|
if (dfs_lfs_fd != RT_NULL)
|
||||||
|
{
|
||||||
|
rt_free(dfs_lfs_fd);
|
||||||
|
}
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _dfs_lfs_close(struct dfs_file* file)
|
||||||
|
{
|
||||||
|
int result;
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd;
|
||||||
|
uint8_t need_time_update;
|
||||||
|
RT_ASSERT(file != RT_NULL);
|
||||||
|
RT_ASSERT(file->data != RT_NULL);
|
||||||
|
|
||||||
|
RT_ASSERT(file->vnode->ref_count > 0);
|
||||||
|
if (file->vnode->ref_count > 1)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
dfs_lfs_fd = (dfs_lfs_fd_t*)file->data;
|
||||||
|
|
||||||
|
if (file->vnode->type == FT_DIRECTORY)
|
||||||
|
{
|
||||||
|
result = lfs_dir_close(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.dir);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
need_time_update = (dfs_lfs_fd->u.file.flags & LFS_F_DIRTY) || (dfs_lfs_fd->u.file.flags & LFS_F_WRITING);
|
||||||
|
result = lfs_file_close(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file);
|
||||||
|
if (result == LFS_ERR_OK && need_time_update)
|
||||||
|
{
|
||||||
|
time_t now = time(RT_NULL);
|
||||||
|
lfs_setattr(dfs_lfs_fd->lfs, file->vnode->path, ATTR_TIMESTAMP, &now, sizeof(time_t));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
rt_free(dfs_lfs_fd);
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _dfs_lfs_ioctl(struct dfs_file* file, int cmd, void* args)
|
||||||
|
{
|
||||||
|
return -ENOSYS;
|
||||||
|
}
|
||||||
|
|
||||||
|
static DFS_LFS_RW_RETURN_TYPE _dfs_lfs_read(struct dfs_file* file, void* buf, size_t len)
|
||||||
|
{
|
||||||
|
lfs_ssize_t ssize;
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd;
|
||||||
|
|
||||||
|
RT_ASSERT(file != RT_NULL);
|
||||||
|
RT_ASSERT(file->data != RT_NULL);
|
||||||
|
|
||||||
|
if (file->vnode->type == FT_DIRECTORY)
|
||||||
|
{
|
||||||
|
return -EISDIR;
|
||||||
|
}
|
||||||
|
|
||||||
|
dfs_lfs_fd = (dfs_lfs_fd_t*)file->data;
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
if (lfs_file_tell(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file) != file->pos)
|
||||||
|
{
|
||||||
|
lfs_soff_t soff = lfs_file_seek(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file, file->pos, LFS_SEEK_SET);
|
||||||
|
if (soff < 0)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(soff);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
ssize = lfs_file_read(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file, buf, len);
|
||||||
|
if (ssize < 0)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(ssize);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* update position */
|
||||||
|
file->pos = dfs_lfs_fd->u.file.pos;
|
||||||
|
|
||||||
|
return ssize;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
static DFS_LFS_RW_RETURN_TYPE _dfs_lfs_write(struct dfs_file* file, const void* buf, size_t len)
|
||||||
|
{
|
||||||
|
lfs_ssize_t ssize;
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd;
|
||||||
|
RT_ASSERT(file != RT_NULL);
|
||||||
|
RT_ASSERT(file->data != RT_NULL);
|
||||||
|
|
||||||
|
if (file->vnode->type == FT_DIRECTORY)
|
||||||
|
{
|
||||||
|
return -EISDIR;
|
||||||
|
}
|
||||||
|
|
||||||
|
dfs_lfs_fd = (dfs_lfs_fd_t*)file->data;
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
if (lfs_file_tell(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file) != file->pos)
|
||||||
|
{
|
||||||
|
lfs_soff_t soff = lfs_file_seek(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file, file->pos, LFS_SEEK_SET);
|
||||||
|
if (soff < 0)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(soff);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
ssize = lfs_file_write(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file, buf, len);
|
||||||
|
if (ssize < 0)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(ssize);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* update position and file size */
|
||||||
|
file->pos = dfs_lfs_fd->u.file.pos;
|
||||||
|
file->vnode->size = dfs_lfs_fd->u.file.ctz.size;
|
||||||
|
|
||||||
|
return ssize;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static int _dfs_lfs_flush(struct dfs_file* file)
|
||||||
|
{
|
||||||
|
int result;
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd;
|
||||||
|
uint8_t need_time_update;
|
||||||
|
|
||||||
|
RT_ASSERT(file != RT_NULL);
|
||||||
|
RT_ASSERT(file->data != RT_NULL);
|
||||||
|
|
||||||
|
dfs_lfs_fd = (dfs_lfs_fd_t*)file->data;
|
||||||
|
need_time_update = (dfs_lfs_fd->u.file.flags & LFS_F_DIRTY) || (dfs_lfs_fd->u.file.flags & LFS_F_WRITING);
|
||||||
|
result = lfs_file_sync(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file);
|
||||||
|
if (result == LFS_ERR_OK && need_time_update)
|
||||||
|
{
|
||||||
|
time_t now = time(RT_NULL);
|
||||||
|
lfs_setattr(dfs_lfs_fd->lfs, file->vnode->path, ATTR_TIMESTAMP, &now, sizeof(time_t));
|
||||||
|
}
|
||||||
|
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
static DFS_LFS_LSK_RETURN_TYPE _dfs_lfs_lseek(struct dfs_file* file, rt_off_t offset)
|
||||||
|
{
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd;
|
||||||
|
|
||||||
|
RT_ASSERT(file != RT_NULL);
|
||||||
|
RT_ASSERT(file->data != RT_NULL);
|
||||||
|
|
||||||
|
dfs_lfs_fd = (dfs_lfs_fd_t*)file->data;
|
||||||
|
|
||||||
|
if (file->vnode->type == FT_REGULAR)
|
||||||
|
{
|
||||||
|
lfs_soff_t soff = lfs_file_seek(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.file, offset, LFS_SEEK_SET);
|
||||||
|
if (soff < 0)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(soff);
|
||||||
|
}
|
||||||
|
|
||||||
|
file->pos = dfs_lfs_fd->u.file.pos;
|
||||||
|
}
|
||||||
|
else if (file->vnode->type == FT_DIRECTORY)
|
||||||
|
{
|
||||||
|
lfs_soff_t soff = lfs_dir_seek(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.dir, offset);
|
||||||
|
if (soff < 0)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(soff);
|
||||||
|
}
|
||||||
|
|
||||||
|
file->pos = dfs_lfs_fd->u.dir.pos;
|
||||||
|
}
|
||||||
|
|
||||||
|
return (file->pos);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int _dfs_lfs_getdents(struct dfs_file* file, struct dirent* dirp, uint32_t count)
|
||||||
|
{
|
||||||
|
dfs_lfs_fd_t* dfs_lfs_fd;
|
||||||
|
int result;
|
||||||
|
int index;
|
||||||
|
struct dirent* d;
|
||||||
|
struct lfs_info info;
|
||||||
|
|
||||||
|
RT_ASSERT(file->data != RT_NULL);
|
||||||
|
|
||||||
|
dfs_lfs_fd = (dfs_lfs_fd_t*)(file->data);
|
||||||
|
|
||||||
|
/* make integer count */
|
||||||
|
count = (count / sizeof(struct dirent)) * sizeof(struct dirent);
|
||||||
|
if (count == 0)
|
||||||
|
{
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
index = 0;
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
d = dirp + index;
|
||||||
|
|
||||||
|
result = lfs_dir_read(dfs_lfs_fd->lfs, &dfs_lfs_fd->u.dir, &info);
|
||||||
|
if ((result != 1) || (info.name[0] == 0))
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (rt_strcmp(info.name, ".") == 0)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
else if (rt_strcmp(info.name, "..") == 0)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
d->d_type = DT_UNKNOWN;
|
||||||
|
|
||||||
|
switch (info.type)
|
||||||
|
{
|
||||||
|
case LFS_TYPE_DIR:
|
||||||
|
d->d_type |= DT_DIR;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case LFS_TYPE_REG:
|
||||||
|
d->d_type |= DT_REG;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
d->d_namlen = (rt_uint8_t)rt_strlen(info.name);
|
||||||
|
d->d_reclen = (rt_uint16_t)sizeof(struct dirent);
|
||||||
|
rt_strncpy(d->d_name, info.name, DFS_PATH_MAX);
|
||||||
|
|
||||||
|
index++;
|
||||||
|
if (index * sizeof(struct dirent) >= count)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (index == 0)
|
||||||
|
{
|
||||||
|
return _lfs_result_to_dfs(result);
|
||||||
|
}
|
||||||
|
|
||||||
|
file->pos += index * sizeof(struct dirent);
|
||||||
|
|
||||||
|
return index * sizeof(struct dirent);
|
||||||
|
}
|
||||||
|
|
||||||
|
static const struct dfs_file_ops _dfs_lfs_fops = {
|
||||||
|
_dfs_lfs_open,
|
||||||
|
_dfs_lfs_close,
|
||||||
|
_dfs_lfs_ioctl,
|
||||||
|
_dfs_lfs_read,
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
_dfs_lfs_write,
|
||||||
|
#else
|
||||||
|
NULL,
|
||||||
|
#endif
|
||||||
|
_dfs_lfs_flush,
|
||||||
|
_dfs_lfs_lseek,
|
||||||
|
_dfs_lfs_getdents,
|
||||||
|
// RT_NULL, /* poll interface */
|
||||||
|
};
|
||||||
|
|
||||||
|
static const struct dfs_filesystem_ops _dfs_lfs_ops = {
|
||||||
|
"lfs",
|
||||||
|
DFS_FS_FLAG_DEFAULT,
|
||||||
|
&_dfs_lfs_fops,
|
||||||
|
_dfs_lfs_mount,
|
||||||
|
_dfs_lfs_unmount,
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
_dfs_lfs_mkfs,
|
||||||
|
#else
|
||||||
|
NULL,
|
||||||
|
#endif
|
||||||
|
_dfs_lfs_statfs,
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
_dfs_lfs_unlink,
|
||||||
|
#else
|
||||||
|
NULL,
|
||||||
|
#endif
|
||||||
|
_dfs_lfs_stat,
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
_dfs_lfs_rename,
|
||||||
|
#else
|
||||||
|
NULL,
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
int dfs_lfs_init(void)
|
||||||
|
{
|
||||||
|
/* register ram file system */
|
||||||
|
return dfs_register(&_dfs_lfs_ops);
|
||||||
|
}
|
||||||
|
INIT_COMPONENT_EXPORT(dfs_lfs_init);
|
||||||
Vendored
+6549
File diff suppressed because it is too large.
Load diff
Vendored
+801
@@ -0,0 +1,801 @@
|
|||||||
|
/*
|
||||||
|
* The little filesystem
|
||||||
|
*
|
||||||
|
* Copyright (c) 2022, The littlefs authors.
|
||||||
|
* Copyright (c) 2017, Arm Limited. All rights reserved.
|
||||||
|
* SPDX-License-Identifier: BSD-3-Clause
|
||||||
|
*/
|
||||||
|
#ifndef LFS_H
|
||||||
|
#define LFS_H
|
||||||
|
|
||||||
|
#include "lfs_util.h"
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C"
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
/// Version info ///
|
||||||
|
|
||||||
|
// Software library version
|
||||||
|
// Major (top-nibble), incremented on backwards incompatible changes
|
||||||
|
// Minor (bottom-nibble), incremented on feature additions
|
||||||
|
#define LFS_VERSION 0x0002000b
|
||||||
|
#define LFS_VERSION_MAJOR (0xffff & (LFS_VERSION >> 16))
|
||||||
|
#define LFS_VERSION_MINOR (0xffff & (LFS_VERSION >> 0))
|
||||||
|
|
||||||
|
// Version of On-disk data structures
|
||||||
|
// Major (top-nibble), incremented on backwards incompatible changes
|
||||||
|
// Minor (bottom-nibble), incremented on feature additions
|
||||||
|
#define LFS_DISK_VERSION 0x00020001
|
||||||
|
#define LFS_DISK_VERSION_MAJOR (0xffff & (LFS_DISK_VERSION >> 16))
|
||||||
|
#define LFS_DISK_VERSION_MINOR (0xffff & (LFS_DISK_VERSION >> 0))
|
||||||
|
|
||||||
|
|
||||||
|
/// Definitions ///
|
||||||
|
|
||||||
|
// Type definitions
|
||||||
|
typedef uint32_t lfs_size_t;
|
||||||
|
typedef uint32_t lfs_off_t;
|
||||||
|
|
||||||
|
typedef int32_t lfs_ssize_t;
|
||||||
|
typedef int32_t lfs_soff_t;
|
||||||
|
|
||||||
|
typedef uint32_t lfs_block_t;
|
||||||
|
|
||||||
|
// Maximum name size in bytes, may be redefined to reduce the size of the
|
||||||
|
// info struct. Limited to <= 1022. Stored in superblock and must be
|
||||||
|
// respected by other littlefs drivers.
|
||||||
|
#ifndef LFS_NAME_MAX
|
||||||
|
#define LFS_NAME_MAX 255
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Maximum size of a file in bytes, may be redefined to limit to support other
|
||||||
|
// drivers. Limited on disk to <= 2147483647. Stored in superblock and must be
|
||||||
|
// respected by other littlefs drivers.
|
||||||
|
#ifndef LFS_FILE_MAX
|
||||||
|
#define LFS_FILE_MAX 2147483647
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Maximum size of custom attributes in bytes, may be redefined, but there is
|
||||||
|
// no real benefit to using a smaller LFS_ATTR_MAX. Limited to <= 1022. Stored
|
||||||
|
// in superblock and must be respected by other littlefs drivers.
|
||||||
|
#ifndef LFS_ATTR_MAX
|
||||||
|
#define LFS_ATTR_MAX 1022
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Possible error codes, these are negative to allow
|
||||||
|
// valid positive return values
|
||||||
|
enum lfs_error {
|
||||||
|
LFS_ERR_OK = 0, // No error
|
||||||
|
LFS_ERR_IO = -5, // Error during device operation
|
||||||
|
LFS_ERR_CORRUPT = -84, // Corrupted
|
||||||
|
LFS_ERR_NOENT = -2, // No directory entry
|
||||||
|
LFS_ERR_EXIST = -17, // Entry already exists
|
||||||
|
LFS_ERR_NOTDIR = -20, // Entry is not a dir
|
||||||
|
LFS_ERR_ISDIR = -21, // Entry is a dir
|
||||||
|
LFS_ERR_NOTEMPTY = -39, // Dir is not empty
|
||||||
|
LFS_ERR_BADF = -9, // Bad file number
|
||||||
|
LFS_ERR_FBIG = -27, // File too large
|
||||||
|
LFS_ERR_INVAL = -22, // Invalid parameter
|
||||||
|
LFS_ERR_NOSPC = -28, // No space left on device
|
||||||
|
LFS_ERR_NOMEM = -12, // No more memory available
|
||||||
|
LFS_ERR_NOATTR = -61, // No data/attr available
|
||||||
|
LFS_ERR_NAMETOOLONG = -36, // File name too long
|
||||||
|
};
|
||||||
|
|
||||||
|
// File types
|
||||||
|
enum lfs_type {
|
||||||
|
// file types
|
||||||
|
LFS_TYPE_REG = 0x001,
|
||||||
|
LFS_TYPE_DIR = 0x002,
|
||||||
|
|
||||||
|
// internally used types
|
||||||
|
LFS_TYPE_SPLICE = 0x400,
|
||||||
|
LFS_TYPE_NAME = 0x000,
|
||||||
|
LFS_TYPE_STRUCT = 0x200,
|
||||||
|
LFS_TYPE_USERATTR = 0x300,
|
||||||
|
LFS_TYPE_FROM = 0x100,
|
||||||
|
LFS_TYPE_TAIL = 0x600,
|
||||||
|
LFS_TYPE_GLOBALS = 0x700,
|
||||||
|
LFS_TYPE_CRC = 0x500,
|
||||||
|
|
||||||
|
// internally used type specializations
|
||||||
|
LFS_TYPE_CREATE = 0x401,
|
||||||
|
LFS_TYPE_DELETE = 0x4ff,
|
||||||
|
LFS_TYPE_SUPERBLOCK = 0x0ff,
|
||||||
|
LFS_TYPE_DIRSTRUCT = 0x200,
|
||||||
|
LFS_TYPE_CTZSTRUCT = 0x202,
|
||||||
|
LFS_TYPE_INLINESTRUCT = 0x201,
|
||||||
|
LFS_TYPE_SOFTTAIL = 0x600,
|
||||||
|
LFS_TYPE_HARDTAIL = 0x601,
|
||||||
|
LFS_TYPE_MOVESTATE = 0x7ff,
|
||||||
|
LFS_TYPE_CCRC = 0x500,
|
||||||
|
LFS_TYPE_FCRC = 0x5ff,
|
||||||
|
|
||||||
|
// internal chip sources
|
||||||
|
LFS_FROM_NOOP = 0x000,
|
||||||
|
LFS_FROM_MOVE = 0x101,
|
||||||
|
LFS_FROM_USERATTRS = 0x102,
|
||||||
|
};
|
||||||
|
|
||||||
|
// File open flags
|
||||||
|
enum lfs_open_flags {
|
||||||
|
// open flags
|
||||||
|
LFS_O_RDONLY = 1, // Open a file as read only
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
LFS_O_WRONLY = 2, // Open a file as write only
|
||||||
|
LFS_O_RDWR = 3, // Open a file as read and write
|
||||||
|
LFS_O_CREAT = 0x0100, // Create a file if it does not exist
|
||||||
|
LFS_O_EXCL = 0x0200, // Fail if a file already exists
|
||||||
|
LFS_O_TRUNC = 0x0400, // Truncate the existing file to zero size
|
||||||
|
LFS_O_APPEND = 0x0800, // Move to end of file on every write
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// internally used flags
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
LFS_F_DIRTY = 0x010000, // File does not match storage
|
||||||
|
LFS_F_WRITING = 0x020000, // File has been written since last flush
|
||||||
|
#endif
|
||||||
|
LFS_F_READING = 0x040000, // File has been read since last flush
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
LFS_F_ERRED = 0x080000, // An error occurred during write
|
||||||
|
#endif
|
||||||
|
LFS_F_INLINE = 0x100000, // Currently inlined in directory entry
|
||||||
|
};
|
||||||
|
|
||||||
|
// File seek flags
|
||||||
|
enum lfs_whence_flags {
|
||||||
|
LFS_SEEK_SET = 0, // Seek relative to an absolute position
|
||||||
|
LFS_SEEK_CUR = 1, // Seek relative to the current file position
|
||||||
|
LFS_SEEK_END = 2, // Seek relative to the end of the file
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// Configuration provided during initialization of the littlefs
|
||||||
|
struct lfs_config {
|
||||||
|
// Opaque user provided context that can be used to pass
|
||||||
|
// information to the block device operations
|
||||||
|
void *context;
|
||||||
|
|
||||||
|
// Read a region in a block. Negative error codes are propagated
|
||||||
|
// to the user.
|
||||||
|
int (*read)(const struct lfs_config *c, lfs_block_t block,
|
||||||
|
lfs_off_t off, void *buffer, lfs_size_t size);
|
||||||
|
|
||||||
|
// Program a region in a block. The block must have previously
|
||||||
|
// been erased. Negative error codes are propagated to the user.
|
||||||
|
// May return LFS_ERR_CORRUPT if the block should be considered bad.
|
||||||
|
int (*prog)(const struct lfs_config *c, lfs_block_t block,
|
||||||
|
lfs_off_t off, const void *buffer, lfs_size_t size);
|
||||||
|
|
||||||
|
// Erase a block. A block must be erased before being programmed.
|
||||||
|
// The state of an erased block is undefined. Negative error codes
|
||||||
|
// are propagated to the user.
|
||||||
|
// May return LFS_ERR_CORRUPT if the block should be considered bad.
|
||||||
|
int (*erase)(const struct lfs_config *c, lfs_block_t block);
|
||||||
|
|
||||||
|
// Sync the state of the underlying block device. Negative error codes
|
||||||
|
// are propagated to the user.
|
||||||
|
int (*sync)(const struct lfs_config *c);
|
||||||
|
|
||||||
|
#ifdef LFS_THREADSAFE
|
||||||
|
// Lock the underlying block device. Negative error codes
|
||||||
|
// are propagated to the user.
|
||||||
|
int (*lock)(const struct lfs_config *c);
|
||||||
|
|
||||||
|
// Unlock the underlying block device. Negative error codes
|
||||||
|
// are propagated to the user.
|
||||||
|
int (*unlock)(const struct lfs_config *c);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Minimum size of a block read in bytes. All read operations will be a
|
||||||
|
// multiple of this value.
|
||||||
|
lfs_size_t read_size;
|
||||||
|
|
||||||
|
// Minimum size of a block program in bytes. All program operations will be
|
||||||
|
// a multiple of this value.
|
||||||
|
lfs_size_t prog_size;
|
||||||
|
|
||||||
|
// Size of an erasable block in bytes. This does not impact ram consumption
|
||||||
|
// and may be larger than the physical erase size. However, non-inlined
|
||||||
|
// files take up at minimum one block. Must be a multiple of the read and
|
||||||
|
// program sizes.
|
||||||
|
lfs_size_t block_size;
|
||||||
|
|
||||||
|
// Number of erasable blocks on the device. Defaults to block_count stored
|
||||||
|
// on disk when zero.
|
||||||
|
lfs_size_t block_count;
|
||||||
|
|
||||||
|
// Number of erase cycles before littlefs evicts metadata logs and moves
|
||||||
|
// the metadata to another block. Suggested values are in the
|
||||||
|
// range 100-1000, with large values having better performance at the cost
|
||||||
|
// of less consistent wear distribution.
|
||||||
|
//
|
||||||
|
// Set to -1 to disable block-level wear-leveling.
|
||||||
|
int32_t block_cycles;
|
||||||
|
|
||||||
|
// Size of block caches in bytes. Each cache buffers a portion of a block in
|
||||||
|
// RAM. The littlefs needs a read cache, a program cache, and one additional
|
||||||
|
// cache per file. Larger caches can improve performance by storing more
|
||||||
|
// data and reducing the number of disk accesses. Must be a multiple of the
|
||||||
|
// read and program sizes, and a factor of the block size.
|
||||||
|
lfs_size_t cache_size;
|
||||||
|
|
||||||
|
// Size of the lookahead buffer in bytes. A larger lookahead buffer
|
||||||
|
// increases the number of blocks found during an allocation pass. The
|
||||||
|
// lookahead buffer is stored as a compact bitmap, so each byte of RAM
|
||||||
|
// can track 8 blocks.
|
||||||
|
lfs_size_t lookahead_size;
|
||||||
|
|
||||||
|
// Threshold for metadata compaction during lfs_fs_gc in bytes. Metadata
|
||||||
|
// pairs that exceed this threshold will be compacted during lfs_fs_gc.
|
||||||
|
// Defaults to ~88% block_size when zero, though the default may change
|
||||||
|
// in the future.
|
||||||
|
//
|
||||||
|
// Note this only affects lfs_fs_gc. Normal compactions still only occur
|
||||||
|
// when full.
|
||||||
|
//
|
||||||
|
// Set to -1 to disable metadata compaction during lfs_fs_gc.
|
||||||
|
lfs_size_t compact_thresh;
|
||||||
|
|
||||||
|
// Optional statically allocated read buffer. Must be cache_size.
|
||||||
|
// By default lfs_malloc is used to allocate this buffer.
|
||||||
|
void *read_buffer;
|
||||||
|
|
||||||
|
// Optional statically allocated program buffer. Must be cache_size.
|
||||||
|
// By default lfs_malloc is used to allocate this buffer.
|
||||||
|
void *prog_buffer;
|
||||||
|
|
||||||
|
// Optional statically allocated lookahead buffer. Must be lookahead_size.
|
||||||
|
// By default lfs_malloc is used to allocate this buffer.
|
||||||
|
void *lookahead_buffer;
|
||||||
|
|
||||||
|
// Optional upper limit on length of file names in bytes. No downside for
|
||||||
|
// larger names except the size of the info struct which is controlled by
|
||||||
|
// the LFS_NAME_MAX define. Defaults to LFS_NAME_MAX or name_max stored on
|
||||||
|
// disk when zero.
|
||||||
|
lfs_size_t name_max;
|
||||||
|
|
||||||
|
// Optional upper limit on files in bytes. No downside for larger files
|
||||||
|
// but must be <= LFS_FILE_MAX. Defaults to LFS_FILE_MAX or file_max stored
|
||||||
|
// on disk when zero.
|
||||||
|
lfs_size_t file_max;
|
||||||
|
|
||||||
|
// Optional upper limit on custom attributes in bytes. No downside for
|
||||||
|
// larger attributes size but must be <= LFS_ATTR_MAX. Defaults to
|
||||||
|
// LFS_ATTR_MAX or attr_max stored on disk when zero.
|
||||||
|
lfs_size_t attr_max;
|
||||||
|
|
||||||
|
// Optional upper limit on total space given to metadata pairs in bytes. On
|
||||||
|
// devices with large blocks (e.g. 128kB) setting this to a low size (2-8kB)
|
||||||
|
// can help bound the metadata compaction time. Must be <= block_size.
|
||||||
|
// Defaults to block_size when zero.
|
||||||
|
lfs_size_t metadata_max;
|
||||||
|
|
||||||
|
// Optional upper limit on inlined files in bytes. Inlined files live in
|
||||||
|
// metadata and decrease storage requirements, but may be limited to
|
||||||
|
// improve metadata-related performance. Must be <= cache_size, <=
|
||||||
|
// attr_max, and <= block_size/8. Defaults to the largest possible
|
||||||
|
// inline_max when zero.
|
||||||
|
//
|
||||||
|
// Set to -1 to disable inlined files.
|
||||||
|
lfs_size_t inline_max;
|
||||||
|
|
||||||
|
#ifdef LFS_MULTIVERSION
|
||||||
|
// On-disk version to use when writing in the form of 16-bit major version
|
||||||
|
// + 16-bit minor version. This limiting metadata to what is supported by
|
||||||
|
// older minor versions. Note that some features will be lost. Defaults to
|
||||||
|
// to the most recent minor version when zero.
|
||||||
|
uint32_t disk_version;
|
||||||
|
#endif
|
||||||
|
};
|
||||||
|
|
||||||
|
// File info structure
|
||||||
|
struct lfs_info {
|
||||||
|
// Type of the file, either LFS_TYPE_REG or LFS_TYPE_DIR
|
||||||
|
uint8_t type;
|
||||||
|
|
||||||
|
// Size of the file, only valid for REG files. Limited to 32-bits.
|
||||||
|
lfs_size_t size;
|
||||||
|
|
||||||
|
// Name of the file stored as a null-terminated string. Limited to
|
||||||
|
// LFS_NAME_MAX+1, which can be changed by redefining LFS_NAME_MAX to
|
||||||
|
// reduce RAM. LFS_NAME_MAX is stored in superblock and must be
|
||||||
|
// respected by other littlefs drivers.
|
||||||
|
char name[LFS_NAME_MAX+1];
|
||||||
|
};
|
||||||
|
|
||||||
|
// Filesystem info structure
|
||||||
|
struct lfs_fsinfo {
|
||||||
|
// On-disk version.
|
||||||
|
uint32_t disk_version;
|
||||||
|
|
||||||
|
// Size of a logical block in bytes.
|
||||||
|
lfs_size_t block_size;
|
||||||
|
|
||||||
|
// Number of logical blocks in filesystem.
|
||||||
|
lfs_size_t block_count;
|
||||||
|
|
||||||
|
// Upper limit on the length of file names in bytes.
|
||||||
|
lfs_size_t name_max;
|
||||||
|
|
||||||
|
// Upper limit on the size of files in bytes.
|
||||||
|
lfs_size_t file_max;
|
||||||
|
|
||||||
|
// Upper limit on the size of custom attributes in bytes.
|
||||||
|
lfs_size_t attr_max;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Custom attribute structure, used to describe custom attributes
|
||||||
|
// committed atomically during file writes.
|
||||||
|
struct lfs_attr {
|
||||||
|
// 8-bit type of attribute, provided by user and used to
|
||||||
|
// identify the attribute
|
||||||
|
uint8_t type;
|
||||||
|
|
||||||
|
// Pointer to buffer containing the attribute
|
||||||
|
void *buffer;
|
||||||
|
|
||||||
|
// Size of attribute in bytes, limited to LFS_ATTR_MAX
|
||||||
|
lfs_size_t size;
|
||||||
|
};
|
||||||
|
|
||||||
|
// Optional configuration provided during lfs_file_opencfg
|
||||||
|
struct lfs_file_config {
|
||||||
|
// Optional statically allocated file buffer. Must be cache_size.
|
||||||
|
// By default lfs_malloc is used to allocate this buffer.
|
||||||
|
void *buffer;
|
||||||
|
|
||||||
|
// Optional list of custom attributes related to the file. If the file
|
||||||
|
// is opened with read access, these attributes will be read from disk
|
||||||
|
// during the open call. If the file is opened with write access, the
|
||||||
|
// attributes will be written to disk every file sync or close. This
|
||||||
|
// write occurs atomically with update to the file's contents.
|
||||||
|
//
|
||||||
|
// Custom attributes are uniquely identified by an 8-bit type and limited
|
||||||
|
// to LFS_ATTR_MAX bytes. When read, if the stored attribute is smaller
|
||||||
|
// than the buffer, it will be padded with zeros. If the stored attribute
|
||||||
|
// is larger, then it will be silently truncated. If the attribute is not
|
||||||
|
// found, it will be created implicitly.
|
||||||
|
struct lfs_attr *attrs;
|
||||||
|
|
||||||
|
// Number of custom attributes in the list
|
||||||
|
lfs_size_t attr_count;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/// internal littlefs data structures ///
|
||||||
|
typedef struct lfs_cache {
|
||||||
|
lfs_block_t block;
|
||||||
|
lfs_off_t off;
|
||||||
|
lfs_size_t size;
|
||||||
|
uint8_t *buffer;
|
||||||
|
} lfs_cache_t;
|
||||||
|
|
||||||
|
typedef struct lfs_mdir {
|
||||||
|
lfs_block_t pair[2];
|
||||||
|
uint32_t rev;
|
||||||
|
lfs_off_t off;
|
||||||
|
uint32_t etag;
|
||||||
|
uint16_t count;
|
||||||
|
bool erased;
|
||||||
|
bool split;
|
||||||
|
lfs_block_t tail[2];
|
||||||
|
} lfs_mdir_t;
|
||||||
|
|
||||||
|
// littlefs directory type
|
||||||
|
typedef struct lfs_dir {
|
||||||
|
struct lfs_dir *next;
|
||||||
|
uint16_t id;
|
||||||
|
uint8_t type;
|
||||||
|
lfs_mdir_t m;
|
||||||
|
|
||||||
|
lfs_off_t pos;
|
||||||
|
lfs_block_t head[2];
|
||||||
|
} lfs_dir_t;
|
||||||
|
|
||||||
|
// littlefs file type
|
||||||
|
typedef struct lfs_file {
|
||||||
|
struct lfs_file *next;
|
||||||
|
uint16_t id;
|
||||||
|
uint8_t type;
|
||||||
|
lfs_mdir_t m;
|
||||||
|
|
||||||
|
struct lfs_ctz {
|
||||||
|
lfs_block_t head;
|
||||||
|
lfs_size_t size;
|
||||||
|
} ctz;
|
||||||
|
|
||||||
|
uint32_t flags;
|
||||||
|
lfs_off_t pos;
|
||||||
|
lfs_block_t block;
|
||||||
|
lfs_off_t off;
|
||||||
|
lfs_cache_t cache;
|
||||||
|
|
||||||
|
const struct lfs_file_config *cfg;
|
||||||
|
} lfs_file_t;
|
||||||
|
|
||||||
|
typedef struct lfs_superblock {
|
||||||
|
uint32_t version;
|
||||||
|
lfs_size_t block_size;
|
||||||
|
lfs_size_t block_count;
|
||||||
|
lfs_size_t name_max;
|
||||||
|
lfs_size_t file_max;
|
||||||
|
lfs_size_t attr_max;
|
||||||
|
} lfs_superblock_t;
|
||||||
|
|
||||||
|
typedef struct lfs_gstate {
|
||||||
|
uint32_t tag;
|
||||||
|
lfs_block_t pair[2];
|
||||||
|
} lfs_gstate_t;
|
||||||
|
|
||||||
|
// The littlefs filesystem type
|
||||||
|
typedef struct lfs {
|
||||||
|
lfs_cache_t rcache;
|
||||||
|
lfs_cache_t pcache;
|
||||||
|
|
||||||
|
lfs_block_t root[2];
|
||||||
|
struct lfs_mlist {
|
||||||
|
struct lfs_mlist *next;
|
||||||
|
uint16_t id;
|
||||||
|
uint8_t type;
|
||||||
|
lfs_mdir_t m;
|
||||||
|
} *mlist;
|
||||||
|
uint32_t seed;
|
||||||
|
|
||||||
|
lfs_gstate_t gstate;
|
||||||
|
lfs_gstate_t gdisk;
|
||||||
|
lfs_gstate_t gdelta;
|
||||||
|
|
||||||
|
struct lfs_lookahead {
|
||||||
|
lfs_block_t start;
|
||||||
|
lfs_block_t size;
|
||||||
|
lfs_block_t next;
|
||||||
|
lfs_block_t ckpoint;
|
||||||
|
uint8_t *buffer;
|
||||||
|
} lookahead;
|
||||||
|
|
||||||
|
const struct lfs_config *cfg;
|
||||||
|
lfs_size_t block_count;
|
||||||
|
lfs_size_t name_max;
|
||||||
|
lfs_size_t file_max;
|
||||||
|
lfs_size_t attr_max;
|
||||||
|
lfs_size_t inline_max;
|
||||||
|
|
||||||
|
#ifdef LFS_MIGRATE
|
||||||
|
struct lfs1 *lfs1;
|
||||||
|
#endif
|
||||||
|
} lfs_t;
|
||||||
|
|
||||||
|
|
||||||
|
/// Filesystem functions ///
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Format a block device with the littlefs
|
||||||
|
//
|
||||||
|
// Requires a littlefs object and config struct. This clobbers the littlefs
|
||||||
|
// object, and does not leave the filesystem mounted. The config struct must
|
||||||
|
// be zeroed for defaults and backwards compatibility.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_format(lfs_t *lfs, const struct lfs_config *config);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Mounts a littlefs
|
||||||
|
//
|
||||||
|
// Requires a littlefs object and config struct. Multiple filesystems
|
||||||
|
// may be mounted simultaneously with multiple littlefs objects. Both
|
||||||
|
// lfs and config must be allocated while mounted. The config struct must
|
||||||
|
// be zeroed for defaults and backwards compatibility.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_mount(lfs_t *lfs, const struct lfs_config *config);
|
||||||
|
|
||||||
|
// Unmounts a littlefs
|
||||||
|
//
|
||||||
|
// Does nothing besides releasing any allocated resources.
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_unmount(lfs_t *lfs);
|
||||||
|
|
||||||
|
/// General operations ///
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Removes a file or directory
|
||||||
|
//
|
||||||
|
// If removing a directory, the directory must be empty.
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_remove(lfs_t *lfs, const char *path);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Rename or move a file or directory
|
||||||
|
//
|
||||||
|
// If the destination exists, it must match the source in type.
|
||||||
|
// If the destination is a directory, the directory must be empty.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_rename(lfs_t *lfs, const char *oldpath, const char *newpath);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Find info about a file or directory
|
||||||
|
//
|
||||||
|
// Fills out the info structure, based on the specified file or directory.
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_stat(lfs_t *lfs, const char *path, struct lfs_info *info);
|
||||||
|
|
||||||
|
// Get a custom attribute
|
||||||
|
//
|
||||||
|
// Custom attributes are uniquely identified by an 8-bit type and limited
|
||||||
|
// to LFS_ATTR_MAX bytes. When read, if the stored attribute is smaller than
|
||||||
|
// the buffer, it will be padded with zeros. If the stored attribute is larger,
|
||||||
|
// then it will be silently truncated. If no attribute is found, the error
|
||||||
|
// LFS_ERR_NOATTR is returned and the buffer is filled with zeros.
|
||||||
|
//
|
||||||
|
// Returns the size of the attribute, or a negative error code on failure.
|
||||||
|
// Note, the returned size is the size of the attribute on disk, irrespective
|
||||||
|
// of the size of the buffer. This can be used to dynamically allocate a buffer
|
||||||
|
// or check for existence.
|
||||||
|
lfs_ssize_t lfs_getattr(lfs_t *lfs, const char *path,
|
||||||
|
uint8_t type, void *buffer, lfs_size_t size);
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Set custom attributes
|
||||||
|
//
|
||||||
|
// Custom attributes are uniquely identified by an 8-bit type and limited
|
||||||
|
// to LFS_ATTR_MAX bytes. If an attribute is not found, it will be
|
||||||
|
// implicitly created.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_setattr(lfs_t *lfs, const char *path,
|
||||||
|
uint8_t type, const void *buffer, lfs_size_t size);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Removes a custom attribute
|
||||||
|
//
|
||||||
|
// If an attribute is not found, nothing happens.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_removeattr(lfs_t *lfs, const char *path, uint8_t type);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
/// File operations ///
|
||||||
|
|
||||||
|
#ifndef LFS_NO_MALLOC
|
||||||
|
// Open a file
|
||||||
|
//
|
||||||
|
// The mode that the file is opened in is determined by the flags, which
|
||||||
|
// are values from the enum lfs_open_flags that are bitwise-ored together.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_file_open(lfs_t *lfs, lfs_file_t *file,
|
||||||
|
const char *path, int flags);
|
||||||
|
|
||||||
|
// if LFS_NO_MALLOC is defined, lfs_file_open() will fail with LFS_ERR_NOMEM
|
||||||
|
// thus use lfs_file_opencfg() with config.buffer set.
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Open a file with extra configuration
|
||||||
|
//
|
||||||
|
// The mode that the file is opened in is determined by the flags, which
|
||||||
|
// are values from the enum lfs_open_flags that are bitwise-ored together.
|
||||||
|
//
|
||||||
|
// The config struct provides additional config options per file as described
|
||||||
|
// above. The config struct must remain allocated while the file is open, and
|
||||||
|
// the config struct must be zeroed for defaults and backwards compatibility.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_file_opencfg(lfs_t *lfs, lfs_file_t *file,
|
||||||
|
const char *path, int flags,
|
||||||
|
const struct lfs_file_config *config);
|
||||||
|
|
||||||
|
// Close a file
|
||||||
|
//
|
||||||
|
// Any pending writes are written out to storage as though
|
||||||
|
// sync had been called and releases any allocated resources.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_file_close(lfs_t *lfs, lfs_file_t *file);
|
||||||
|
|
||||||
|
// Synchronize a file on storage
|
||||||
|
//
|
||||||
|
// Any pending writes are written out to storage.
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_file_sync(lfs_t *lfs, lfs_file_t *file);
|
||||||
|
|
||||||
|
// Read data from file
|
||||||
|
//
|
||||||
|
// Takes a buffer and size indicating where to store the read data.
|
||||||
|
// Returns the number of bytes read, or a negative error code on failure.
|
||||||
|
lfs_ssize_t lfs_file_read(lfs_t *lfs, lfs_file_t *file,
|
||||||
|
void *buffer, lfs_size_t size);
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Write data to file
|
||||||
|
//
|
||||||
|
// Takes a buffer and size indicating the data to write. The file will not
|
||||||
|
// actually be updated on the storage until either sync or close is called.
|
||||||
|
//
|
||||||
|
// Returns the number of bytes written, or a negative error code on failure.
|
||||||
|
lfs_ssize_t lfs_file_write(lfs_t *lfs, lfs_file_t *file,
|
||||||
|
const void *buffer, lfs_size_t size);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Change the position of the file
|
||||||
|
//
|
||||||
|
// The change in position is determined by the offset and whence flag.
|
||||||
|
// Returns the new position of the file, or a negative error code on failure.
|
||||||
|
lfs_soff_t lfs_file_seek(lfs_t *lfs, lfs_file_t *file,
|
||||||
|
lfs_soff_t off, int whence);
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Truncates the size of the file to the specified size
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_file_truncate(lfs_t *lfs, lfs_file_t *file, lfs_off_t size);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Return the position of the file
|
||||||
|
//
|
||||||
|
// Equivalent to lfs_file_seek(lfs, file, 0, LFS_SEEK_CUR)
|
||||||
|
// Returns the position of the file, or a negative error code on failure.
|
||||||
|
lfs_soff_t lfs_file_tell(lfs_t *lfs, lfs_file_t *file);
|
||||||
|
|
||||||
|
// Change the position of the file to the beginning of the file
|
||||||
|
//
|
||||||
|
// Equivalent to lfs_file_seek(lfs, file, 0, LFS_SEEK_SET)
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_file_rewind(lfs_t *lfs, lfs_file_t *file);
|
||||||
|
|
||||||
|
// Return the size of the file
|
||||||
|
//
|
||||||
|
// Similar to lfs_file_seek(lfs, file, 0, LFS_SEEK_END)
|
||||||
|
// Returns the size of the file, or a negative error code on failure.
|
||||||
|
lfs_soff_t lfs_file_size(lfs_t *lfs, lfs_file_t *file);
|
||||||
|
|
||||||
|
|
||||||
|
/// Directory operations ///
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Create a directory
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_mkdir(lfs_t *lfs, const char *path);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Open a directory
|
||||||
|
//
|
||||||
|
// Once open a directory can be used with read to iterate over files.
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_dir_open(lfs_t *lfs, lfs_dir_t *dir, const char *path);
|
||||||
|
|
||||||
|
// Close a directory
|
||||||
|
//
|
||||||
|
// Releases any allocated resources.
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_dir_close(lfs_t *lfs, lfs_dir_t *dir);
|
||||||
|
|
||||||
|
// Read an entry in the directory
|
||||||
|
//
|
||||||
|
// Fills out the info structure, based on the specified file or directory.
|
||||||
|
// Returns a positive value on success, 0 at the end of directory,
|
||||||
|
// or a negative error code on failure.
|
||||||
|
int lfs_dir_read(lfs_t *lfs, lfs_dir_t *dir, struct lfs_info *info);
|
||||||
|
|
||||||
|
// Change the position of the directory
|
||||||
|
//
|
||||||
|
// The new off must be a value previous returned from tell and specifies
|
||||||
|
// an absolute offset in the directory seek.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_dir_seek(lfs_t *lfs, lfs_dir_t *dir, lfs_off_t off);
|
||||||
|
|
||||||
|
// Return the position of the directory
|
||||||
|
//
|
||||||
|
// The returned offset is only meant to be consumed by seek and may not make
|
||||||
|
// sense, but does indicate the current position in the directory iteration.
|
||||||
|
//
|
||||||
|
// Returns the position of the directory, or a negative error code on failure.
|
||||||
|
lfs_soff_t lfs_dir_tell(lfs_t *lfs, lfs_dir_t *dir);
|
||||||
|
|
||||||
|
// Change the position of the directory to the beginning of the directory
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_dir_rewind(lfs_t *lfs, lfs_dir_t *dir);
|
||||||
|
|
||||||
|
|
||||||
|
/// Filesystem-level filesystem operations
|
||||||
|
|
||||||
|
// Find on-disk info about the filesystem
|
||||||
|
//
|
||||||
|
// Fills out the fsinfo structure based on the filesystem found on-disk.
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_fs_stat(lfs_t *lfs, struct lfs_fsinfo *fsinfo);
|
||||||
|
|
||||||
|
// Finds the current size of the filesystem
|
||||||
|
//
|
||||||
|
// Note: Result is best effort. If files share COW structures, the returned
|
||||||
|
// size may be larger than the filesystem actually is.
|
||||||
|
//
|
||||||
|
// Returns the number of allocated blocks, or a negative error code on failure.
|
||||||
|
lfs_ssize_t lfs_fs_size(lfs_t *lfs);
|
||||||
|
|
||||||
|
// Traverse through all blocks in use by the filesystem
|
||||||
|
//
|
||||||
|
// The provided callback will be called with each block address that is
|
||||||
|
// currently in use by the filesystem. This can be used to determine which
|
||||||
|
// blocks are in use or how much of the storage is available.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_fs_traverse(lfs_t *lfs, int (*cb)(void*, lfs_block_t), void *data);
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Attempt to make the filesystem consistent and ready for writing
|
||||||
|
//
|
||||||
|
// Calling this function is not required, consistency will be implicitly
|
||||||
|
// enforced on the first operation that writes to the filesystem, but this
|
||||||
|
// function allows the work to be performed earlier and without other
|
||||||
|
// filesystem changes.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_fs_mkconsistent(lfs_t *lfs);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Attempt any janitorial work
|
||||||
|
//
|
||||||
|
// This currently:
|
||||||
|
// 1. Calls mkconsistent if not already consistent
|
||||||
|
// 2. Compacts metadata > compact_thresh
|
||||||
|
// 3. Populates the block allocator
|
||||||
|
//
|
||||||
|
// Though additional janitorial work may be added in the future.
|
||||||
|
//
|
||||||
|
// Calling this function is not required, but may allow the offloading of
|
||||||
|
// expensive janitorial work to a less time-critical code path.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure. Accomplishing nothing is not
|
||||||
|
// an error.
|
||||||
|
int lfs_fs_gc(lfs_t *lfs);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
// Grows the filesystem to a new size, updating the superblock with the new
|
||||||
|
// block count.
|
||||||
|
//
|
||||||
|
// If LFS_SHRINKNONRELOCATING is defined, this function will also accept
|
||||||
|
// block_counts smaller than the current configuration, after checking
|
||||||
|
// that none of the blocks that are being removed are in use.
|
||||||
|
// Note that littlefs's pseudorandom block allocation means that
|
||||||
|
// this is very unlikely to work in the general case.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_fs_grow(lfs_t *lfs, lfs_size_t block_count);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_READONLY
|
||||||
|
#ifdef LFS_MIGRATE
|
||||||
|
// Attempts to migrate a previous version of littlefs
|
||||||
|
//
|
||||||
|
// Behaves similarly to the lfs_format function. Attempts to mount
|
||||||
|
// the previous version of littlefs and update the filesystem so it can be
|
||||||
|
// mounted with the current version of littlefs.
|
||||||
|
//
|
||||||
|
// Requires a littlefs object and config struct. This clobbers the littlefs
|
||||||
|
// object, and does not leave the filesystem mounted. The config struct must
|
||||||
|
// be zeroed for defaults and backwards compatibility.
|
||||||
|
//
|
||||||
|
// Returns a negative error code on failure.
|
||||||
|
int lfs_migrate(lfs_t *lfs, const struct lfs_config *cfg);
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
} /* extern "C" */
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif
|
||||||
+202
@@ -0,0 +1,202 @@
|
|||||||
|
#ifndef _LFS_CONFIG_H_
|
||||||
|
#define _LFS_CONFIG_H_
|
||||||
|
|
||||||
|
#include <rtthread.h>
|
||||||
|
|
||||||
|
// System includes
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <inttypes.h>
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C"
|
||||||
|
{
|
||||||
|
#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
|
||||||
|
#ifdef LFS_YES_TRACE
|
||||||
|
#define LFS_TRACE(fmt, ...) \
|
||||||
|
rt_kprintf("%s:%d:trace: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_TRACE(...) LFS_TRACE_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_TRACE(...)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_NO_DEBUG
|
||||||
|
#define LFS_DEBUG_(fmt, ...) \
|
||||||
|
rt_kprintf("%s:%d:debug: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_DEBUG(...) LFS_DEBUG_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_DEBUG(...)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_NO_WARN
|
||||||
|
#define LFS_WARN_(fmt, ...) \
|
||||||
|
rt_kprintf("%s:%d:warn: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_WARN(...) LFS_WARN_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_WARN(...)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_NO_ERROR
|
||||||
|
#define LFS_ERROR_(fmt, ...) \
|
||||||
|
rt_kprintf("%s:%d:error: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_ERROR(...) LFS_ERROR_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_ERROR(...)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Runtime assertions
|
||||||
|
#ifndef LFS_NO_ASSERT
|
||||||
|
#define LFS_ASSERT(test) RT_ASSERT(test)
|
||||||
|
#else
|
||||||
|
#define LFS_ASSERT(test)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
// 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;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_min(uint32_t a, uint32_t b) {
|
||||||
|
return (a < b) ? a : b;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Align to nearest multiple of a size
|
||||||
|
static inline uint32_t lfs_aligndown(uint32_t a, uint32_t alignment) {
|
||||||
|
return a - (a % alignment);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_alignup(uint32_t a, uint32_t alignment) {
|
||||||
|
return lfs_aligndown(a + alignment-1, alignment);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Find the smallest power of 2 greater than or equal to a
|
||||||
|
static inline uint32_t lfs_npw2(uint32_t a) {
|
||||||
|
#if !defined(LFS_NO_INTRINSICS) && (defined(__GNUC__) || defined(__CC_ARM))
|
||||||
|
return 32 - __builtin_clz(a-1);
|
||||||
|
#else
|
||||||
|
uint32_t r = 0;
|
||||||
|
uint32_t s;
|
||||||
|
a -= 1;
|
||||||
|
s = (a > 0xffff) << 4; a >>= s; r |= s;
|
||||||
|
s = (a > 0xff ) << 3; a >>= s; r |= s;
|
||||||
|
s = (a > 0xf ) << 2; a >>= s; r |= s;
|
||||||
|
s = (a > 0x3 ) << 1; a >>= s; r |= s;
|
||||||
|
return (r | (a >> 1)) + 1;
|
||||||
|
#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(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(LFS_NO_INTRINSICS) && (defined(__GNUC__) || defined(__CC_ARM))
|
||||||
|
return __builtin_popcount(a);
|
||||||
|
#else
|
||||||
|
a = a - ((a >> 1) & 0x55555555);
|
||||||
|
a = (a & 0x33333333) + ((a >> 2) & 0x33333333);
|
||||||
|
return (((a + (a >> 4)) & 0xf0f0f0f) * 0x1010101) >> 24;
|
||||||
|
#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 between 32-bit little-endian and native order
|
||||||
|
static inline uint32_t lfs_fromle32(uint32_t a) {
|
||||||
|
#if !defined(LFS_NO_INTRINSICS) && ( \
|
||||||
|
(defined( BYTE_ORDER ) && defined( ORDER_LITTLE_ENDIAN ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_LITTLE_ENDIAN ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__))
|
||||||
|
return a;
|
||||||
|
#elif !defined(LFS_NO_INTRINSICS) && ( \
|
||||||
|
(defined( BYTE_ORDER ) && defined( ORDER_BIG_ENDIAN ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_BIG_ENDIAN ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__))
|
||||||
|
return __builtin_bswap32(a);
|
||||||
|
#else
|
||||||
|
return (((uint8_t*)&a)[0] << 0) |
|
||||||
|
(((uint8_t*)&a)[1] << 8) |
|
||||||
|
(((uint8_t*)&a)[2] << 16) |
|
||||||
|
(((uint8_t*)&a)[3] << 24);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_tole32(uint32_t a) {
|
||||||
|
return lfs_fromle32(a);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Convert between 32-bit big-endian and native order
|
||||||
|
static inline uint32_t lfs_frombe32(uint32_t a) {
|
||||||
|
#if !defined(LFS_NO_INTRINSICS) && ( \
|
||||||
|
(defined( BYTE_ORDER ) && defined( ORDER_LITTLE_ENDIAN ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_LITTLE_ENDIAN ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__))
|
||||||
|
return __builtin_bswap32(a);
|
||||||
|
#elif !defined(LFS_NO_INTRINSICS) && ( \
|
||||||
|
(defined( BYTE_ORDER ) && defined( ORDER_BIG_ENDIAN ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_BIG_ENDIAN ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__))
|
||||||
|
return a;
|
||||||
|
#else
|
||||||
|
return (((uint8_t*)&a)[0] << 24) |
|
||||||
|
(((uint8_t*)&a)[1] << 16) |
|
||||||
|
(((uint8_t*)&a)[2] << 8) |
|
||||||
|
(((uint8_t*)&a)[3] << 0);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_tobe32(uint32_t a) {
|
||||||
|
return lfs_frombe32(a);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Calculate CRC-32 with polynomial = 0x04c11db7
|
||||||
|
uint32_t lfs_crc(uint32_t crc, const void *buffer, size_t size);
|
||||||
|
|
||||||
|
// Allocate memory, only used if buffers are not provided to littlefs
|
||||||
|
// Note, memory must be 64-bit aligned
|
||||||
|
static inline void *lfs_malloc(size_t size) {
|
||||||
|
#ifndef LFS_NO_MALLOC
|
||||||
|
return rt_malloc(size);
|
||||||
|
#else
|
||||||
|
(void)size;
|
||||||
|
return NULL;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deallocate memory, only used if buffers are not provided to littlefs
|
||||||
|
static inline void lfs_free(void *p) {
|
||||||
|
#ifndef LFS_NO_MALLOC
|
||||||
|
rt_free(p);
|
||||||
|
#else
|
||||||
|
(void)p;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
} /* extern "C" */
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif
|
||||||
Vendored
+20
@@ -0,0 +1,20 @@
|
|||||||
|
#include "lfs_util.h"
|
||||||
|
|
||||||
|
// Software CRC implementation with small lookup table
|
||||||
|
uint32_t lfs_crc(uint32_t crc, const void *buffer, size_t size) {
|
||||||
|
static const uint32_t rtable[16] = {
|
||||||
|
0x00000000, 0x1db71064, 0x3b6e20c8, 0x26d930ac,
|
||||||
|
0x76dc4190, 0x6b6b51f4, 0x4db26158, 0x5005713c,
|
||||||
|
0xedb88320, 0xf00f9344, 0xd6d6a3e8, 0xcb61b38c,
|
||||||
|
0x9b64c2b0, 0x86d3d2d4, 0xa00ae278, 0xbdbdf21c,
|
||||||
|
};
|
||||||
|
|
||||||
|
const uint8_t *data = buffer;
|
||||||
|
|
||||||
|
for (size_t i = 0; i < size; i++) {
|
||||||
|
crc = (crc >> 4) ^ rtable[(crc ^ (data[i] >> 0)) & 0xf];
|
||||||
|
crc = (crc >> 4) ^ rtable[(crc ^ (data[i] >> 4)) & 0xf];
|
||||||
|
}
|
||||||
|
|
||||||
|
return crc;
|
||||||
|
}
|
||||||
Vendored
+37
@@ -0,0 +1,37 @@
|
|||||||
|
/*
|
||||||
|
* lfs util functions
|
||||||
|
*
|
||||||
|
* Copyright (c) 2022, The littlefs authors.
|
||||||
|
* Copyright (c) 2017, Arm Limited. All rights reserved.
|
||||||
|
* SPDX-License-Identifier: BSD-3-Clause
|
||||||
|
*/
|
||||||
|
#include "lfs_util.h"
|
||||||
|
|
||||||
|
// Only compile if user does not provide custom config
|
||||||
|
#ifndef LFS_CONFIG
|
||||||
|
|
||||||
|
|
||||||
|
// If user provides their own CRC impl we don't need this
|
||||||
|
#ifndef LFS_CRC
|
||||||
|
// Software CRC implementation with small lookup table
|
||||||
|
uint32_t lfs_crc(uint32_t crc, const void *buffer, size_t size) {
|
||||||
|
static const uint32_t rtable[16] = {
|
||||||
|
0x00000000, 0x1db71064, 0x3b6e20c8, 0x26d930ac,
|
||||||
|
0x76dc4190, 0x6b6b51f4, 0x4db26158, 0x5005713c,
|
||||||
|
0xedb88320, 0xf00f9344, 0xd6d6a3e8, 0xcb61b38c,
|
||||||
|
0x9b64c2b0, 0x86d3d2d4, 0xa00ae278, 0xbdbdf21c,
|
||||||
|
};
|
||||||
|
|
||||||
|
const uint8_t *data = buffer;
|
||||||
|
|
||||||
|
for (size_t i = 0; i < size; i++) {
|
||||||
|
crc = (crc >> 4) ^ rtable[(crc ^ (data[i] >> 0)) & 0xf];
|
||||||
|
crc = (crc >> 4) ^ rtable[(crc ^ (data[i] >> 4)) & 0xf];
|
||||||
|
}
|
||||||
|
|
||||||
|
return crc;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
||||||
Vendored
+273
@@ -0,0 +1,273 @@
|
|||||||
|
/*
|
||||||
|
* lfs utility functions
|
||||||
|
*
|
||||||
|
* Copyright (c) 2022, The littlefs authors.
|
||||||
|
* Copyright (c) 2017, Arm Limited. All rights reserved.
|
||||||
|
* SPDX-License-Identifier: BSD-3-Clause
|
||||||
|
*/
|
||||||
|
#ifndef LFS_UTIL_H
|
||||||
|
#define LFS_UTIL_H
|
||||||
|
|
||||||
|
#define LFS_STRINGIZE(x) LFS_STRINGIZE2(x)
|
||||||
|
#define LFS_STRINGIZE2(x) #x
|
||||||
|
|
||||||
|
// Users can override lfs_util.h with their own configuration by defining
|
||||||
|
// LFS_CONFIG as a header file to include (-DLFS_CONFIG=lfs_config.h).
|
||||||
|
//
|
||||||
|
// If LFS_CONFIG is used, none of the default utils will be emitted and must be
|
||||||
|
// provided by the config file. To start, I would suggest copying lfs_util.h
|
||||||
|
// and modifying as needed.
|
||||||
|
#ifdef LFS_CONFIG
|
||||||
|
#include LFS_STRINGIZE(LFS_CONFIG)
|
||||||
|
#else
|
||||||
|
|
||||||
|
// Alternatively, users can provide a header file which defines
|
||||||
|
// macros and other things consumed by littlefs.
|
||||||
|
//
|
||||||
|
// For example, provide my_defines.h, which contains
|
||||||
|
// something like:
|
||||||
|
//
|
||||||
|
// #include <stddef.h>
|
||||||
|
// extern void *my_malloc(size_t sz);
|
||||||
|
// #define LFS_MALLOC(sz) my_malloc(sz)
|
||||||
|
//
|
||||||
|
// And build littlefs with the header by defining LFS_DEFINES.
|
||||||
|
// (-DLFS_DEFINES=my_defines.h)
|
||||||
|
|
||||||
|
#ifdef LFS_DEFINES
|
||||||
|
#include LFS_STRINGIZE(LFS_DEFINES)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// System includes
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <inttypes.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) || \
|
||||||
|
defined(LFS_YES_TRACE)
|
||||||
|
#include <stdio.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C"
|
||||||
|
{
|
||||||
|
#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_TRACE
|
||||||
|
#ifdef LFS_YES_TRACE
|
||||||
|
#define LFS_TRACE_(fmt, ...) \
|
||||||
|
printf("%s:%d:trace: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_TRACE(...) LFS_TRACE_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_TRACE(...)
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_DEBUG
|
||||||
|
#ifndef LFS_NO_DEBUG
|
||||||
|
#define LFS_DEBUG_(fmt, ...) \
|
||||||
|
printf("%s:%d:debug: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_DEBUG(...) LFS_DEBUG_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_DEBUG(...)
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_WARN
|
||||||
|
#ifndef LFS_NO_WARN
|
||||||
|
#define LFS_WARN_(fmt, ...) \
|
||||||
|
printf("%s:%d:warn: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_WARN(...) LFS_WARN_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_WARN(...)
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef LFS_ERROR
|
||||||
|
#ifndef LFS_NO_ERROR
|
||||||
|
#define LFS_ERROR_(fmt, ...) \
|
||||||
|
printf("%s:%d:error: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__)
|
||||||
|
#define LFS_ERROR(...) LFS_ERROR_(__VA_ARGS__, "")
|
||||||
|
#else
|
||||||
|
#define LFS_ERROR(...)
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Runtime assertions
|
||||||
|
#ifndef LFS_ASSERT
|
||||||
|
#ifndef LFS_NO_ASSERT
|
||||||
|
#define LFS_ASSERT(test) assert(test)
|
||||||
|
#else
|
||||||
|
#define LFS_ASSERT(test)
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
// 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;
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_min(uint32_t a, uint32_t b) {
|
||||||
|
return (a < b) ? a : b;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Align to nearest multiple of a size
|
||||||
|
static inline uint32_t lfs_aligndown(uint32_t a, uint32_t alignment) {
|
||||||
|
return a - (a % alignment);
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_alignup(uint32_t a, uint32_t alignment) {
|
||||||
|
return lfs_aligndown(a + alignment-1, alignment);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Find the smallest power of 2 greater than or equal to a
|
||||||
|
static inline uint32_t lfs_npw2(uint32_t a) {
|
||||||
|
#if !defined(LFS_NO_INTRINSICS) && (defined(__GNUC__) || defined(__CC_ARM))
|
||||||
|
return 32 - __builtin_clz(a-1);
|
||||||
|
#else
|
||||||
|
uint32_t r = 0;
|
||||||
|
uint32_t s;
|
||||||
|
a -= 1;
|
||||||
|
s = (a > 0xffff) << 4; a >>= s; r |= s;
|
||||||
|
s = (a > 0xff ) << 3; a >>= s; r |= s;
|
||||||
|
s = (a > 0xf ) << 2; a >>= s; r |= s;
|
||||||
|
s = (a > 0x3 ) << 1; a >>= s; r |= s;
|
||||||
|
return (r | (a >> 1)) + 1;
|
||||||
|
#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(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(LFS_NO_INTRINSICS) && (defined(__GNUC__) || defined(__CC_ARM))
|
||||||
|
return __builtin_popcount(a);
|
||||||
|
#else
|
||||||
|
a = a - ((a >> 1) & 0x55555555);
|
||||||
|
a = (a & 0x33333333) + ((a >> 2) & 0x33333333);
|
||||||
|
return (((a + (a >> 4)) & 0xf0f0f0f) * 0x1010101) >> 24;
|
||||||
|
#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 between 32-bit little-endian and native order
|
||||||
|
static inline uint32_t lfs_fromle32(uint32_t a) {
|
||||||
|
#if (defined( BYTE_ORDER ) && defined( ORDER_LITTLE_ENDIAN ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_LITTLE_ENDIAN ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__)
|
||||||
|
return a;
|
||||||
|
#elif !defined(LFS_NO_INTRINSICS) && ( \
|
||||||
|
(defined( BYTE_ORDER ) && defined( ORDER_BIG_ENDIAN ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_BIG_ENDIAN ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__))
|
||||||
|
return __builtin_bswap32(a);
|
||||||
|
#else
|
||||||
|
return ((uint32_t)((uint8_t*)&a)[0] << 0) |
|
||||||
|
((uint32_t)((uint8_t*)&a)[1] << 8) |
|
||||||
|
((uint32_t)((uint8_t*)&a)[2] << 16) |
|
||||||
|
((uint32_t)((uint8_t*)&a)[3] << 24);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_tole32(uint32_t a) {
|
||||||
|
return lfs_fromle32(a);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Convert between 32-bit big-endian and native order
|
||||||
|
static inline uint32_t lfs_frombe32(uint32_t a) {
|
||||||
|
#if !defined(LFS_NO_INTRINSICS) && ( \
|
||||||
|
(defined( BYTE_ORDER ) && defined( ORDER_LITTLE_ENDIAN ) && BYTE_ORDER == ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_LITTLE_ENDIAN ) && __BYTE_ORDER == __ORDER_LITTLE_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_LITTLE_ENDIAN__) && __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__))
|
||||||
|
return __builtin_bswap32(a);
|
||||||
|
#elif (defined( BYTE_ORDER ) && defined( ORDER_BIG_ENDIAN ) && BYTE_ORDER == ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER ) && defined(__ORDER_BIG_ENDIAN ) && __BYTE_ORDER == __ORDER_BIG_ENDIAN ) || \
|
||||||
|
(defined(__BYTE_ORDER__) && defined(__ORDER_BIG_ENDIAN__) && __BYTE_ORDER__ == __ORDER_BIG_ENDIAN__)
|
||||||
|
return a;
|
||||||
|
#else
|
||||||
|
return ((uint32_t)((uint8_t*)&a)[0] << 24) |
|
||||||
|
((uint32_t)((uint8_t*)&a)[1] << 16) |
|
||||||
|
((uint32_t)((uint8_t*)&a)[2] << 8) |
|
||||||
|
((uint32_t)((uint8_t*)&a)[3] << 0);
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline uint32_t lfs_tobe32(uint32_t a) {
|
||||||
|
return lfs_frombe32(a);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Calculate CRC-32 with polynomial = 0x04c11db7
|
||||||
|
#ifdef LFS_CRC
|
||||||
|
static inline uint32_t lfs_crc(uint32_t crc, const void *buffer, size_t size) {
|
||||||
|
return LFS_CRC(crc, buffer, size);
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
uint32_t lfs_crc(uint32_t crc, const void *buffer, size_t size);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Allocate memory, only used if buffers are not provided to littlefs
|
||||||
|
//
|
||||||
|
// littlefs current has no alignment requirements, as it only allocates
|
||||||
|
// byte-level buffers.
|
||||||
|
static inline void *lfs_malloc(size_t size) {
|
||||||
|
#if defined(LFS_MALLOC)
|
||||||
|
return LFS_MALLOC(size);
|
||||||
|
#elif !defined(LFS_NO_MALLOC)
|
||||||
|
return malloc(size);
|
||||||
|
#else
|
||||||
|
(void)size;
|
||||||
|
return NULL;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deallocate memory, only used if buffers are not provided to littlefs
|
||||||
|
static inline void lfs_free(void *p) {
|
||||||
|
#if defined(LFS_FREE)
|
||||||
|
LFS_FREE(p);
|
||||||
|
#elif !defined(LFS_NO_MALLOC)
|
||||||
|
free(p);
|
||||||
|
#else
|
||||||
|
(void)p;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
} /* extern "C" */
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
+2063
File diff suppressed because it is too large.
Load diff
+146
@@ -0,0 +1,146 @@
|
|||||||
|
/*
|
||||||
|
* Runner for littlefs benchmarks
|
||||||
|
*
|
||||||
|
* Copyright (c) 2022, The littlefs authors.
|
||||||
|
* SPDX-License-Identifier: BSD-3-Clause
|
||||||
|
*/
|
||||||
|
#ifndef BENCH_RUNNER_H
|
||||||
|
#define BENCH_RUNNER_H
|
||||||
|
|
||||||
|
|
||||||
|
// override LFS_TRACE
|
||||||
|
void bench_trace(const char *fmt, ...);
|
||||||
|
|
||||||
|
#define LFS_TRACE_(fmt, ...) \
|
||||||
|
bench_trace("%s:%d:trace: " fmt "%s\n", \
|
||||||
|
__FILE__, \
|
||||||
|
__LINE__, \
|
||||||
|
__VA_ARGS__)
|
||||||
|
#define LFS_TRACE(...) LFS_TRACE_(__VA_ARGS__, "")
|
||||||
|
#define LFS_EMUBD_TRACE(...) LFS_TRACE_(__VA_ARGS__, "")
|
||||||
|
|
||||||
|
// provide BENCH_START/BENCH_STOP macros
|
||||||
|
void bench_start(void);
|
||||||
|
void bench_stop(void);
|
||||||
|
|
||||||
|
#define BENCH_START() bench_start()
|
||||||
|
#define BENCH_STOP() bench_stop()
|
||||||
|
|
||||||
|
|
||||||
|
// note these are indirectly included in any generated files
|
||||||
|
#include "bd/lfs_emubd.h"
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
// give source a chance to define feature macros
|
||||||
|
#undef _FEATURES_H
|
||||||
|
#undef _STDIO_H
|
||||||
|
|
||||||
|
|
||||||
|
// generated bench configurations
|
||||||
|
struct lfs_config;
|
||||||
|
|
||||||
|
enum bench_flags {
|
||||||
|
BENCH_REENTRANT = 0x1,
|
||||||
|
};
|
||||||
|
typedef uint8_t bench_flags_t;
|
||||||
|
|
||||||
|
typedef struct bench_define {
|
||||||
|
intmax_t (*cb)(void *data);
|
||||||
|
void *data;
|
||||||
|
} bench_define_t;
|
||||||
|
|
||||||
|
struct bench_case {
|
||||||
|
const char *name;
|
||||||
|
const char *path;
|
||||||
|
bench_flags_t flags;
|
||||||
|
size_t permutations;
|
||||||
|
|
||||||
|
const bench_define_t *defines;
|
||||||
|
|
||||||
|
bool (*filter)(void);
|
||||||
|
void (*run)(struct lfs_config *cfg);
|
||||||
|
};
|
||||||
|
|
||||||
|
struct bench_suite {
|
||||||
|
const char *name;
|
||||||
|
const char *path;
|
||||||
|
bench_flags_t flags;
|
||||||
|
|
||||||
|
const char *const *define_names;
|
||||||
|
size_t define_count;
|
||||||
|
|
||||||
|
const struct bench_case *cases;
|
||||||
|
size_t case_count;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// deterministic prng for pseudo-randomness in benches
|
||||||
|
uint32_t bench_prng(uint32_t *state);
|
||||||
|
|
||||||
|
#define BENCH_PRNG(state) bench_prng(state)
|
||||||
|
|
||||||
|
|
||||||
|
// access generated bench defines
|
||||||
|
intmax_t bench_define(size_t define);
|
||||||
|
|
||||||
|
#define BENCH_DEFINE(i) bench_define(i)
|
||||||
|
|
||||||
|
// a few preconfigured defines that control how benches run
|
||||||
|
|
||||||
|
#define READ_SIZE_i 0
|
||||||
|
#define PROG_SIZE_i 1
|
||||||
|
#define ERASE_SIZE_i 2
|
||||||
|
#define ERASE_COUNT_i 3
|
||||||
|
#define BLOCK_SIZE_i 4
|
||||||
|
#define BLOCK_COUNT_i 5
|
||||||
|
#define CACHE_SIZE_i 6
|
||||||
|
#define LOOKAHEAD_SIZE_i 7
|
||||||
|
#define COMPACT_THRESH_i 8
|
||||||
|
#define METADATA_MAX_i 9
|
||||||
|
#define INLINE_MAX_i 10
|
||||||
|
#define BLOCK_CYCLES_i 11
|
||||||
|
#define ERASE_VALUE_i 12
|
||||||
|
#define ERASE_CYCLES_i 13
|
||||||
|
#define BADBLOCK_BEHAVIOR_i 14
|
||||||
|
#define POWERLOSS_BEHAVIOR_i 15
|
||||||
|
|
||||||
|
#define READ_SIZE bench_define(READ_SIZE_i)
|
||||||
|
#define PROG_SIZE bench_define(PROG_SIZE_i)
|
||||||
|
#define ERASE_SIZE bench_define(ERASE_SIZE_i)
|
||||||
|
#define ERASE_COUNT bench_define(ERASE_COUNT_i)
|
||||||
|
#define BLOCK_SIZE bench_define(BLOCK_SIZE_i)
|
||||||
|
#define BLOCK_COUNT bench_define(BLOCK_COUNT_i)
|
||||||
|
#define CACHE_SIZE bench_define(CACHE_SIZE_i)
|
||||||
|
#define LOOKAHEAD_SIZE bench_define(LOOKAHEAD_SIZE_i)
|
||||||
|
#define COMPACT_THRESH bench_define(COMPACT_THRESH_i)
|
||||||
|
#define METADATA_MAX bench_define(METADATA_MAX_i)
|
||||||
|
#define INLINE_MAX bench_define(INLINE_MAX_i)
|
||||||
|
#define BLOCK_CYCLES bench_define(BLOCK_CYCLES_i)
|
||||||
|
#define ERASE_VALUE bench_define(ERASE_VALUE_i)
|
||||||
|
#define ERASE_CYCLES bench_define(ERASE_CYCLES_i)
|
||||||
|
#define BADBLOCK_BEHAVIOR bench_define(BADBLOCK_BEHAVIOR_i)
|
||||||
|
#define POWERLOSS_BEHAVIOR bench_define(POWERLOSS_BEHAVIOR_i)
|
||||||
|
|
||||||
|
#define BENCH_IMPLICIT_DEFINES \
|
||||||
|
BENCH_DEF(READ_SIZE, PROG_SIZE) \
|
||||||
|
BENCH_DEF(PROG_SIZE, ERASE_SIZE) \
|
||||||
|
BENCH_DEF(ERASE_SIZE, 0) \
|
||||||
|
BENCH_DEF(ERASE_COUNT, (1024*1024)/BLOCK_SIZE) \
|
||||||
|
BENCH_DEF(BLOCK_SIZE, ERASE_SIZE) \
|
||||||
|
BENCH_DEF(BLOCK_COUNT, ERASE_COUNT/lfs_max(BLOCK_SIZE/ERASE_SIZE,1))\
|
||||||
|
BENCH_DEF(CACHE_SIZE, lfs_max(64,lfs_max(READ_SIZE,PROG_SIZE))) \
|
||||||
|
BENCH_DEF(LOOKAHEAD_SIZE, 16) \
|
||||||
|
BENCH_DEF(COMPACT_THRESH, 0) \
|
||||||
|
BENCH_DEF(METADATA_MAX, 0) \
|
||||||
|
BENCH_DEF(INLINE_MAX, 0) \
|
||||||
|
BENCH_DEF(BLOCK_CYCLES, -1) \
|
||||||
|
BENCH_DEF(ERASE_VALUE, 0xff) \
|
||||||
|
BENCH_DEF(ERASE_CYCLES, 0) \
|
||||||
|
BENCH_DEF(BADBLOCK_BEHAVIOR, LFS_EMUBD_BADBLOCK_PROGERROR) \
|
||||||
|
BENCH_DEF(POWERLOSS_BEHAVIOR, LFS_EMUBD_POWERLOSS_NOOP)
|
||||||
|
|
||||||
|
#define BENCH_GEOMETRY_DEFINE_COUNT 4
|
||||||
|
#define BENCH_IMPLICIT_DEFINE_COUNT 16
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
||||||
+2818
File diff suppressed because it is too large.
Load diff
+142
@@ -0,0 +1,142 @@
|
|||||||
|
/*
|
||||||
|
* Runner for littlefs tests
|
||||||
|
*
|
||||||
|
* Copyright (c) 2022, The littlefs authors.
|
||||||
|
* SPDX-License-Identifier: BSD-3-Clause
|
||||||
|
*/
|
||||||
|
#ifndef TEST_RUNNER_H
|
||||||
|
#define TEST_RUNNER_H
|
||||||
|
|
||||||
|
|
||||||
|
// override LFS_TRACE
|
||||||
|
void test_trace(const char *fmt, ...);
|
||||||
|
|
||||||
|
#define LFS_TRACE_(fmt, ...) \
|
||||||
|
test_trace("%s:%d:trace: " fmt "%s\n", \
|
||||||
|
__FILE__, \
|
||||||
|
__LINE__, \
|
||||||
|
__VA_ARGS__)
|
||||||
|
#define LFS_TRACE(...) LFS_TRACE_(__VA_ARGS__, "")
|
||||||
|
#define LFS_EMUBD_TRACE(...) LFS_TRACE_(__VA_ARGS__, "")
|
||||||
|
|
||||||
|
|
||||||
|
// note these are indirectly included in any generated files
|
||||||
|
#include "bd/lfs_emubd.h"
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
// give source a chance to define feature macros
|
||||||
|
#undef _FEATURES_H
|
||||||
|
#undef _STDIO_H
|
||||||
|
|
||||||
|
|
||||||
|
// generated test configurations
|
||||||
|
struct lfs_config;
|
||||||
|
|
||||||
|
enum test_flags {
|
||||||
|
TEST_REENTRANT = 0x1,
|
||||||
|
};
|
||||||
|
typedef uint8_t test_flags_t;
|
||||||
|
|
||||||
|
typedef struct test_define {
|
||||||
|
intmax_t (*cb)(void *data);
|
||||||
|
void *data;
|
||||||
|
} test_define_t;
|
||||||
|
|
||||||
|
struct test_case {
|
||||||
|
const char *name;
|
||||||
|
const char *path;
|
||||||
|
test_flags_t flags;
|
||||||
|
size_t permutations;
|
||||||
|
|
||||||
|
const test_define_t *defines;
|
||||||
|
|
||||||
|
bool (*filter)(void);
|
||||||
|
void (*run)(struct lfs_config *cfg);
|
||||||
|
};
|
||||||
|
|
||||||
|
struct test_suite {
|
||||||
|
const char *name;
|
||||||
|
const char *path;
|
||||||
|
test_flags_t flags;
|
||||||
|
|
||||||
|
const char *const *define_names;
|
||||||
|
size_t define_count;
|
||||||
|
|
||||||
|
const struct test_case *cases;
|
||||||
|
size_t case_count;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// deterministic prng for pseudo-randomness in testes
|
||||||
|
uint32_t test_prng(uint32_t *state);
|
||||||
|
|
||||||
|
#define TEST_PRNG(state) test_prng(state)
|
||||||
|
|
||||||
|
|
||||||
|
// access generated test defines
|
||||||
|
intmax_t test_define(size_t define);
|
||||||
|
|
||||||
|
#define TEST_DEFINE(i) test_define(i)
|
||||||
|
|
||||||
|
// a few preconfigured defines that control how tests run
|
||||||
|
|
||||||
|
#define READ_SIZE_i 0
|
||||||
|
#define PROG_SIZE_i 1
|
||||||
|
#define ERASE_SIZE_i 2
|
||||||
|
#define ERASE_COUNT_i 3
|
||||||
|
#define BLOCK_SIZE_i 4
|
||||||
|
#define BLOCK_COUNT_i 5
|
||||||
|
#define CACHE_SIZE_i 6
|
||||||
|
#define LOOKAHEAD_SIZE_i 7
|
||||||
|
#define COMPACT_THRESH_i 8
|
||||||
|
#define METADATA_MAX_i 9
|
||||||
|
#define INLINE_MAX_i 10
|
||||||
|
#define BLOCK_CYCLES_i 11
|
||||||
|
#define ERASE_VALUE_i 12
|
||||||
|
#define ERASE_CYCLES_i 13
|
||||||
|
#define BADBLOCK_BEHAVIOR_i 14
|
||||||
|
#define POWERLOSS_BEHAVIOR_i 15
|
||||||
|
#define DISK_VERSION_i 16
|
||||||
|
|
||||||
|
#define READ_SIZE TEST_DEFINE(READ_SIZE_i)
|
||||||
|
#define PROG_SIZE TEST_DEFINE(PROG_SIZE_i)
|
||||||
|
#define ERASE_SIZE TEST_DEFINE(ERASE_SIZE_i)
|
||||||
|
#define ERASE_COUNT TEST_DEFINE(ERASE_COUNT_i)
|
||||||
|
#define BLOCK_SIZE TEST_DEFINE(BLOCK_SIZE_i)
|
||||||
|
#define BLOCK_COUNT TEST_DEFINE(BLOCK_COUNT_i)
|
||||||
|
#define CACHE_SIZE TEST_DEFINE(CACHE_SIZE_i)
|
||||||
|
#define LOOKAHEAD_SIZE TEST_DEFINE(LOOKAHEAD_SIZE_i)
|
||||||
|
#define COMPACT_THRESH TEST_DEFINE(COMPACT_THRESH_i)
|
||||||
|
#define METADATA_MAX TEST_DEFINE(METADATA_MAX_i)
|
||||||
|
#define INLINE_MAX TEST_DEFINE(INLINE_MAX_i)
|
||||||
|
#define BLOCK_CYCLES TEST_DEFINE(BLOCK_CYCLES_i)
|
||||||
|
#define ERASE_VALUE TEST_DEFINE(ERASE_VALUE_i)
|
||||||
|
#define ERASE_CYCLES TEST_DEFINE(ERASE_CYCLES_i)
|
||||||
|
#define BADBLOCK_BEHAVIOR TEST_DEFINE(BADBLOCK_BEHAVIOR_i)
|
||||||
|
#define POWERLOSS_BEHAVIOR TEST_DEFINE(POWERLOSS_BEHAVIOR_i)
|
||||||
|
#define DISK_VERSION TEST_DEFINE(DISK_VERSION_i)
|
||||||
|
|
||||||
|
#define TEST_IMPLICIT_DEFINES \
|
||||||
|
TEST_DEF(READ_SIZE, PROG_SIZE) \
|
||||||
|
TEST_DEF(PROG_SIZE, ERASE_SIZE) \
|
||||||
|
TEST_DEF(ERASE_SIZE, 0) \
|
||||||
|
TEST_DEF(ERASE_COUNT, (1024*1024)/ERASE_SIZE) \
|
||||||
|
TEST_DEF(BLOCK_SIZE, ERASE_SIZE) \
|
||||||
|
TEST_DEF(BLOCK_COUNT, ERASE_COUNT/lfs_max(BLOCK_SIZE/ERASE_SIZE,1)) \
|
||||||
|
TEST_DEF(CACHE_SIZE, lfs_max(64,lfs_max(READ_SIZE,PROG_SIZE))) \
|
||||||
|
TEST_DEF(LOOKAHEAD_SIZE, 16) \
|
||||||
|
TEST_DEF(COMPACT_THRESH, 0) \
|
||||||
|
TEST_DEF(METADATA_MAX, 0) \
|
||||||
|
TEST_DEF(INLINE_MAX, 0) \
|
||||||
|
TEST_DEF(BLOCK_CYCLES, -1) \
|
||||||
|
TEST_DEF(ERASE_VALUE, 0xff) \
|
||||||
|
TEST_DEF(ERASE_CYCLES, 0) \
|
||||||
|
TEST_DEF(BADBLOCK_BEHAVIOR, LFS_EMUBD_BADBLOCK_PROGERROR) \
|
||||||
|
TEST_DEF(POWERLOSS_BEHAVIOR, LFS_EMUBD_POWERLOSS_NOOP) \
|
||||||
|
TEST_DEF(DISK_VERSION, 0)
|
||||||
|
|
||||||
|
#define TEST_GEOMETRY_DEFINE_COUNT 4
|
||||||
|
#define TEST_IMPLICIT_DEFINE_COUNT 17
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
||||||
Binary file not shown.
@@ -8,5 +8,10 @@
|
|||||||
"path": "/packages/system/sqlite",
|
"path": "/packages/system/sqlite",
|
||||||
"ver": "v3.19.3",
|
"ver": "v3.19.3",
|
||||||
"name": "SQLITE"
|
"name": "SQLITE"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"path": "/packages/system/littlefs",
|
||||||
|
"ver": "v2.11.2",
|
||||||
|
"name": "LITTLEFS"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
@@ -40,12 +40,12 @@ __exit:
|
|||||||
if ((result > 0) && (!init_ok))
|
if ((result > 0) && (!init_ok))
|
||||||
{
|
{
|
||||||
init_ok = 1;
|
init_ok = 1;
|
||||||
log_i("RT-Thread Flash Abstraction Layer initialize success.");
|
log_i("Flash Abstraction Layer initialize success.");
|
||||||
}
|
}
|
||||||
else if(result <= 0)
|
else if(result <= 0)
|
||||||
{
|
{
|
||||||
init_ok = 0;
|
init_ok = 0;
|
||||||
log_e("RT-Thread Flash Abstraction Layer initialize failed.");
|
log_e("Flash Abstraction Layer initialize failed.");
|
||||||
}
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
|
|||||||
+22
-1
@@ -88,7 +88,7 @@
|
|||||||
#define DFS_USING_WORKDIR
|
#define DFS_USING_WORKDIR
|
||||||
#define DFS_FD_MAX 16
|
#define DFS_FD_MAX 16
|
||||||
#define RT_USING_DFS_V1
|
#define RT_USING_DFS_V1
|
||||||
#define DFS_FILESYSTEMS_MAX 4
|
#define DFS_FILESYSTEMS_MAX 6
|
||||||
#define DFS_FILESYSTEM_TYPES_MAX 4
|
#define DFS_FILESYSTEM_TYPES_MAX 4
|
||||||
#define RT_USING_DFS_ELMFAT
|
#define RT_USING_DFS_ELMFAT
|
||||||
|
|
||||||
@@ -111,6 +111,11 @@
|
|||||||
#define RT_USING_DFS_DEVFS
|
#define RT_USING_DFS_DEVFS
|
||||||
#define RT_USING_DFS_TMPFS
|
#define RT_USING_DFS_TMPFS
|
||||||
/* end of DFS: device virtual file system */
|
/* end of DFS: device virtual file system */
|
||||||
|
#define RT_USING_FAL
|
||||||
|
#define FAL_DEBUG 0
|
||||||
|
#define FAL_PART_HAS_TABLE_CFG
|
||||||
|
#define FAL_USING_SFUD_PORT
|
||||||
|
#define FAL_USING_NOR_FLASH_DEV_NAME "W25Q128"
|
||||||
|
|
||||||
/* Device Drivers */
|
/* Device Drivers */
|
||||||
|
|
||||||
@@ -119,6 +124,7 @@
|
|||||||
#define RT_USING_SERIAL
|
#define RT_USING_SERIAL
|
||||||
#define RT_USING_SERIAL_V1
|
#define RT_USING_SERIAL_V1
|
||||||
#define RT_SERIAL_RB_BUFSZ 512
|
#define RT_SERIAL_RB_BUFSZ 512
|
||||||
|
#define RT_USING_MTD_NOR
|
||||||
#define RT_USING_RTC
|
#define RT_USING_RTC
|
||||||
#define RT_USING_SOFT_RTC
|
#define RT_USING_SOFT_RTC
|
||||||
#define RT_USING_SDIO
|
#define RT_USING_SDIO
|
||||||
@@ -130,6 +136,11 @@
|
|||||||
#define RT_USING_SPI
|
#define RT_USING_SPI
|
||||||
#define RT_USING_QSPI
|
#define RT_USING_QSPI
|
||||||
#define RT_USING_SPI_MSD
|
#define RT_USING_SPI_MSD
|
||||||
|
#define RT_USING_SFUD
|
||||||
|
#define RT_SFUD_USING_SFDP
|
||||||
|
#define RT_SFUD_USING_FLASH_INFO_TABLE
|
||||||
|
#define RT_SFUD_USING_QSPI
|
||||||
|
#define RT_SFUD_SPI_MAX_HZ 50000000
|
||||||
#define RT_USING_DEV_BUS
|
#define RT_USING_DEV_BUS
|
||||||
#define RT_USING_PIN
|
#define RT_USING_PIN
|
||||||
|
|
||||||
@@ -263,6 +274,16 @@
|
|||||||
#define PKG_SQLITE_SQL_MAX_LEN 1024
|
#define PKG_SQLITE_SQL_MAX_LEN 1024
|
||||||
#define PKG_SQLITE_DB_NAME_MAX_LEN 64
|
#define PKG_SQLITE_DB_NAME_MAX_LEN 64
|
||||||
#define PKG_USING_SQLITE_V3193
|
#define PKG_USING_SQLITE_V3193
|
||||||
|
#define PKG_USING_LITTLEFS
|
||||||
|
#define PKG_USING_LITTLEFS_V2112
|
||||||
|
#define LFS_READ_SIZE 256
|
||||||
|
#define LFS_PROG_SIZE 256
|
||||||
|
#define LFS_BLOCK_SIZE 4096
|
||||||
|
#define LFS_CACHE_SIZE 256
|
||||||
|
#define LFS_BLOCK_CYCLES 500
|
||||||
|
#define LFS_THREADSAFE
|
||||||
|
#define LFS_LOOKAHEAD_MAX 128
|
||||||
|
#define RT_DEF_LFS_DRIVERS 2
|
||||||
/* end of system packages */
|
/* end of system packages */
|
||||||
|
|
||||||
/* peripheral libraries and drivers */
|
/* peripheral libraries and drivers */
|
||||||
|
|||||||
@@ -5,6 +5,7 @@
|
|||||||
/* Automatically generated file; DO NOT EDIT. */
|
/* Automatically generated file; DO NOT EDIT. */
|
||||||
/* RT-Thread pre-include file */
|
/* RT-Thread pre-include file */
|
||||||
|
|
||||||
|
#define LFS_CONFIG lfs_config.h
|
||||||
#define RT_USING_LIBC
|
#define RT_USING_LIBC
|
||||||
#define RT_USING_NEWLIBC
|
#define RT_USING_NEWLIBC
|
||||||
#define _POSIX_C_SOURCE 1
|
#define _POSIX_C_SOURCE 1
|
||||||
|
|||||||
Reference in new issue
Block a user